跳至主要内容

多租戶隔離

在多租戶架構中,確保不同客戶(租戶)之間的数据和資源是完全隔離的非常重要。這意味著一個租戶的操作或數據不會影響到另一個租戶的運行或資料安全。WordPress 本身在設計上提供了基礎的多租戶能力,但要實現真正的、強大的隔離,我們需要依賴特定的插件或架構來處理用戶權限、數據分離和環境配置。

核心概念:什麼是多租戶隔離?

簡單來說,多租戶隔離就是「沙盒化」。每個租戶就像在一個獨立的房間裡運行,他們可以自由地使用自己的資源(如特定的設定、內容或功能),但不會看到或干擾到其他房間裡的內容。

主要涉及以下幾個層面:

  1. 數據分離 (Data Isolation):確保 A 租戶的資料永遠無法被 B 租戶讀取或修改。
  2. 環境隔離 (Environment Isolation):如果可能,為每個租戶提供獨立的設定、主題和外掛環境。
  3. 權限隔離 (Permission Isolation):嚴格控制用戶只能存取其自己租戶的資源。

如何實現多租戶隔離?

在 WordPress 生態系統中,實現多租戶隔離通常有幾種主要方法:

這是最常見且最推薦的方法。許多知名的 WooCommerce 或 WordPress 多租戶插件(例如 Ultimate Multisite 的某些進階功能或專門的 SaaS 解決方案)會處理大部分複雜的隔離邏輯,包括:

  • 用戶角色管理:為每個租戶建立獨立的角色和權限集。
  • 數據庫分離 (Database Separation):在某些高級設定中,插件可以配置不同的資料庫或前綴來物理上分隔數據。
  • URL 結構隔離:確保所有連結都正確地指向各自的租戶目錄。

2. 使用子目錄/子網域架構 (Subdirectory/Subdomain Structure)

對於較輕量的需求,可以利用 WordPress 的標準功能來實現邏輯上的隔離:

  • 子目錄 (Subdirectories):例如 example.com/tenant1example.com/tenant2。這允許您使用不同的設定檔或主題來區分它們,但數據仍然共享同一個主資料庫(需要嚴格的權限控制)。
  • 子網域 (Subdomains):例如 tenant1.example.comtenant2.example.com。這提供了更強的環境隔離,因為每個租戶可以擁有自己的獨立安裝或設定檔。

3. 使用 Hooks 或 Custom Logic 進行細粒度控制

當您需要非常精確地在特定事件(例如用戶登入、內容保存)時執行隔離邏輯,可以使用 WordPress 的 Hooks 來編寫自定義程式碼。

/**
* 在訂單完成後觸發的自定義邏輯
*/
add_action( 'woocommerce_order_status_completed', 'my_custom_isolation_logic' );

function my_custom_isolation_logic( $order_id ) {
// 這裡可以加入檢查:確保當處理這個訂單時,用戶的租戶 ID 是正確的。
$current_tenant_id = get_current_user_tenant_id();

if ( ! $current_tenant_id ) {
// 如果沒有設定到租戶,則拋出錯誤或進行預設處理
return;
}

// 執行特定於該租戶的數據清理或通知
error_log( "Order {$order_id} completed for Tenant ID: {$current_tenant_id}" );
}

安全注意事項:避免隔離漏洞

即使您設置了多租戶架構,安全仍然是首要任務。請務必注意以下幾點:

  • 輸入驗證 (Input Validation):永遠不要信任來自用戶的任何數據。在處理任何與租戶 ID 或資源相關的請求時,必須進行嚴格的驗證,防止「越權訪問」(Privilege Escalation)。
  • 資料庫查詢隔離:確保您的所有資料庫查詢都明確地包含租戶的上下文(例如 WHERE tenant_id = X),從而防止 SQL 注入或跨租戶數據洩露。
  • 定期審核:定期的安全審計可以幫助您確認隔離機制是否仍然有效,特別是當您的插件或核心 WordPress 版本更新時。

總結來說,要實現穩健的多租戶隔離,建議從使用成熟的、經過測試的插件開始,並結合正確的架構設計來確保數據和環境的徹底分離。

Ultimate Multisite:多租戶功能 1.2.0 支持為每個子網站提供獨立的資料庫和檔案系統隔離,以確保主權租戶的數據保持分離,同時保留網路層級的配置、計費和管理能力。

隔離策略

為需要更強資料隔離、專用檔案系統儲存或獨立主機邊界(host boundary)的客戶,請使用主權隔離(sovereign isolation)。

每個主權租戶都應該擁有:

  • 專門為租戶設計的資料庫或已獲得主機批准的資料庫前綴策略。
  • 專門為租戶設定的文件系統根目錄。
  • 一個租戶註冊表條目,用於將網站與其資料庫、根路徑、主機名稱和隔離模型進行對應。

在租戶被視為上線之前,需要進行遷移驗證結果。

資料庫主機綁定

版本 1.2.0 對主機綁定行為進行了預設的同機器安裝調整。例如 localhost 這類同機器值會被標準化,這樣 Bedrock、FrankenPHP 和容器化的 WordPress 安裝就可以對 MySQL 實際看到的 Host 字串授予和驗證權限了。

當設定主權租戶(sovereign tenant)時:

  1. 將資料庫主機設定為租戶運行環境所要求的數值。

  2. 當主機預期是本地連線時,請使用 localhost 來進行本地套件安裝。

  3. 僅在資料庫伺服器授予該主機權限時,才使用 127.0.0.1 或服務主機名稱。

  4. 更換主機綁定後,執行遷移驗證。

如果驗證報告顯示失敗,請將租戶資料庫中的使用者權限與配置的主機綁定進行比較。對於被授予 user@localhost 的使用者,這與 [email protected]user@% 是不同的。

檔案系統根目錄

租戶根目錄應在重啟和部署後保持穩定。請避免使用臨時的掛載路徑。對於 Bedrock 風格的安裝,請確認租戶根目錄指向租戶啟動程序(bootstrap)預期的 WordPress 網站根目錄,而不僅僅是專案根目錄。

供應順序

對於新的主權租戶,請使用以下順序:

  1. 建立租戶註冊條目。

  2. 建立租戶資料庫和資料庫使用者。

  3. 初始化租戶結構(schema)。

  4. 建立租戶使用者。

  5. 設定租戶檔案系統路徑。

  6. 執行遷移驗證。

  7. 在驗證通過後切換路由或 DNS。

這個順序可以防止部分隔離的租戶在資料庫寫入器、使用者和檔案系統準備就緒之前接收到流量。

主權客戶管理流程

Ultimate Multisite v2.13.0 在啟用主權模式(sovereign mode)時,會將客戶管理操作保留在主網站上。租戶仍然可以作為一個獨立的 WordPress 安裝來運行,但那些依賴網路計費、會員資格或共享帳戶資料的面向客戶的操作,應該將客戶導回主網站,而不是嘗試在租戶運行環境中完成該操作。

主站流程適用於:

  • 結帳與計劃變更。
  • 帳戶概覽與客戶資料操作。
  • 帳單地址更新和付款管理畫面。
  • 發票與付款歷史記錄檢視。
  • 網站管理操作,例如新增或刪除網站。

模板切換。 網域映射與主網域變更。

當客戶從某個主權租戶(sovereign tenant)開始執行其中一項操作時,Ultimate Multisite 會建立對應的主站 URL,並在安全的情況下保留來源租戶作為返回目標。這樣做可以讓客戶在網路記錄上完成該受管操作後,回到租戶的上下文,而不會在主資料庫中重複計費或會員狀態。

對於操作人員來說,實務上的規則是:應讓計費、帳戶、結帳、發票、主題和網域管理頁面在主網站上保持可見,以供主權網路使用。租戶儀表板可以連結到這些頁面,但主網站仍然是該操作的「真實來源」(source of truth)。