SPIFFE 是 CNCF 用於向工作負載簽發身分的標準。SPIRE 是其開源參考實作,另有數個商業產品也會簽發符合 SPIFFE 規範的身分。Anthropic 可與任何發出 OIDC 相容 JWT-SVID 的 SPIFFE 實作進行聯合。如需目前的實作清單,請參閱 SPIFFE 專案網站上的 Commercial software that implements SPIFFE。
聯合可透過位於公開 HTTPS URL 的 OIDC 探索文件(discovery 模式,受 URL 限制約束)運作,或直接註冊 JWKS(inline 模式)。
JWT-SVID 規範將 sub 定義為工作負載的 SPIFFE ID,而 SPIFFE Workload API 要求呼叫者在擷取時提供 aud,因此這些宣告(claim)在各實作之間是相同的。Anthropic 另外要求 iss 和 iat,這兩者都不是 JWT-SVID 規範所強制要求的,因此請設定您的實作以填入這兩者(在 SPIRE 中,iss 是 jwt_issuer 伺服器設定,而 iat 會自動設定)。具備這些之後,本指南的設定 Anthropic、取得並使用權杖和限定規則範圍章節適用於任何 SPIFFE 實作。
SPIFFE 為每個工作負載指派一個形式為 spiffe://<trust-domain>/<path> 的穩定身分 URI,而 SPIRE 會透過 Workload API 依需求將該身分簽發為 JWT-SVID。JWT-SVID 是一個普通的已簽署 JWT,其 sub 宣告是工作負載的 SPIFFE ID,而其 aud 宣告由工作負載在擷取時提供。
從 SPIRE 信任網域到標準 OIDC 的橋樑是 SPIRE OIDC Discovery Provider,這是一個獨立的輔助程式,會為信任網域的 JWT 簽署金鑰發布 /.well-known/openid-configuration 和 JWKS 端點。在探索提供者運行的情況下,JWT-SVID 的驗證方式與任何其他 OIDC 權杖相同:將探索 URL 註冊為聯合簽發者,撰寫一個比對工作負載 SPIFFE ID 的聯合規則,並讓工作負載將其 JWT-SVID 提交至 Anthropic 的權杖交換端點。
本頁的範例使用 SPIRE,並適用於 SPIRE Agent 運行的任何地方:Kubernetes pod、虛擬機器和裸機主機。
如果您的 Kubernetes 叢集未運行 SPIRE,而您想改用叢集原生的投射服務帳戶權杖進行驗證,請參閱搭配 Kubernetes 使用 WIF。
inline 註冊。iss 宣告設為您將註冊為聯合簽發者 issuer_url 的值。對於 discovery 模式,這是探索端點的公開 URL(在 SPIRE 中為 jwt_issuer 伺服器設定)。擷取 JWT-SVID 時要請求的 audience 值始終為 https://api.anthropic.com。請在 spiffe-helper 的 jwt_audience、Workload API 的 FetchJWTSVID 呼叫以及聯合規則的 audience 比對器中使用此值。
本節中的說明是 SPIRE 專屬的。如果您使用不同的 SPIFFE 簽發者,請根據其自身的文件設定其 OIDC 探索端點和 JWT-SVID 擷取,然後繼續至設定 Anthropic。
如果您已經運行帶有 OIDC Discovery Provider 的 SPIRE,與 Anthropic 聯合在 SPIRE 端需要三件事:與探索 URL 相符的 jwt_issuer、將呼叫 Claude API 的工作負載的註冊項目,以及讓該工作負載以 Anthropic audience 擷取 JWT-SVID 的方式。以下小節將逐一說明。設定片段僅顯示與 Anthropic 聯合相關的設定,而非完整的 SPIRE 部署設定。
第一次設定 SPIRE?請依照 SPIRE 快速入門部署 SPIRE Server 和 Agent,然後將 OIDC Discovery Provider 作為獨立服務與 SPIRE Server 一起新增。探索模式聯合取決於該提供者已部署且可公開存取。該提供者不是預設 SPIRE 安裝的一部分。
Anthropic 透過將 JWT-SVID 的 iss 宣告與已註冊的聯合簽發者進行比對,並從該簽發者的探索文件擷取 JWKS 來驗證 JWT-SVID。兩個 SPIRE 設定必須使用相同的 URL:SPIRE Server 的 jwt_issuer(它會成為每個鑄造的 JWT-SVID 中的 iss 宣告)和 OIDC Discovery Provider 的 domains 清單(它決定探索文件和 JWKS 的服務主機)。該共用 URL 就是您向 Anthropic 註冊的內容。
信任網域和簽發者 URL 是獨立的。信任網域(spiffe://prod.example.com)限定 sub 宣告的範圍。簽發者 URL(https://oidc-discovery.prod.example.com)是 Anthropic 擷取簽署金鑰的位置。它們不需要共用主機名稱。
確認 SPIRE Server 的設定中已設定 jwt_issuer 並指向探索提供者的公開 URL。以下範例也顯示了預設的 JWT-SVID 存留期。SPIRE 的內建預設值為 5 分鐘,這足夠短,因此需要持續輪換(請參閱運行 spiffe-helper)。Anthropic 的權杖交換端點會拒絕任何存留期超過聯合簽發者設定的最大值的身分權杖,預設為 1 小時(請參閱驗證規則)。此檢查適用於每個 SPIFFE 實作,而不僅僅是 SPIRE,因此請將 default_jwt_svid_ttl(或任何個別項目的覆寫值)保持在該最大值或以下。
server {
trust_domain = "prod.example.com"
jwt_issuer = "https://oidc-discovery.prod.example.com"
default_jwt_svid_ttl = "5m"
# ...
}在 OIDC Discovery Provider 的設定中,相同的主機名稱必須出現在 domains 下,且該提供者必須能夠連線到 SPIRE Server 的 API socket。該提供者透過 HTTPS 提供探索文件和 JWKS。使用其內建的 ACME 支援終止 TLS,或在其前方放置一個執行此操作的負載平衡器。
domains = ["oidc-discovery.prod.example.com"]
server_api {
address = "unix:///run/spire/sockets/private/api.sock"
}
acme {
email = "[email protected]"
tos_accepted = true
}此範例使用 server_api,它將探索提供者連接到 SPIRE Server 的特權 API socket。該提供者也接受 workload_api 區塊(帶有 socket_path 和 trust_domain),改為透過 SPIRE Agent 的 Workload API 取得套件(bundle)。當探索提供者不應存取 Server API 或運行在無法連線到 Server 的節點上時,請使用它。
每個呼叫 Claude API 的工作負載都需要一個 SPIRE 註冊項目,將其執行階段選擇器(selector)對應到 SPIFFE ID。如果工作負載已經註冊,請記下其 SPIFFE ID,您會在聯合規則的 subject_prefix 中使用它。如果尚未註冊,請進行註冊。對於 Kubernetes pod,選擇器通常是命名空間和 Kubernetes 服務帳戶:
# 將 NODE_UID 替換為節點的 UID:
# kubectl get node <node-name> -o jsonpath='{.metadata.uid}'
spire-server entry create \
-spiffeID spiffe://prod.example.com/ns/inference/sa/worker \
-parentID spiffe://prod.example.com/spire/agent/k8s_psat/prod-cluster/NODE_UID \
-selector k8s:ns:inference \
-selector k8s:sa:worker所示的 parentID 是單一節點自動產生的 agent ID。若要進行叢集範圍的註冊,請將項目的父項設為節點別名,使其比對每個節點上的工作負載,如同 SPIRE Kubernetes 快速入門所做的那樣。
Kubernetes 之外的工作負載使用主機層級的選擇器,例如 unix:uid:1000(unix:path 也可用,但需要在 agent 的 unix 工作負載認證器設定中設定 discover_workload_path = true)。運行 spire-controller-manager 的叢集可以使用 ClusterSPIFFEID 自訂資源宣告項目,而不是直接呼叫 spire-server entry create。
spiffe-helper 是一個 sidecar 工具程式,它連接到 SPIRE Agent socket,為指定的 audience 擷取 JWT-SVID,將其寫入檔案,並在到期前重新擷取。該輔助程式預設以常駐程式(daemon)模式運行。以下範例明確設定 daemon_mode = true。
agent_address = "/run/spire/sockets/agent.sock"
# The JWT-SVID file is written under cert_dir
cert_dir = "/var/run/secrets/anthropic.com"
daemon_mode = true
jwt_svids = [{
jwt_audience = "https://api.anthropic.com"
jwt_svid_file_name = "token"
}]在 Kubernetes 中,將 spiffe-helper 作為 sidecar 容器運行,與您的應用程式容器共用一個以記憶體為後端的 emptyDir 磁碟區(medium: Memory),這樣持有者 SVID 就永遠不會落在節點的磁碟上。將 SPIRE Agent socket 從主機掛載到 sidecar 中,在兩個容器中將共用磁碟區掛載到 /var/run/secrets/anthropic.com,並在應用程式容器上設定 ANTHROPIC_IDENTITY_TOKEN_FILE=/var/run/secrets/anthropic.com/token。在虛擬機器和裸機上,將 spiffe-helper 作為系統服務與工作負載一起運行,並將兩者指向一個共用目錄。
在 Claude Console 中,開啟 Settings → Workload identity,點擊 Connect workload,然後選擇 Custom OIDC。精靈會引導您完成註冊簽發者、建立服務帳戶和建立聯合規則。
精靈會為您建立這些資源。無論您是在精靈中輸入這些值,還是將其傳送至 Admin API,請使用以下值:
**聯合簽發者:**以 discovery 模式註冊 OIDC Discovery Provider 的公開 URL。Anthropic 會從此 URL 擷取 /.well-known/openid-configuration,並依照回傳的 jwks_uri 擷取信任網域的簽署金鑰。
{
"name": "spire-prod",
"issuer_url": "https://oidc-discovery.prod.example.com",
"jwks": { "type": "discovery" }
}如果探索提供者無法從公開網際網路存取,請自行擷取 JWKS(curl https://oidc-discovery.prod.example.com/keys),並使用回傳的 keys 陣列內容以 "jwks": {"type": "inline", "keys": [...]} 註冊簽發者。在 inline 模式下,issuer_url 僅用於與 JWT-SVID 的 iss 宣告進行比較。Anthropic 永遠不會嘗試連線到它。
SPIRE 會頻繁輪換 JWT 簽署金鑰,預設與 CA 相同的週期(ca_ttl,24 小時)。如果您使用內嵌 JWKS 而非探索 URL 註冊簽發者,則每次 SPIRE 輪換時都必須更新 JWKS:在工作負載開始提交新金鑰之前新增它,並在以被取代金鑰簽署的權杖過期後移除被取代的金鑰。留在內嵌 JWKS 中的過時金鑰會無限期地保持受信任狀態。
若要在不公開探索端點的情況下自動更新 JWKS,請設定 SPIRE Server 的 BundlePublisher 外掛程式(aws_s3、gcp_cloudstorage 或 k8s_configmap),並設定 format = "jwks",以便在每次輪換時將 JWT 簽署金鑰推送到外部儲存空間,然後透過 Admin API 更新簽發者的內嵌金鑰。
**聯合規則:**比對 JWT-SVID 的 sub(SPIFFE ID)和您設定 spiffe-helper 請求的 aud。SPIFFE ID 是 URI 字串,而 subject_prefix 將它們作為不透明文字進行比對,因此精確值或尾端 * 的前綴比對都適用於它們。對於更複雜的模式,請使用 CEL condition。
{
"name": "spire-inference-worker",
"issuer_id": "fdis_...",
"match": {
"subject_prefix": "spiffe://prod.example.com/ns/inference/sa/worker",
"audience": "https://api.anthropic.com"
},
"target": {
"type": "service_account",
"service_account_id": "svac_..."
},
"workspace_id": "wrkspc_...",
"oauth_scope": "workspace:developer",
"token_lifetime_seconds": 600
}token_lifetime_seconds 是交換回傳的 Anthropic 存取權杖的存留期,而不是 JWT-SVID 的存留期。SDK 會自動重新整理存取權杖。
請盡可能依工作負載允許的程度具體指定。只有當在該路徑下註冊的每個工作負載都應對應到同一個 Anthropic 服務帳戶時,才將 subject_prefix 放寬為 spiffe://prod.example.com/ns/inference/*。將規則的 fdrl_... ID 新增到工作負載的 ANTHROPIC_FEDERATION_RULE_ID 環境變數中。
Anthropic SDK 可以從 spiffe-helper 維護的檔案讀取 JWT-SVID,或透過權杖提供者可呼叫物件(callable)直接呼叫 SPIFFE Workload API。檔案路徑是最簡單的整合方式,適用於每種 SDK 語言。可呼叫物件路徑可移除 sidecar,但需要您的應用程式語言中有 SPIFFE Workload API 用戶端。
在 spiffe-helper 將新的 JWT-SVID 寫入 /var/run/secrets/anthropic.com/token 的情況下,將 ANTHROPIC_IDENTITY_TOKEN_FILE 設為該路徑,並一併設定 ANTHROPIC_FEDERATION_RULE_ID、ANTHROPIC_ORGANIZATION_ID、ANTHROPIC_SERVICE_ACCOUNT_ID 和 ANTHROPIC_WORKSPACE_ID。SDK 在每次權杖交換時都會讀取該檔案,因此它始終會取得最近輪換的 SVID,並在 Anthropic 存取權杖過期前自動重新整理。請參閱環境變數以了解每個值的來源。
import anthropic
# 讀取 spiffe-helper 寫入至
# ANTHROPIC_IDENTITY_TOKEN_FILE 的 JWT-SVID,以及 ANTHROPIC_FEDERATION_RULE_ID、
# ANTHROPIC_ORGANIZATION_ID、ANTHROPIC_SERVICE_ACCOUNT_ID 和 ANTHROPIC_WORKSPACE_ID。
client = anthropic.Anthropic()
message = client.messages.create(
model="claude-opus-5",
max_tokens=1024,
messages=[{"role": "user", "content": "Hello, Claude"}],
)
print(next(block.text for block in message.content if block.type == "text"))在接入 SDK 之前,請直接從 SPIRE Agent 擷取 JWT-SVID,並確認宣告與您的聯合規則所預期的相符。如果您使用不同的 SPIFFE 實作,請使用其 CLI 或 Workload API 用戶端擷取 JWT-SVID,並以相同的方式解碼酬載(payload)。
Workload API 會認證呼叫的程序。對於 Kubernetes 註冊項目,請在滿足該項目選擇器且已掛載 agent socket 的 pod 內運行此命令(例如,使用 kubectl exec)。在虛擬機器和裸機上,請以符合該項目 unix: 選擇器的使用者或程序身分運行它。從未經認證的主機 shell 運行會回傳 no identity issued,這是最常見的驗證步驟失敗原因。
spire-agent api fetch jwt \
-audience https://api.anthropic.com \
-socketPath /run/spire/sockets/agent.sock \
-output json \
| jq -r '.[0].svids[0].svid' \
| jq -rR 'split(".")[1] | gsub("-";"+") | gsub("_";"/") | @base64d | fromjson'-output json 旗標會將 SVID 回應和套件回應作為雙元素 JSON 陣列回傳,因此 jq -r '.[0].svids[0].svid' 可擷取純權杖。在沒有 -output 的較舊 SPIRE 版本上,該命令會改為列印帶標籤的區塊。在這種情況下,請將預設輸出透過管線傳遞給 awk '/^[[:space:]]*eyJ/{print $1; exit}' 以擷取權杖行。檢查 iss 是否為您註冊的 OIDC Discovery Provider URL、sub 是否為工作負載的 SPIFFE ID,以及 aud 是否包含 https://api.anthropic.com。然後運行取得並使用權杖中的 cURL 範例。成功的交換會回傳以 sk-ant-oat01- 開頭的 access_token。若出現 400 invalid_grant,請參閱疑難排解失敗的交換。SPIRE 端最常見的原因是 SPIRE Server 的 jwt_issuer 與註冊為聯合簽發者的 URL 不相符。
SPIFFE ID 路徑慣例由操作者定義,因此聯合規則的 subject_prefix 比對器應反映您的註冊項目使用的路徑方案。常見的方案包括 spiffe://<trust-domain>/ns/<namespace>/sa/<service-account>(spire-controller-manager 中 ClusterSPIFFEID 資源發出的預設值)以及用於虛擬機器和裸機工作負載的 spiffe://<trust-domain>/host/<hostname>/<service>。
subject_prefix 為 spiffe://prod.example.com/* 會比對信任網域中的每個工作負載。如果沒有 audience 比對器,該規則也會接受為任何 audience 鑄造的 JWT-SVID,包括工作負載為不相關的信賴方(relying party)請求的那些。
將規則的 match 區塊鎖定在符合您使用案例的最窄範圍:
subject_prefix 設為完整的 SPIFFE ID,不帶尾端 *。audience,並以相同的值設定 spiffe-helper(或 Workload API 呼叫),以便拒絕為其他信賴方鑄造的 SVID。spiffe://prod.example.com/ns/inference/* 授予在某個命名空間下註冊的每個工作負載,並為每個命名空間建立獨立的規則和 Anthropic 服務帳戶,而不是擴大單一規則。使用 Workload Identity Federation 將 Okta 服務應用程式身分聯合至 Claude API。
使用來自您自己的身分提供者的短期身分權杖(而非長期靜態 API 金鑰)將工作負載驗證至 Claude API。
Workload Identity Federation 的環境變數、驗證規則、設定檔組態和錯誤參考。
使用投射服務帳戶權杖從自行管理的 Kubernetes 叢集驗證至 Claude API。
Was this page helpful?