角色與權限
Sandbox 的權限是一條階梯,不是「凡是變更都要 company manager」。誰能寫環境、誰能建任務、誰能啟用房間、誰能看到別人的 run,分別看 owner scope、consumer scope 與 聊天室管理員階梯。目錄任務只有部門或公司擁有 — 分享/啟用/選單的切分見 任務受眾。一般使用者的執行路徑見 一般使用者執行任務。
Root / 營運操作不在本頁,見 營運與 Root。
角色整數
門檻來自環境變數,不要在前端自己重算:
| 變數 | 預設 | 意義 |
|---|---|---|
CAN_MANAGE_DEPARTMENT | 2 | role ≥ 2 → 部門管理員 |
CAN_MANAGE_COMPANY | 3 | role ≥ 3 → 公司管理員(租戶管理員 / tenant manager) |
role < 2 且只是聊天室成員,就是一般租戶使用者。角色整數不是聊天室管理員:聊天室管理員是另一條階梯。
聊天室管理員階梯
is_chatroom_manager_for_principal 成立,當呼叫者是使用者(非受限 key),且符合以下任一:
- 直接管理員:該室的
creator,或在chatroom_manager_association裡。 - 同部門的部門管理員:
role ≥ 2且department_id等於該室的部門。 - 公司管理員:
role ≥ 3,全公司的室都算。
受限 Sandbox API key 與外部 social client 永遠不算聊天室管理員。
Quick-run、綁定的建立/接受/撤銷、對「聊天室」consumer 寫 secret,都走這條階梯,不是「只要 role ≥ 2」。部門管理員不能對別的部門的室硬綁 Agent;除非他們也符合該室的階梯。
受限 Sandbox API key
Sandbox scope 的 API key 比一般使用者更窄。它只允許:允許清單內聊天室的 menu、手動提交、查自己的 run(list / status / content / artifacts / download)、取消自己的 run。
受限金鑰不能用的管理面:quick-run、retry、environments(含 context 上傳)、tasks(含公司執行歷史)、granted-jobs、bindings、secrets、settings、root。要用這些,需要使用者 JWT 或 Full scope key(Full 仍受租戶/角色限制)。
受限金鑰打 quick-run、/root、/environments、/tasks,或路徑缺聊天室段/聊天室不在允許清單時,認證層回 403(bindings、secrets、settings 這類沒有聊天室段的路由都落在這條);帶聊天室段但不在 Sandbox 允許清單上的其他路由(granted-jobs、retry、public-link…)則由 is_valid_api 回 405 Access to <METHOD> <path> is not allowed for your role。Sandbox router 若收到受限 principal 會 404。見 認證。受限金鑰欄列出實際 auth/route 閘門;可用路徑上的未授權資源仍可能回 404。
404 與 403 例外
未授權的識別碼通常回 404(隱藏存在性)。所以 404 常常是「沒權限」而不是「不存在」。
例外(不要寫「未授權一律 404」):
- 建立呼叫者不能擁有的 department/company 任務 → 403
owner_scope_forbidden。 POST /tasks送owner_scope=chatroom→ 422(enumSandboxTaskCreateOwnerScope)。GET/PUT /settings走共用的COMPANY_MANAGER角色依賴:role < 3→ 403Insufficient permissions.(不是 404)。- 錯誤碼對照表裡的 writeback/預算 403。
取消與讀取同一條邊界(can_cancel_run == can_read_run):管理員可以取消他們看得到的 run,不只是「自己的」。Agent 工具不用這條放寬(A-011):sandbox_cancel_job/sandbox_job_status/sandbox_submitted_jobs 即使使用者是管理員,仍綁行為主體。
can_execute_manually(POST /runs + trigger 存檔/觸發)是:同公司 +(受限 key 允許該房)+ 呼叫者是該房成員(或在該房管理員階梯上)+ 仍有活著的適用 share(歷史上的擁有方聊天室任務仍算)。這道閘不要求啟用。外部社群 client 必須釘在那個精確的 chatroom_id。不是成員、也不在該房階梯上的部門管理員,不能在那裡執行。
GET /chatrooms/{id}/menu 與 Agent 目錄更嚴:已授予 且 房間已啟用,每個呼叫者看到同一份清單。見 任務受眾。
沒有根層 GET /bindings;除 GET /chatrooms/{id}/granted-jobs 外,也可用 task/room scoped binding 歷史,請見管理查詢。一般使用者用 menu。
權限矩陣
| 動作 | 一般租戶使用者(聊天室成員,role < 2) | 聊天室管理員 | 部門管理員(role ≥ 2) | 公司管理員(role ≥ 3) | 受限 Sandbox API key |
|---|---|---|---|---|---|
| 建立 / 更新 / 歸檔環境 | 否(404) | 除非另具 owner-scope 管理權 | 自己部門擁有的環境 | 全部公司/部門擁有環境 | 403 at auth |
GET/PUT /settings | 否(403) | 否(403) | 否(403) | 是 | 403 at auth |
| 列出 / 讀取環境、版本、建置 | 是(自家公司 + system_curated) | 是 | 是 | 是 | 403 at auth |
| 建立公司擁有任務 | 否 | 否 | 否 | 是 | 403 at auth |
| 建立部門擁有任務 | 否 | 否 | 僅自己的部門 | 是 | 403 at auth |
| 建立聊天室擁有的目錄任務 | 422(已移除) | 422 | 422 | 422 | 403 at auth |
| 管理 / 發布 / 歸檔任務、分享 | 僅 can_manage_task_owner_scope | 僅歷史上的聊天室擁有任務,且他們管理該室 | 自己部門擁有的任務;公司管理員可全部 | 公司擁有 + 全部 | 403 at auth |
| 列出 / 啟用 / 停用 granted-jobs | 否 | 該室 | 若符合該室管理員階梯 | 是(經階梯) | 405 on an allowed room |
| 建立 / 接受 / 撤銷綁定(與啟用同一釘選) | 否 | 目標聊天室管理員階梯 | 若符合該室管理員階梯 | 是(經階梯) | 403 at auth |
Company manager 每任務歷史 GET /tasks/{id}/runs | 否 | 否 | 否 | 是 | 403 at auth |
| Secret 寫入 / 輪替 / 撤銷 + 核准 | 否 | 自己管理的 consumer 聊天室 | 自己管理的 consumer 部門 | consumer 公司 | 403 at auth |
GET /chatrooms/{id}/menu | 已授予 且 已啟用(每個呼叫者同一份清單) | 同左 | 同左 | 同左 | 是(允許的聊天室) |
POST runs | 成員資格 + 適用的分享(不要求啟用) | 若可執行 | 同左 | 同左 | 是(允許的聊天室) |
| 列出 / 讀取 run、content、artifacts、download、cancel | 僅自己的 run | 逐筆路由(status/content/artifacts/download/cancel)可及自己直接管理的室裡所有 run;GET /chatrooms/{id}/runs 列表只對 role ≥ 2 放寬,role < 2 的直接管理員仍只列到自己提交的 run | 自己部門聊天室的 run | 公司所有聊天室 run | 僅自己的 run、允許的聊天室 |
| retry | 若 can_execute_manually | 是 | 是 | 是 | 允許房間 405;router 404 |
| quick-run | 否(404) | 是(該室) | 若符合該室管理員階梯 | 是 | 403 at auth |
GET /tasks 列表 | 只看 live grant 受眾 | 可管理任務或適用受眾 | 自己部門任務或適用受眾 | 公司全部任務 | 403 at auth |
| 借用者視圖 | startup_script / work_script / work_command / ordinary_env / secret_slot_declarations / output_policy 皆為 null(output_policy 內含擁有方的 table id,或 Command 與聊天室的 id),content_hash 為空字串;secret_slot_names 仍會回傳。source_digest / source_ref 是 environment version 借用者視圖才拿掉的欄位,不在 task version 上 | 若管理 owner scope 則為擁有者視圖 | 同左 | 同左 | 不適用 |
管理任務(發布、歸檔、分享)走 can_manage_task_owner_scope:歷史上的聊天室擁有 → 該室管理員階梯;部門擁有 → 該部門的部門管理員(公司管理員可全部);公司擁有 → 只有公司管理員。新的目錄建立不能是聊天室擁有。
Secret 的寫入與核准走 consumer-scope manager,不是任務擁有方:聊天室 consumer → 該室階梯;部門 consumer → 該部門管理員;公司 consumer → 公司管理員。任務擁有方不能代替借用方核准 secret。
A-010:分享任務的擁有方看不到借用方的 run
共用任務的 OWNER 不會自動看到借用方聊天室的 run。房間定址的 run API 仍只看:自己提交的、自己直接管理的室(僅逐筆路由;GET /chatrooms/{id}/runs 列表只對 role ≥ 2 放寬)、自己部門的室、或公司管理員看全公司。擁有任務 ≠ 看到別人在別的室跑它。
例外: company manager 可以用 GET /tasks/{task_id}/runs(+ /numOfData)列出一個目錄任務的每一次執行,不必逐房走訪。那不是房間 run 清單;任務擁有者除非同時是 company manager,否則也拿不到。
接下來做什麼
- 一般使用者執行任務:menu → 提交 → 輪詢 → 產出物(不要建環境或任務)。
- 建立環境並建置:環境寫入依公司/部門 owner scope 判斷;
GET/PUT /settings同樣只要公司管理員(保留天數見 保留期)。 - 任務受眾:部門/公司擁有、分享 vs 啟用 vs 選單。
- 任務、分享與啟用:HTTP 步驟。
- Secret 與授權:consumer-scope manager 才能寫值與核准。
- 營運與 Root:root 不在本頁。
- Agent toolkit:在房間啟用
ChatroomJobType.sandbox;工具仍綁行為主體。 - 自訂表格 trigger:觸發時的 principal 仍必須
can_execute_manually(Command 輸出的版本則改為要求 trigger 的撰寫者)。