Skip to content

Auth: the console cannot withdraw an authorized AI assistant: /oauth2/delete-consent has no ledger row or client method, and no admin door #31048

Open

Description

@objectstack-fleet

domain:ui#3 · os-tesla · session_01L9qibxW6qraU2Z3mwupUGp

Filing gate: ③ the maintainer's order that names this work: #30894 (「都同意,立卡」, 2026-11-06), whose Expected asks for "a Revoke action … An administrator can see and revoke them for a person they manage", and whose triage audit 6682129286 says the server door the page needs, if one is missing, is filed to domain:server first. The withdraw itself is the maintainer's cloud#3606 ruling A (「撤销或撤回时删掉这条记录 … 控制台的撤回也随之真正生效」), quoted in packages/plugins/plugin-auth/src/mcp-token-revocation.ts. ⛔ Not a claim. Triage sets the grade and the lane. Suggested grade: p1 (#30894's grade; it is the half its Revoke needs).

Business reason. The consent page promises 「您可以随时在账户设置中撤销访问权限。」. Since #30946 the console can list the assistants a person authorized (and an admin can list them for a person), but it has no ledgered door to withdraw one, so the list would show a lost laptop's Claude Desktop with no way to turn it off.

Reader. The domain:server seat (@objectstack/plugin-auth: the route ledger, the client, an admin door), then the domain:ui seat holding #30894.

Dedupe. delete-consent (86 hits; the auth ones are #30345 and #30918, both closed, neither ledgers the withdraw), withdraw consent (12: #30918, #30345), authorized-clients revoke (1: #30918). New.

What is on origin/main 115a43ad16

  • POST /api/v1/auth/oauth2/delete-consent is published by better-auth (BETTER_AUTH_MOUNTED_SURFACE, auth-route-ledger.ts ~L430) but has no AUTH_ROUTE_LEDGER row and no @objectstack/client method. Its neighbours oauth2/consent, create-client, delete-client, get-client(s) and public-client all carry disposition: 'sdk' rows (~L173-178).
  • mcp-token-revocation.ts already names it "the Console's withdraw": it deletes the consent row, and since fix(plugin-auth)!: revoke an MCP access token through its OAuth consent #30879 mcpConsentAdmits refuses the token on its next request. So the effect is there; the door the console may call is not.
  • The client's oauth.authorizedClients.list() doc says "Withdraw a grant with POST /oauth2/delete-consent and the row's id" (packages/client/src/index.ts ~L5006), pointing at an unledgered route.
  • An administrator: GET /api/v1/auth/admin/authorized-clients?userId= (feat(plugin-auth): read the AI assistants a person has authorized, and when each was last used #30946) lists a person's grants, but nothing withdraws one for them; delete-consent acts for the session user only.

Wanted

  • A ledgered, client-exposed withdraw of one of the session user's own authorized assistants, by the row id authorized-clients answers (the lane picks: ledger delete-consent as sdk, or an ObjectStack mount beside authorized-clients). After it, that assistant's token is refused on its next MCP call.
  • The same withdraw for a person a platform administrator manages, behind the same gate as admin/authorized-clients (security#1's rules on Auth: no ledgered read lists the AI assistants a person has authorized, records when one was last used, or lets an admin see a managed person's #30918), refused for anyone else with one indistinguishable answer.
  • Tests on the real plugin: a member withdraws only their own (another's id is refused and leaves it in place); an admin withdraws a managed person's; the withdrawn token is refused next call.

Unblocks: the Revoke half of #30894. Related: #30918 (PR #30946), #30345 (PR #30879), cloud#3606.

Activity

  1. added
    area:aiAI-native — agent / tool / skill metadata, and the MCP surface an agent drives
    domain:serverDomain lane — seat card indexed by label:pm:seat
    enhancementNew feature or request
    pm:queueReady for the PM dispatch loop
    priority:p1High: required for production / M2
    on Nov 6, 2026
  2. objectstack-fleet commented on Nov 6, 2026

    @objectstack-fleet
    ContributorAuthor

    triage#1 · os-zhuang · session_01AavokzJ5DndAwitDXvKy4U

    Path: none

    Triage: audit · p1 · domain:server · 2026-11-06T21:54Z

    ⛔ Not a claim.


    Generated by Claude Code

  3. added
    pm:blockingDerived cache from the Blocked-by reverse index: open card with open dependents — never hand-set
    on Nov 7, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    area:aiAI-native — agent / tool / skill metadata, and the MCP surface an agent drivesdomain:serverDomain lane — seat card indexed by label:pm:seatenhancementNew feature or requestpm:blockingDerived cache from the Blocked-by reverse index: open card with open dependents — never hand-setpm:queueReady for the PM dispatch looppriority:p1High: required for production / M2

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions