認証と権限
Chorus はすべてのリクエストを認証して一つの統一された AuthContext に解決し、そのうえで、きめ細かな権限
セットに照らしてエージェントに何ができるかを制御します。本ページは、認証方式、エージェント API キーの
仕様、そして MCP ツールの可視性と REST アクセスの両方を駆動する権限モデルを説明します。
引用できる安定したアンカー:#統一された-authcontext、
#解決カスケード、#agent-api-key、
#権限モデル、#ロールプリセット、
#カスタム権限と有効な権限セット。
統一された AuthContext
Section titled “統一された AuthContext”認証されたすべてのリクエストは、三つのコンテキスト種別のいずれかへ解決されます。マルチテナンシーは
companyUuid を通じて強制されます。すべてのデータアクセスはその範囲に限定され、複数のワークスペースにまたがって
操作できるのはスーパー管理者だけです。
| コンテキスト種別 | type | 主なフィールド | 生成元 |
|---|---|---|---|
| User | user | companyUuid、actorUuid、email、name | OIDC、Default Auth |
| Agent | agent | companyUuid、actorUuid、roles[](プリセット選択子)、permissions[](有効セット)、agentName、ownerUuid | API キー |
| スーパー管理者 | super_admin | email(companyUuid なし) | スーパー管理者セッション |
エージェントの認可は、その permissions[]、つまりフラットな有効セットからすべて生じます。roles[]
フィールドはプリセットの選択子にすぎず、認可の源ではありません。
解決カスケード
Section titled “解決カスケード”単一の入口が、優先順位に従って各方式を順に試し、最初の成功で返します。
1. Authorization: Bearer <token> ├─ cho_… 接頭辞 → API key の検証 → Agent コンテキスト ├─ RS*/ES* JWT → OIDC トークンの検証 → User コンテキスト └─ HS256 JWT → Chorus JWT の検証 → User コンテキスト2. セッション Cookie └─ user_session → User3. OIDC Cookie(SSE / EventSource 用、Authorization ヘッダーなし) └─ oidc_access_token cookie → User コンテキスト4. 一致なし → 未認証ステップ 1 のトークンは形状で分類されます。cho_ 接頭辞は API キーです。それ以外の 3 つの部分からなる JWT は、
ヘッダーのアルゴリズムが非対称(RS*/ES*)なら OIDC、HS256 なら Chorus の自己署名セッション
トークンです。
セッション署名用の秘密鍵
Section titled “セッション署名用の秘密鍵”NEXTAUTH_SECRET は Default Auth の user_session とスーパー管理者の admin_session JWT
に署名します。スーパー管理者ルートは通常のユーザー認証とは別に admin_session を検証します。
OIDC トークンはプロバイダーの鍵で、エージェントの API キーは保存されたハッシュで検証します。
NEXTAUTH_SECRET を変更すると Chorus が署名したセッションは無効になりますが、API キーや OIDC トークンには影響しません。
npm ランチャーは生成した鍵を既定で ~/.chorus-data/.secret に保存し、Docker は /app/data/.secret
を使います。どちらも環境変数の既知の公開プレースホルダーを無視し、保存済みの鍵が公開プレースホルダー
なら起動を停止します。直接起動する場合は鍵を自分で設定してください。
0.18.1 での移行、永続化、レプリカの設定は Docker のセッション秘密鍵を参照してください。
Agent API key
Section titled “Agent API key”エージェントは、すべての MCP と REST リクエストで bearer の API キーにより認証します。
Authorization: Bearer cho_<random>その仕様は次のとおりです。
cho_接頭辞。 すべてのキーはcho_で始まり、その後に base64url エンコードされたランダム バイトが続きます。解決カスケードはこの接頭辞でキーと JWT を見分けます。- 一度だけ表示。 生のキーは作成時にのみ返されます。そのとき控えてください。あとから取得はできません。
- 保存時は SHA-256 ハッシュ。 保存されるのはキーの SHA-256 ハッシュだけです。データベースは生の値を 決して保持しないため、データベースのダンプから使える認証情報が漏れることはありません。
- タイミング安全な比較。 検証は提示されたトークンをハッシュ化し、ハッシュどうしを定数時間で比較します。 そのため、先頭が何文字一致しても、不一致にかかる時間は同じです。
- ローテーション、失効、有効期限。 キーは失効させたり、任意の有効期限を与えたりできます。失効した キーや期限切れのキーは検証に失敗します。ローテーションは、置き換えのキーを作り、古いものを失効させて 行います。権限はキーではなくエージェントに設定されているため、キーをローテーションしてもエージェントの 権限は保たれます。権限を変えるにはエージェントを編集します。
キーの作成、編集、ローテーション、失効は API 呼び出しではなく 設定 画面で行います。認証情報の作成 手順はエージェントのアクセスを準備する、編集と失効は エージェントと API キーを管理する、キーをエージェントに組み込む方法は エージェントランタイムを接続するをご覧ください。
その他の認証方式
Section titled “その他の認証方式”以下は人間のユーザーとプラットフォーム管理者向けです。ここでは要点をまとめます。設定は運用ガイドが扱います。
OIDC(ユーザー)
Section titled “OIDC(ユーザー)”人間のユーザー向けのエンタープライズ SSO で、スーパー管理者がワークスペースごとに設定します(issuer、client ID、
有効化トグル)。サインインは PKCE 付きの認可コードフローを使い、client secret は不要です。プロバイダーが
リダイレクトで戻したあと、Chorus は (companyUuid, oidcSub) でユーザーを検索または作成し、HTTP-only の
Cookie を設定します。
| Cookie | 用途 |
|---|---|
oidc_access_token | API 呼び出し用のアクセストークン(約 1 時間) |
oidc_refresh_token | サイレント更新用のリフレッシュトークン(約 30 日) |
oidc_client_id | トークン更新時に使う client ID |
oidc_issuer | JWKS 発見に使う issuer |
アクセストークンはプロバイダーの JWKS(キャッシュ済み)に照らして検証され、edge middleware はリクエストが アプリに届く前に、期限切れ間近のアクセストークンを透過的に更新します。
Default Auth(開発用)
Section titled “Default Auth(開発用)”OIDC のない開発・デモ向けの、単一のメール/パスワードによるサインインです。DEFAULT_USER と DEFAULT_PASSWORD
の両方が設定されているときにのみ有効になります。
DEFAULT_USER="dev@example.local"DEFAULT_PASSWORD="change-me"サインイン時、Chorus はワークスペースとユーザーを自動プロビジョニングし、長寿命の自己署名 JWT を一つ、user_session
Cookie に発行します。更新フローはなく、期限が切れたらユーザーが再度サインインします。本番では Default Auth を
有効にしないでください。
スーパー管理者
Section titled “スーパー管理者”すべてのワークスペースにまたがるプラットフォームレベルの管理(ワークスペースの管理、ワークスペースごとの OIDC 設定)です。環境変数に、 メールと bcrypt のパスワードハッシュを設定します。
SUPER_ADMIN_EMAIL="admin@example.com"SUPER_ADMIN_PASSWORD_HASH="$2b$10$…" # bcrypt ハッシュサインインに成功すると admin_session Cookie が設定されます。スーパー管理者コンテキストは companyUuid
を持たないため、ワークスペースによる範囲の制限を受けません。テナントをまたいで読める唯一のコンテキストです。
エージェントの認可は権限ビットの集合です。エージェントが持つ有効セットが、あらゆる層で、それに何が できるかを決めます。
5 × 3 のマトリクス
Section titled “5 × 3 のマトリクス”権限は {resource}:{action} と書きます。五つの資源に三つの動作を掛けて、15 個の可能なビットになります。
read | write | admin | |
|---|---|---|---|
idea | 着想を閲覧 | 着想の作成 / 担当 / 解除 / 更新;要件詳細化の実行 | 着想のクローズ / 削除 |
proposal | 提案とドラフトを閲覧 | 作成 / 提出 / 却下 / 撤回;ドラフトの管理;課題の一括作成;課題 DAG の管理;課題の割り当て | 提案の承認 / クローズ |
document | 文書を閲覧 | 文書の作成 / 更新 | 文書の削除 |
task | 課題を閲覧 | 担当 / 解除 / 提出 / 報告;受け入れ基準の自己確認 | 課題の検証 / 再オープン / クローズ / 削除;受け入れ基準のマーク |
project | プロジェクトとグループを閲覧 | プロジェクトとグループの作成 / 更新 / 削除;プロジェクトの移動 | 予約済み(admin_agent に含まれるが、現時点でこれを必要とする操作はない) |
各動作は通常まとめて付与されますが、どの動作も他の動作を含意しません。task:admin を付与しても
task:read や task:write は含まれないため、各ビットを明示的に付与します。
ロールプリセット
Section titled “ロールプリセット”三つの名前付きプリセットは、15 個のビットの固定された部分集合に展開されます。プリセットは近道であって、 独立した認可のしくみではありません。
| プリセット | 個数 | 展開される権限 |
|---|---|---|
developer_agent | 6 | *:read + task:write |
pm_agent | 10 | *:read + idea:write + proposal:write + document:write + task:write + project:write |
admin_agent | 15 | すべてのビット(*:read + *:write + *:admin) |
展開すると、各プリセットは次のようになります。
developer_agent (6): idea:read proposal:read document:read project:read task:read task:write
pm_agent (10): idea:read idea:write proposal:read proposal:write document:read document:write task:read task:write project:read project:write
admin_agent (15): idea:read idea:write idea:admin proposal:read proposal:write proposal:admin document:read document:write document:admin task:read task:write task:admin project:read project:write project:adminカスタム権限と有効な権限セット
Section titled “カスタム権限と有効な権限セット”プリセットに加えて、エージェントはカスタムの権限ビットを持てます。有効セットは、展開されたプリセットと カスタムビットの和集合です。
effective = expand(preset) ∪ custom順序は関係ありません。純粋な集合の和です。よくある形は次のとおりです。
- 読み取り専用の監査者 — プリセットなし、カスタムは
*:readのみ:すべてを閲覧できるが、何も変更できない。 - 自己検証する開発者 —
developer_agent+task:admin:管理者を待たずに課題を検証できる。 - 承認権を持つ PM —
pm_agent+proposal:admin:提案を直接承認できる。
有効セットがどうアクセスを制御するか
Section titled “有効セットがどうアクセスを制御するか”同じ有効セットが、次の二つの経路でアクセスを決定します。
- MCP ツールの可視性。 権限で制限される各 MCP ツールは、必要な権限をちょうど一つ宣言します。接続時、
ツールの必要な権限が有効セットに含まれる場合にのみ、そのツールはエージェントのサーバーに登録されます。
そうでなければ、そのツールは単にエージェントのツール一覧に現れません。共通ツール(discover / read /
list / search / comment / session、そして
chorus_create_tasks/chorus_update_task)は制限されず、 すべてのエージェントに現れます。 - REST のアクセス制御。 権限で制限される各 REST ルートは、呼び出し元のエージェントが
特定の
{resource}:{action}ビットを一つ持っているかを検査します。そのビットを欠くエージェントは403 Missing permissionを受け取ります。人間のユーザーはこのエージェント権限検査の対象ではなく (人間のアクセスはセッションを通じて検査されます)、スーパー管理者はすべての権限検査を素通りします。