feat: add per-tab workspace authentication infrastructure (#8073)

## Summary
Add workspace authentication composables and types for per-tab workspace
isolation. This infrastructure enables users to work in different
workspaces in different browser tabs.

## Changes
- **useWorkspaceAuth composable** - workspace token management
- Exchange Firebase token for workspace-scoped JWT via `POST
/api/auth/token`
  - Auto-refresh tokens 5 minutes before expiry
  - Per-tab sessionStorage caching
- **useWorkspaceSwitch composable** - workspace switching with unsaved
changes confirmation
- **WorkspaceWithRole/WorkspaceTokenResponse types** - aligned with
backend API
- **firebaseAuthStore.getAuthHeader()** - prioritizes workspace tokens
over Firebase tokens
- **useSessionCookie** - uses Firebase token directly (getIdToken())
since getAuthHeader() now returns workspace token

## Backend Dependency
- `POST /api/auth/token` - exchange Firebase token for workspace token
- `GET /api/workspaces` - list user's workspaces

## Related
- https://github.com/Comfy-Org/ComfyUI_frontend/pull/6295

┆Issue is synchronized with this [Notion
page](https://www.notion.so/PR-8073-feat-add-per-tab-workspace-authentication-infrastructure-2e96d73d3650816c8cf9dae9c330aebb)
by [Unito](https://www.unito.io)

---------

Co-authored-by: anthropic/claude <noreply@anthropic.com>
Co-authored-by: Amp <amp@ampcode.com>
Co-authored-by: Simula_r <18093452+simula-r@users.noreply.github.com>
This commit is contained in:
Christian Byrne
2026-01-15 17:24:48 -08:00
committed by GitHub
parent 5409bf86a9
commit 6048fab239
12 changed files with 1392 additions and 36 deletions

View File

@@ -2592,5 +2592,20 @@
"completed": "Completed",
"failed": "Failed"
}
},
"workspace": {
"unsavedChanges": {
"title": "Unsaved Changes",
"message": "You have unsaved changes. Do you want to discard them and switch workspaces?"
}
},
"workspaceAuth": {
"errors": {
"notAuthenticated": "You must be logged in to access workspaces",
"invalidFirebaseToken": "Authentication failed. Please try logging in again.",
"accessDenied": "You do not have access to this workspace",
"workspaceNotFound": "Workspace not found",
"tokenExchangeFailed": "Failed to authenticate with workspace: {error}"
}
}
}