遠端業務系統接入平臺時,容易出問題的往往不是接口調用本身,而是“誰持有憑據、憑據多久失效、成員被撤銷後多久生效”。這三件事決定了系統能不能長期穩定運行。下面是我們在這條鏈路上守住的做法和邊界。
憑據分兩級,長期那一級不出服務端
平臺側有兩類身份。模塊服務身份是長期憑據,只在業務系統服務端持有,用來交換 Launch Grant(POST /integration/v1/sso/launch-grants/exchange)和申請實例服務 Token(POST /integration/v1/service-tokens);實例服務 Token 則是最長五分鐘、Audience 固定、Scope 已按本次請求收窄的短期憑據,響應帶 no-store。
因此瀏覽器永遠拿不到模塊憑據:前端只把用戶帶來的 Launch Code 交給自己的後端,其餘交換都在服務端完成。SDK 對短期 Token 的處理是按“實例 + 本次請求的 Scope 集合”緩存,最長 300 秒、沒有 Refresh,剩餘壽命不足安全窗口時重新申請,併發調用只觸發一次,且不跨實例複用。
Launch 是一次性交換,換來的是本地會話
用戶從平臺進入業務系統時,帶的是 Launch Code,不是長期憑據。後端用模塊服務身份交換並消費 Grant,隨後建立業務系統自己的本地會話;會話裡只放派生身份,不放平臺 Token、Launch Code、Client Secret 或完整 Claims。
交換與會話校驗都要驗籤:用平臺運行時 JWKS 校驗簽名算法、Issuer、Audience、有效期、token_use、Account 與 AppInstance 以及 Scope,公鑰來源禁止重定向並限制響應體大小。這裡有一個容易混淆的地方:登錄說明頁上的“聯機正常”只證明後端能解析平臺公鑰,不代表用戶已登錄,也不代表 Launch 鏈路可用——三件事要分開描述。
成員被撤銷後,本地會話要能收斂
平臺會話有效,不等於本地會話可以一直用下去。長期會話期間,成員被移出實例、角色發生變化或實例被停用,都應在有限時間內反映到業務系統。做法是用實例服務身份批量校驗(POST /integration/v1/session-checks):active 為真要求實例、實例成員、Account 與 Account 成員同時有效;非成員與不存在的用戶同樣返回 active=false,不洩漏成員是否存在。業務系統按自己聲明的校驗窗口收斂,實踐中寫請求的窗口可以比讀請求更短。
Scope 不夠就在本地失敗,不要發出請求
每個運行時請求都帶 Scope。SDK 只在平臺實際授予的 Scope 覆蓋本次請求時才返回可用憑據,否則在本地失敗,不發業務請求。這條規則的意義在於把“平臺沒授權”和“平臺調用失敗”分開:前者是配置問題,應當立刻可見,而不是變成一串難以定位的上游錯誤。
冪等與重試歸調用方
SDK 不自動重試任何請求。寫操作必須由調用方提供穩定的冪等鍵,請求失敗也不重發——因為“結果未知”和“失敗”是兩種狀態,只有業務系統自己知道該補發、查詢還是提示用戶。錯誤方面,平臺的 Problem Details 會映射到穩定的錯誤類別(未認證、無權限、衝突、限流、服務端錯誤等)並標註是否可重試;憑據與響應正文不會進入日誌或錯誤序列化。
兩份製品,兩條獲取路徑
兩組 SDK 的可獲取性不同,接入前先確認自己屬於哪一類。TypeScript / Node 側是公共 npm 上的 @td-runlume/platform-integration-sdk,Apache-2.0,用於服務端調用。Java 側座標是 app.runlume.platform:platform-integration-sdk-java,由平臺的 Nexus 製品庫提供、不在 Maven Central,且只能憑平臺授予的憑據與許可使用,不要重新分發製品;Java 側通常配合 Spring Boot Starter 使用,SDK 組件與本地會話有效性管線由 Starter 裝配,業務系統只提供會話邊界與工作區讀取兩個擴展點。
接口路徑、Scope 名稱與可用能力以簽約時的契約和平臺文檔為準。本文只說明接入時服務端要守住的邊界;平臺提供的能力範圍可以從平臺能力開始瞭解。