JWT 驗證外掛程式

Solr 可以使用 JWTAuthPlugin 支援基於 JSON Web Token (JWT) 的持有人驗證。

這允許 Solr 藉由驗證 JWT 格式的 存取權杖是否由身分提供者以數位方式簽署,來斷言使用者已經過外部身分提供者驗證。典型的使用案例是將 Solr 與啟用 OpenID Connect 的 IdP 整合。

模組

這是透過 jwt-auth Solr 模組提供,使用前需要啟用。

啟用 JWT 驗證

若要使用 JWT 持有人驗證,security.json 檔案必須包含 authentication 部分,其中定義用於驗證的類別以及設定參數。

用於註冊外掛程式的最簡單 security.json (不含設定) 如下

{
  "authentication": {
    "class":"solr.JWTAuthPlugin",
    "blockUnknown":"false"
  }
}

外掛程式預設會要求所有流量都必須有有效的 JWT 權杖。

如果 blockUnknown 屬性如上例所示設定為 false,則可以使用未經驗證的 REST API 呼叫開始設定外掛程式,這在編輯 JWT 驗證外掛程式設定一節中進一步說明。

設定參數

金鑰 描述 預設值

blockUnknown

如果您需要透過 REST API 執行設定,或如果您使用授權外掛程式且只想保護特定路徑,請設為 false。預設情況下,所有請求都需要權杖

true

realm

要在 HTTP 401 回應中回顯的驗證領域名稱。也會顯示在管理 UI 登入頁面中

'solr-jwt'

scope

以空白分隔的有效範圍清單。如果已設定,JWT 存取權杖必須包含 scope 宣告,其中至少包含列出的其中一個範圍。範例:solr:read solr:admin

requireIss

若請求缺少 iss (發行者) 宣告則會失敗

true

requireExp

若請求缺少 exp (到期時間) 宣告則會失敗

true

algAllowlist

要接受的演算法 JSON 陣列:HS256HS384HS512RS256RS384RS512ES256ES384ES512PS256PS384PS512、`none

預設為允許所有演算法

jwkCacheDur

JWK 快取持續時間 (以秒為單位)

3600 (1 小時)

principalClaim

要從哪個宣告 ID 提取主體

sub

rolesClaim

要從哪個聲明 ID 中提取使用者角色。支援頂層聲明和巢狀聲明。使用 someClaim.child 語法來處理巢狀在 someClaim 物件內的 child 聲明。然後,聲明必須包含以空格分隔的角色列表或 JSON 陣列。這些角色接著可用於在授權外掛程式中定義細微的存取權限

預設情況下,來自 scope 聲明的範圍會作為使用者角色傳遞。

claimsMatch

必須與正規表示式 (值) 匹配的聲明 (鍵) 的 JSON 物件。範例:{ "foo" : "A|B" } 將要求 foo 聲明為 "A" 或 "B"。

adminUiScope

定義從管理 UI 登入時請求的範圍。

如果未定義,則使用 scope 參數的第一個範圍。

redirectUris

外部驗證後重定向的有效位置。接受字串或字串陣列。必須是 Solr 的基本 URL,例如 https://solr1.example.com:8983/solr/,且必須與事先在身分提供者處註冊的重定向 URI 清單相符。

預設為空清單,即假設任何節點都是有效的重定向目標。

trustedCerts

與 IdP 通訊時應信任的一個或多個純文字 PEM 或 PKCS#7 格式的 X.509 SSL 憑證。換行符號必須替換為 \n。有關其用法的更多資訊,請參閱 信任 IdP 伺服器 段落。

預設為 Java 信任儲存區

trustedCertsFile

類型為 PEM、DER 或 PKCS#7 的檔案路徑,其中包含與 IdP 通訊時應信任的一個或多個 X.509 SSL 憑證。也可以是檔案路徑陣列。有關其用法的更多資訊,請參閱 信任 IdP 伺服器 段落。

預設為 Java 信任儲存區

issuers

要支援的發行者 (身分提供者) 清單。有關配置語法,請參閱 發行者配置 章節。

發行者配置

此外掛程式支援一個或多個權杖發行者 (IdP)。發行者配置為 issuers 配置金鑰下的 JSON 物件清單。清單中的第一個發行者是「主要發行者」,這是用於登入管理 UI 的發行者。

金鑰 描述 預設值

name

發行者的唯一名稱。用於透過 API 操作清單。

wellKnownUrl

指向 OpenID Connect Discovery 端點的 URL

clientId

用於 OpenID Connect 的用戶端識別碼。必須使用管理 UI 進行驗證。僅限於主要發行者使用。

jwksUrl

指向 JWKs 端點的 URL。必須使用 https 協定。也可以選擇使用 URL 陣列,在驗證簽名時將查詢所有 URL 的所有公鑰。

如果提供 wellKnownUrl,則會自動配置。

jwk

作為 jwksUrl 的替代方案,您可以提供包含發行者公鑰的靜態 JSON 物件。格式可以是 JWK 或 JWK Set,範例請參閱 RFC7517

iss

在 IdP 上設定的唯一發行者 ID。傳入的權杖必須具有相符的 iss 聲明。也用於在設定多個發行者時解析發行者。

如果提供 wellKnownUrl,則會自動配置。

aud

驗證 aud (對象) 聲明是否等於此字串。

如果已配置,則使用 clientId

authorizationEndpoint

Id 提供者的授權端點的 URL。

如果提供 wellKnownUrl,則會自動配置。

tokenEndpoint

Id 提供者的權杖端點的 URL。

如果提供 wellKnownUrl,則會自動配置。

authorizationFlow

指定要使用的 OAuth 2.0 流程。支援的流程為 'implicit' 和 'code_pkce' (用於授權碼並帶有「用於代碼交換的驗證密鑰」)。請注意:'implicit' 已被棄用,強烈建議改用 'code_pkce'。

implicit

為了向後相容,主要發行者的所有配置金鑰都可以配置為頂層金鑰,除了 name

更多配置範例

使用 JWKS URL

若要開始對所有使用者強制執行驗證,並要求在 Authorization 標頭中使用有效的 JWT,您需要使用一個或多個 JSON Web Key (JWK) 來配置外掛程式。這是一個 JSON 文件,其中包含用於簽署/加密 JWT 的金鑰。它可以是對稱或非對稱金鑰。JWK 可以從外部 HTTPS 端點提取 (並快取),或直接在 security.json 中指定。以下是前者的範例

{
  "authentication": {
    "class": "solr.JWTAuthPlugin",
    "jwksUrl": "https://my.key.server/jwk.json"
  }
}

使用管理 UI 支援

此範例顯示如何使用 OpenID Connect Discovery 和一個知名的 URI 來配置,以便自動設定許多常見設定,包括使用啟用了 OpenID Connect 的身分提供者來使用管理 UI 的功能。

{
  "authentication": {
    "class": "solr.JWTAuthPlugin",
    "wellKnownUrl": "https://idp.example.com/.well-known/openid-configuration",
    "clientId": "xyz",
    "redirectUris": "https://my.solr.server:8983/solr/"
  }
}

在此情況下,jwksUrlissauthorizationEndpoint 將從提取的設定自動配置。

複雜範例

讓我們看一下更複雜的配置,這次配置了兩個發行者,其中一個使用靜態嵌入的 JWK

{
  "authentication": {
    "class": "solr.JWTAuthPlugin", (1)
    "blockUnknown": true, (2)
    "principalClaim": "solruid", (3)
    "claimsMatch": { "foo" : "A|B", "dept" : "IT" }, (4)
    "scope": "solr:read solr:write solr:admin", (5)
    "algAllowlist" : [ "RS256", "RS384", "RS512" ], (6)
    "issuers": [ (7)
      {
        "name": "example1-static", (8)
        "jwk": { (9)
          "e": "AQAB",
          "kid": "k1",
          "kty": "RSA",
          "n": "3ZF6w....vjbCXxw"
        },
        "clientId": "solr-client-12345", (10)
        "iss": "https://example.com/idp", (11)
        "aud": "https://example.com/solr" (12)
      },
      {
        "name": "example2",
        "wellKnownUrl": "https://example2.com/.well-known/oidc", (13)
        "aud": "https://example2.com/solr"
      }
    ],
    "trustedCertsFile": "/path/to/certsFile.pem" (14)
  }
}

讓我們評論一下此配置

1 外掛程式類別
2 請務必封鎖沒有有效權杖的任何人 (這也是預設值)
3 從預設 sub 以外的其他聲明中提取使用者 ID
4 要求 roles 聲明為 "A" 或 "B" 其中之一,且 dept 聲明為 "IT"
5 要求範圍 solr:readsolr:writesolr:admin 其中之一
6 僅接受 RSA 演算法用於簽名
7 發行者配置的陣列
8 每個發行者物件都應具有唯一名稱
9 在此,我們內聯傳遞 JWK,而不是使用 jwksUrl 參考 URL
10 設定在身分提供者註冊的用戶端 ID
11 設定發行者 ID。將用於驗證權杖。權杖的 'iss' 聲明必須與設定的發行者 ID 之一相符。
12 設定對象聲明。權杖的 'aud' 聲明必須與設定的發行者之一的 'aud' 相符。
13 此發行者透過探索自動設定,因此不需要 'iss' 和 JWK 設定。
14 提供 SSL 憑證以信任 IdP 的 https 通訊。

使用非 SSL URL

在生產環境中,您應該始終使用 SSL 保護的 HTTPS 連線,否則您會讓自己遭受攻擊。但是,在開發中,使用普通的 HTTP URL 並繞過 Solr 執行的安全性檢查可能很有用。若要支援此操作,您可以在啟動時設定系統屬性 -Dsolr.auth.jwt.allowOutboundHttp=true

信任 IdP 伺服器

與 Oauth2 伺服器 (IdP) 的所有通訊均透過 HTTPS 進行。預設情況下,使用 Java 的內建信任儲存區。但是,透過設定 trustedCertsFiletrustedCerts 選項之一,此外掛程式將改為信任提供的憑證集,而不是任何由根 CA 簽署的憑證。這既更安全,也讓您信任自簽憑證。它也具有即使 Solr 未在 SSL 模式下啟動也能運作的優點。

請設定 trustedCertstrustedCertsFile 選項。同時設定兩者會導致錯誤。如果 trustedCertsFile 是字串陣列,則 Solr 將從所有檔案中剖析憑證。

多重驗證方案

Solr 提供 MultiAuthPlugin 以支援基於 Authorization 標頭的多重驗證方案。這讓您可以將 Solr 設定為使用 JWTAuthPlugin 將使用者管理和驗證委派給 OIDC 提供者,但也允許一小組服務帳戶在使用 OIDC 不受支援或不實際時使用 Basic 驗證。

編輯 JWT 驗證外掛程式配置

可以使用 驗證 API 設定或變更上述所有屬性。因此,您可以從僅配置 classblockUnknown=false 的簡單配置開始,然後使用 API 配置其餘部分。

設定配置屬性

設定驗證外掛程式的屬性。上表中每個配置金鑰都可以用作 set-property 命令的參數金鑰。

範例

  • V1 API

  • V2 API

curl https://127.0.0.1:8983/solr/admin/authentication -H 'Content-type:application/json' -H 'Authorization: Bearer xxx.yyy.zzz' -d '{
  "set-property": {
    "blockUnknown":true,
    "wellKnownUrl": "https://example.com/.well-known/openid-configuration",
    "scope": "solr:read solr:write"
  }
}
'
curl https://127.0.0.1:8983/api/cluster/security/authentication -H 'Content-type:application/json' -H 'Authorization: Bearer xxx.yyy.zzz' -d '{
  "set-property": {
    "blockUnknown":true,
    "wellKnownUrl": "https://example.com/.well-known/openid-configuration",
    "scope": "solr:read solr:write"
  }
}
'

在此外掛程式啟動後,在緊湊序列化格式 (上面的 xxx.yyy.zzz) 中插入有效的 JWT 存取權杖以使用 Solr 進行驗證,或保留 blockUnknown=false 直到配置完成,然後將其切換為 true 以開始強制執行。

目前不支援透過 REST API 新增多個權杖發行者,但是您可以使用 'issuer' 屬性作為頂層屬性,透過 API 設定單個發行者來解決此問題。

搭配 JWT 驗證使用用戶端

SolrJ

SolrJ 目前不支援為每個請求提供 JWT 權杖。

cURL

若要在使用 cURL 公用程式時使用 Solr 進行驗證,請在 Authorization 標頭中提供有效的 JWT 存取權杖,如下所示 (將 xxxxxx.xxxxxx.xxxxxx 替換為您的 JWT 緊湊權杖)

curl -H "Authorization: Bearer xxxxxx.xxxxxx.xxxxxx" https://127.0.0.1:8983/solr/admin/info/system

管理 UI

啟用此外掛程式後,使用者嘗試執行受限制的動作時,將會被重新導向至管理 UI 中的登入頁面。該頁面有一個按鈕,使用者點擊該按鈕後將被重新導向至身分提供者的登入頁面。

如果設定多個發行者 (IdP),則將使用清單中的第一個發行者用於管理 UI。驗證成功後,使用者將被重新導向回 Solr 管理 UI 到最後一個已知位置。工作階段將持續到 JWT 權杖過期時間,並且僅對一個 Solr 伺服器有效。這表示您在瀏覽至另一個 Solr 節點時必須再次登入。在左側欄中還有一個登出選單,使用者可以在其中明確登出。

搭配 JWT 驗證使用 Solr 控制指令碼

控制指令碼 (bin/solr) 目前不支援 JWT 驗證。