{"record":{"id":"317bbfcbfe975b12","repo":"Significant-Gravitas/AutoGPT","slug":"invitation-invitation-id-not-found","errorCode":null,"errorMessage":"Invitation {invitation_id} not found","messagePattern":"Invitation (.+?) not found","errorType":"http","errorClass":"NotFoundError","httpStatus":404,"severity":"error","filePath":"autogpt_platform/backend/backend/api/features/orgs/invitation_routes.py","lineNumber":128,"sourceCode":"\n@org_router.delete(\n    \"/{invitation_id}\",\n    summary=\"Revoke invitation\",\n    tags=[\"orgs\", \"invitations\"],\n    status_code=204,\n)\nasync def revoke_invitation(\n    org_id: str,\n    invitation_id: str,\n    ctx: Annotated[\n        RequestContext,\n        Security(requires_org_permission(OrgAction.MANAGE_MEMBERS)),\n    ],\n) -> None:\n    _verify_org_path(ctx, org_id)\n    invitation = await prisma.orginvitation.find_unique(where={\"id\": invitation_id})\n    if invitation is None or invitation.orgId != org_id:\n        raise NotFoundError(f\"Invitation {invitation_id} not found\")\n\n    await prisma.orginvitation.update(\n        where={\"id\": invitation_id},\n        data={\"revokedAt\": datetime.now(timezone.utc)},\n    )\n\n\n# --- Token-based endpoints (under /api/invitations) ---\n\n\n@router.post(\n    \"/{token}/accept\",\n    summary=\"Accept invitation\",\n    tags=[\"invitations\"],\n    dependencies=[Security(requires_user)],\n)\nasync def accept_invitation(\n    token: str,","sourceCodeStart":110,"sourceCodeEnd":146,"githubUrl":"https://github.com/Significant-Gravitas/AutoGPT/blob/9c8bb5550f446ba5d3046b78896578742495b3cf/autogpt_platform/backend/backend/api/features/orgs/invitation_routes.py#L110-L146","documentation":"Raised by DELETE revoke-invitation when the OrgInvitation record with the given invitation_id either does not exist or exists but its orgId does not match the org_id in the path. This prevents an admin of org A from revoking (or even probing) invitations of org B. It is a NotFoundError (mapped to HTTP 404).","triggerScenarios":"POST/DELETE to /api/orgs/{org_id}/invitations/{invitation_id}/revoke with an invitation id from another org, a deleted invitation, or a malformed/typo'd id. Also when the invitation list in the UI is stale and the row was already revoked/removed.","commonSituations":"Admin has multiple orgs open and copies an invitation id across contexts; concurrent admin already revoked and cleanup removed the record; frontend keeps a cached list of invitations after org switch.","solutions":["Confirm invitation_id comes from the pending-invitations list of the same org_id in the URL.","If the 404 is unexpected, query prisma.orginvitation.find_unique for the id and inspect its orgId.","Refresh the invitations table after the error and treat a 404 as 'already gone' — remove the row from the UI.","Check for trailing whitespace or URL-encoding issues in the id parameter."],"exampleFix":"# before\ninvitation = await prisma.orginvitation.find_unique(where={'id': invitation_id})\n# after — verify org ownership before acting\ninvitation = await prisma.orginvitation.find_unique(where={'id': invitation_id})\nif invitation is None or invitation.orgId != org_id:\n    return None  # treat as already revoked/removed in the UI","handlingStrategy":"try-catch","validationCode":"const pending = await api.get(`/api/orgs/${orgId}/invitations/pending`).then(r => r.data);\nconst exists = pending.some(i => i.id === invitationId);","typeGuard":null,"tryCatchPattern":"try {\n  await api.delete(`/api/orgs/${orgId}/invitations/${invitationId}/revoke`);\n} catch (e) {\n  if (e.status === 404) { removeInvitationFromUI(invitationId); return; }\n  throw e;\n}","preventionTips":["Revoke only ids obtained from the same org's invitation list","Treat 404 as already-gone and reconcile UI state","Refresh the list after concurrent admin actions"],"tags":["invitations","orgs","not-found","http-404","authorization"],"backgroundTag":null,"analyzedSha":"9c8bb5550f446ba5d3046b78896578742495b3cf","analyzedAt":"2026-08-14T17:17:21.957Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}