Tencent/WeKnora · error

resource registration requires tenant and physical path

Error message

resource registration requires tenant and physical path

What it means

Resource.Register requires a non-zero tenant ID and a non-empty physical path. After trimming whitespace, if either is missing the registration is rejected outright. This is an input-contract error: nothing can be registered without knowing who owns it and where the bytes live.

Source

Thrown at internal/application/service/resource.go:53

		return "", err
	}
	return base64.RawURLEncoding.EncodeToString(buf), nil
}

func resourceLocationHash(path string) string {
	sum := sha256.Sum256([]byte(path))
	return hex.EncodeToString(sum[:])
}

func (s *resourceCatalog) Register(
	ctx context.Context,
	tenantID uint64,
	physicalPath string,
	meta interfaces.ResourceRegistration,
) (string, error) {
	physicalPath = strings.TrimSpace(physicalPath)
	if tenantID == 0 || physicalPath == "" {
		return "", fmt.Errorf("resource registration requires tenant and physical path")
	}
	if _, ok := types.ParseResourcePath(physicalPath); ok {
		return physicalPath, nil
	}
	locationHash := resourceLocationHash(physicalPath)
	existing, err := s.repo.GetByTenantLocation(ctx, tenantID, locationHash)
	if err != nil {
		return "", err
	}
	if existing != nil {
		return types.BuildResourcePath(existing.Handle), nil
	}

	backendID, inner, scoped := types.ParseStorageBackendPath(physicalPath)
	providerPath := physicalPath
	if scoped {
		providerPath = inner
	}

View on GitHub (pinned to 988cbb0330)

Solutions

  1. Ensure the caller has an authenticated context and pass the real tenant ID (non-zero).
  2. Trim and validate physicalPath at the call site before invoking Register.
  3. Fix upstream code that drops the tenant ID (e.g. background jobs losing context values).
  4. Reject earlier in your own API layer with a clearer validation message including which field is missing.

Example fix

// before
id, err := svc.Register(ctx, tenantID, filePath, meta) // tenantID==0, filePath==""
// after
if tenantID == 0 || strings.TrimSpace(filePath) == "" {
    return nil, fmt.Errorf("cannot register resource: tenantID=%d path=%q", tenantID, filePath)
}
id, err := svc.Register(ctx, tenantID, strings.TrimSpace(filePath), meta)
Defensive patterns

Strategy: validation

Validate before calling

if tenantID == 0 { return fmt.Errorf("tenantID required") }
if strings.TrimSpace(physicalPath) == "" { return fmt.Errorf("physicalPath required") }

Type guard

func registrable(tenantID uint64, physicalPath string) bool {
    return tenantID != 0 && strings.TrimSpace(physicalPath) != ""
}

Try / catch

id, err := svc.Register(ctx, tenantID, path, meta)
if err != nil && strings.Contains(err.Error(), "requires tenant and physical path") {
    return nil, fmt.Errorf("invalid resource registration input: %w", err)
}

Prevention

When it happens

Trigger: Calling Register(ctx, 0, "", meta) or with a physicalPath that is only whitespace; programmatically building registrations where tenant scoping was lost upstream (unauthenticated context, nil tenant).

Common situations: Upload pipeline losing tenant context before resource registration; passing a file path variable that was never assigned; migrating code that previously registered tenant-less global resources.

Understand the failure class

Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.

Related errors


AI-assisted analysis of Tencent/WeKnora@988cbb0330 (2026-09-02). Data as JSON: /api/errors/855f340c10c824f9. Report an issue: GitHub.