信任與隔離
信任政策由維運人員制定,套件清單不能自行宣告信任層級。發行外掛的可選 trust
路徑指定 JSON 政策檔,相對於應用設定檔解析,管理應用中的受管項目。
- 受管製品必須取得精確匹配的核准,才能透過 facade 接納呼叫。
- 不可信項目必須在沙箱子行程中執行;Worker 不是安全邊界。
- 主機憑證只由主機能力處理器使用。
使用套件名稱與擷取的 Artifact 摘要。將範例摘要換成實際值。第一方與第三方套件使用相同的指派與核准檢查。
{ "version": "1", "entries": [ { "entry": "forecasts", "artifact": { "package": "@example/forecasts", "digest": "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa" }, "tier": "untrusted", "contractEntry": "dist/index.js", "grants": [ { "_tag": "Http", "id": "weather", "origin": "https://weather.example", "credential": "WEATHER_KEY" }, { "_tag": "Files", "id": "data", "directory": "/srv/forecast-data" } ] } ]}| 欄位 | 含義 |
|---|---|
version |
維運政策版本;變更會使既有核准失效。 |
entry 與 artifact |
項目 id、套件名稱與目錄摘要。未知製品拒絕執行。 |
tier |
own、trusted 或 untrusted。都需要核准,只有 untrusted 強制使用作業系統隔離。 |
contractEntry |
不可信程式碼的契約匯出,必須打包在製品內。 |
grants |
具名主機能力;變更需要重新核准。檔案系統根目錄必須是絕對路徑。 |
在使用受管項目或投影前安裝政策。政策在一次執行期間不可變;修改後重新啟動。列出每個預定使用的製品身分,包括升級候選。主機程式碼、CLI 擴充、啟動器與主機契約模組屬於可信應用程式碼,不在外掛隔離範圍內。不要在這些位置匯入不可信套件。安裝政策後,普通 Remote 與 runner 部署會被拒絕。
@graftland/plugin-remote/Policy 負責級別、授權與撤銷規則。 Policy.install
回傳有作用域歸屬的政策服務。在建立受管項目的應用程式外使用
Effect.provideService(Policy.Service, authority),並保持安裝作用域存活。發行外掛會向子項目提供這個上下文。消費者宣告
inject: [Policy.Service];Policy.service
讀取注入的上下文,缺少服務時回傳可恢復的 PolicyError。一般外掛也可以透過
Graft.provide
發布它。受管驅動要求穩定的環境服務,因為替換線上圖提供者會繞過協調器。安裝准入權威後,缺少對應政策服務的執行會被拒絕。核心的
Trust.register、Trust.check 與 Trust.publish
為所有政策外掛提供原子准入和不透明值比較,不設獨立的服務目錄。政策持有已解碼維運資料的副本,並按結構比較。投影外掛驗證自己的帶標籤核准資料;這些資料描述外部視圖,不是契約結構或身分。每次分配的嘗試都有獨立的綁定租約,包括失敗或從未啟動的嘗試。所有擁有者退出後,服務鍵可重新使用。
以 cli: true 啟用兩個命令外掛:@graftland/plugin-release/cli 與
@graftland/plugin-release/approve-cli。從 approvals 回覆選取聲明,儲存為
statement.json,檢視後核准該檔案。控制 socket 僅限擁有者存取;who
是維運人員填寫的稽核標識,不是獨立的身分驗證系統。
graft release approvals --socket /app/control.sock --jsongraft approve statement.json --who operator@example --socket /app/control.sock --jsongraft release revoke weather --who operator@example --socket /app/control.sock --json| 核准範圍 | 比較方式 |
|---|---|
| 製品 | 套件名稱與擷取目錄摘要,包括目錄中實際包含的相依套件。 |
| 暴露的視圖 | 精確比較投影標籤、邏輯視圖名稱、服務/操作綁定和資料。MCP 包括名稱、標題、描述、四項提示與輸出處理;空白也參與比較。 |
| 授權 | 精確比較能力 id、目標位址、檔案系統根目錄與憑證參照名稱。 |
| 政策 | 精確比較版本與項目指派。 |
日誌先記錄核准者、時間與完整聲明,再啟用呼叫。過期聲明回傳
Unapproved。發布描述變更時,先更新核准聲明,再通知 MCP 用戶端。tools/list_changed
不是核准;快取舊清單的用戶端也會在接納呼叫時收到
Unapproved。程式碼位元組取得核准不表示行為是確定的,也不會固定已授權外部服務的行為。
已發布的呈現事實獨立於視圖的掛載狀態。撤下或重新掛載未變的視圖,不會改變核准陳述,也不會阻止無關的主機消費者。
每筆事實由投影標籤、穩定的邏輯視圖名稱及服務/操作識別。
Projection.offer("forecast-tools", bindings)
的名稱由投影作者或維運人員指定;不同伺服器視圖使用不同名稱。掛載 UUID 不是邏輯身分。在同一 Graft 執行時內,每個視圖只允許一個線上擁有者;重複宣告回傳
ProjectionConflict。
更新只取代該視圖的完整事實集。撤下與重新掛載後保留最新資料,修訂不會使陳述增長。還原已核准的資料時,只要陳述的其他部分仍相符且沒有撤銷阻擋,就恢復准入。更新一個視圖不會取代同一操作的另一個視圖。
發行外掛持有的政策先將修訂寫入發行稽核日誌,再改變准入或公開中繼資料。日誌重播恢復最新事實,包括未經核准的變更,不會把歷史修訂重新加入陳述。稽核寫入失敗會拒絕發布。嵌入式主機可提供
Policy.Audit 來保存持久歷史。 嵌入式復原需把最新發布快照傳給
Policy.install;只有核准記錄無法描述目前視圖。
撤銷授權或 env:NAME
參照時,先阻止新呼叫,再為每個相關單元等待最多五秒,確認終止及獨立觀察到的退出,最多並行回收四個單元。Policy.termination
為撤銷、後註冊的擁有者和政策關閉統一定義這些限額。啟動器準備階段直接傳播純取消,不記錄錯誤;混合清理原因會完整記錄。失敗會說明退出尚未確認,不會重新開放呼叫。撤銷記錄在重新啟動後保留,回復也檢查授權參照。恢復需要記錄在案的
--override-revocations,以及帶有該明確覆寫的匹配核准;兩者都不刪除撤銷記錄。重新啟動後的單元可憑已記錄的覆寫進行初始化。啟動會恢復最新稽核的呈現事實;發布不同的中繼資料會再次阻止呼叫。後續發行沿用撤銷記錄不會再次撤銷覆寫;新的明確撤銷會。
執行不可信程式碼
Section titled “執行不可信程式碼”發行外掛預設選擇 Linux bubblewrap 啟動器,可信主機也可以提供
Sandbox.Current。嵌入式主機可建立 Sandbox.linux,透過該參照傳入
Sandbox.Launcher。自訂啟動器屬於可信程式碼,必須提供等效隔離。缺少啟動器、不支援的平台或命名空間失敗都不會退回普通行程執行。
| Linux 邊界 | 範圍 |
|---|---|
| 命名空間 | 強制使用 user、mount、PID、IPC、UTS 與 network 命名空間;移除 capabilities,禁止再建立 user 命名空間。 |
| 可見檔案 | 唯讀製品、打包的可信子行程入口與 Node 執行庫;不掛載主機資料目錄。 |
| 環境 | 清空;受管 Worker 與普通子行程也不繼承主機環境。 |
| 網路 | 無外部網路介面;使用 HTTP 代理能力。 |
| 限額 | Node 堆積 128 MiB、檔案描述符 256 個、單檔 16 MiB、暫存檔案系統 16 MiB;不提供硬性總記憶體或 CPU 配額。 |
Linux 需要 bwrap、prlimit、ldd
與可用的非特權 user 命名空間。專案 CI 環境提供這些命令。設施不可用時,真實作業系統測試註明原因後略過;核准與模擬啟動器測試在所有平台執行。macOS 等不支援的平台拒絕不可信程式碼執行。Node 的
--permission 與限定讀取路徑僅用於縱深防禦:
Node 明確不將其視為安全邊界。
將實作、契約匯出與執行相依套件打包成製品內自包含的 JavaScript。外部執行相依套件不會被擷取或固定,也不會掛載到沙箱。首次建構不可信發行時,使用
build(..., { file, references, revocations, metadataOnly: true })。受政策管理的發行建構與計畫讀取已儲存的發布中繼資料,不在主機匯入不可信實作,重複建構同一發行也一樣。重用既有發行只驗證不可變位元組和已儲存的中繼資料。執行時就緒檢查仍比較單元自己的宣告。作者側發布與一致性工具只能用於可信程式碼,或放到另設的隔離環境執行。
在 Remote 契約的 inject 宣告 Capabilities.service,在實作外掛注入
Capabilities.Broker。受管 Remote 仍不支援其他主機服務注入。在發行的主機相容性中繼資料中包含代理服務及其套件來源。代理每次請求都重新檢查核准。新整合初始化時不要呼叫代理;註冊服務並暴露工具中繼資料後才能進行首次核准。需要能力的探針要求已有匹配核准。
| 能力 | 規則 |
|---|---|
http({ grant, url }) |
僅 GET;精確匹配已授權 origin,禁止 URL 憑證與重新導向。主機從具名環境參照添加 Authorization。 |
read({ grant, path }) |
唯讀根目錄內的 UTF-8 檔案;正規化路徑不能逃出根目錄。 |
| 限額 | 每次請求五秒;HTTP 回應與檔案大小最多一 MiB。 |
| 拒絕原因 | Unapproved、Revoked、DestinationDenied、FileDenied、ResponseLimit 或 Unavailable。 |
選擇可信的憑證目標,也要信任其回應。單元不會收到憑證設定或繼承的主機環境值。受政策管理的發行輸入拒絕解析
!env/$env;憑證參照名稱應放在授權中。不要把秘密字面值寫入輸入或套件檔案。
graft add
對所有套件停用相依套件生命週期腳本,包括不可信套件;恢復安裝也保持停用。安裝腳本執行時還沒有執行時沙箱。需要建構腳本的套件應先在獨立可信建構環境中建構,再擷取。CLI 擴充在主機執行,必須單獨信任。
該邊界針對惡意外掛套件讀取未授權檔案或秘密、繞過出口授權、使用過期描述呼叫,以及撤銷後繼續執行。不包含核心或沙箱逃逸、側通道、惡意主機或維運人員、Graft/Effect 供應鏈失陷、Windows,以及超出上述限額的阻斷服務防護。