Skip to content

Workspace enumeration via tool-layer 'not found' messages (connector-tools), follow-up to #17 #346

@mgoldsborough

Description

@mgoldsborough

Summary

After #17 collapsed workspace-resolution errors into a single generic 403 "Access denied to workspace." (no ID echo), several tool-layer paths still distinguish "workspace does not exist" from "exists but access denied" by echoing the workspace id in a not-found message. The clearest case is src/tools/connector-tools.ts, where install/management actions do:

const ws = await ctx.runtime.getWorkspaceStore().get(wsId);
if (!ws) return errResult(`Workspace "${wsId}" not found.`);
// ... then:
if (!isWorkspaceAdmin(ws, identity)) return errResult(/* admin required */);

An authenticated caller supplying an arbitrary wsId (tool arg) can distinguish:

  • nonexistent workspace → Workspace "<id>" not found.
  • existent but not-admin → admin-required error

That's the same enumeration shape #17 closed, one layer up. Multiple sites in connector-tools.ts follow this pattern (~lines 837, 1315, 1435, 1493, 1821, 1906, 1973).

Scope / severity

Lower severity than #17:

  • Requires an authenticated session (not the unauthenticated HTTP data-path gate Use generic error messages for workspace resolution failures #17 addressed).
  • Returns tool-result text, not an HTTP status code.
  • workspace-mgmt-tools.ts CRUD paths that echo the id are gated behind an org-admin check first, so those are not a cross-tenant leak — this issue is specifically the connector-tools (and similar) paths that echo the id before/around the per-workspace admin check.

Suggested fix

For paths reachable with an attacker-suppliable wsId, return a single generic "access denied" result for both not-found and not-authorized, without echoing the id — mirroring the #17 resolution. Leave paths that operate only on an already-resolved/authorized workspace as-is.

Priority

P3 — information disclosure, minor (same class as #17).

Metadata

Metadata

Assignees

No one assigned

    Labels

    securitySecurity hardening and defense-in-depth

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions