Tencent/WeKnora · error

WEKNORA_REDIS_NAMESPACE must not contain control characters

Error message

WEKNORA_REDIS_NAMESPACE must not contain control characters

What it means

validateRedisNamespace rejects a WEKNORA_REDIS_NAMESPACE containing Unicode control characters. Control chars produce malformed or ambiguous Redis keys and log output, so NewRedisSessionSandboxBindingStore rejects them at startup.

Solutions

  1. Trim the env value when loading (strings.TrimSpace) or fix at the loader/secret-mount layer.
  2. Fix the .env/secret source so the value has no trailing newline (printf without \n).
  3. Verify bytes with `echo -n "$WEKNORA_REDIS_NAMESPACE" | od -c` and remove \n/\r.

Example fix

// before
ns := os.Getenv("WEKNORA_REDIS_NAMESPACE") // "weknora\n"
store, err := sandbox.NewRedisSessionSandboxBindingStore(client, ns) // fails
// after
ns := strings.TrimSpace(os.Getenv("WEKNORA_REDIS_NAMESPACE"))
store, err := sandbox.NewRedisSessionSandboxBindingStore(client, ns)
Defensive patterns

Strategy: validation

Validate before calling

ns := strings.TrimSpace(os.Getenv("WEKNORA_REDIS_NAMESPACE"))
for _, r := range ns {
    if unicode.IsControl(r) { return fmt.Errorf("WEKNORA_REDIS_NAMESPACE has control chars: %q", ns) }
}

Try / catch

store, err := sandbox.NewRedisSessionSandboxBindingStore(client, ns)
if err != nil {
    return fmt.Errorf("redis namespace %q rejected: %w", ns, err)
}

Prevention

When it happens

Trigger: Starting the service with WEKNORA_REDIS_NAMESPACE containing control runes (e.g. trailing \n from an untrimmed env file, \r from Windows CRLF, or an embedded \t).

Common situations: Docker/K8s secret mounted with a trailing newline loaded verbatim into the env var; .env file edited on Windows; echo/base64 mishandling adding a newline.

Related errors


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

Appendix: source

Thrown at internal/sandbox/session_binding_redis.go:409

	return "weknora:sandbox:session:{" + s.hashTag(key) + "}:create-lock"
}

func (s *RedisSessionSandboxBindingStore) hashTag(key SessionSandboxKey) string {
	return fmt.Sprintf("%s:%d:%s", s.namespace, key.TenantID, key.SessionID)
}

var (
	_ tenantBindingScanner  = (*RedisSessionSandboxBindingStore)(nil)
	_ sessionTurnLeaseStore = (*RedisSessionSandboxBindingStore)(nil)
)

func validateRedisNamespace(namespace string) error {
	if strings.ContainsAny(namespace, "{}") {
		return errors.New("WEKNORA_REDIS_NAMESPACE must not contain braces")
	}
	for _, r := range namespace {
		if unicode.IsControl(r) {
			return errors.New("WEKNORA_REDIS_NAMESPACE must not contain control characters")
		}
	}
	return nil
}

View on GitHub (pinned to 988cbb0330)