😸

keycloakを利用してSCIM実装してみる

2024/05/27に公開

認証とは

参考:https://www.keycloak.org/getting-started/getting-started-docker
docker run -p 18081:8081 -e KEYCLOAK_ADMIN=admin -e KEYCLOAK_ADMIN_PASSWORD=admin -v C:\dev\mount:/tmp --name keycloak quay.io/keycloak/keycloak:22.0.5 start-dev
※マウントしてます
※複数個のポートフォワーディングしています

SCIMプラグイン導入方法

ダウンロード参考:https://scim-for-keycloak.de/

scimのプラグイン
アカウント作成


インストールの参考:https://scim-for-keycloak.de/documentation/installation/install
provider配下に配置
cp /tmp/scim-for-keycloak-kc-22-1.1.1-free.jar /opt/keycloak/providers/
設定ファイルを修正
/keycloak/conf/keycloak.confに下記を追記
spi-theme-welcome-theme=scim
spi-realm-restapi-extension-scim-license-key={ライセンスキー}
※ライセンスキーはアカウントページよりDL

ビルド
cd /opt/keycloak/bin
./kc.sh build
./kc.sh start-dev --http-port 8081

確認
下記へ
http://localhost:18081/
SCIM専用のコンソール画面がでた。感動。

使い方
https://scim-for-keycloak.de/documentation/administration/realm-management

参考:https://czetsuya.medium.com/generate-keycloak-bearer-token-using-postman-5bd81d7d1f8
アクセストークン取得
クライアントを作成
クレデンシャルタブ→クライアント認証:Client Id and Secret
cliantid:test2
クライアント・シークレット:xdJcWzwQgLNmbfVD0vkr5cKyESSAcfUH

ユーザ作成
ID:3975faa8-481c-4e7e-b9e5-e79d77b75ec5
ユーザ名:czetsuyatech
パスワード:czetsuyatech

OAuthをやる

参考:https://paulbares.medium.com/quick-tip-oauth2-with-keycloak-and-postman-cc7211b693a5
Realm id:master
Client id:test2
CS:xdJcWzwQgLNmbfVD0vkr5cKyESSAcfUH

POSTMAN
AuthURL:http://localhost:18081/auth/realms/master/protocol/openid-connect/auth
Access Token URL::http://localhost:18081/auth/realms/master/protocol/openid-connect/auth

アクセス
curl -H 'Content-Type: application/json;charset=utf-8' -H 'Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICIxNDY0ZjUwNC1kNWYwLTQ0ZmEtOWI4Mi1hMjE2YjA0ZTc5NDgifQ.eyJleHAiOjE3MDI2NzQzOTYsImlhdCI6MTY5ODUyNzE5NiwianRpIjoiNWU4MDFiZjQtODhkYy00MTk2LTkwZDgtMzcwYWY5MWRmNzgxIiwiaXNzIjoiaHR0cDovL2xvY2FsaG9zdDoxODA4MS9yZWFsbXMvbWFzdGVyIiwiYXVkIjoiaHR0cDovL2xvY2FsaG9zdDoxODA4MS9yZWFsbXMvbWFzdGVyIiwidHlwIjoiSW5pdGlhbEFjY2Vzc1Rva2VuIn0.vKgKBZxlptMo8NlfWscNAOk_l6dqol7TKT6rtwbyIK0' http://localhost:18081/realms/master/scim/v2/Users

もう一回

レルムの作成

設定値
Realm name testRealm
enabled on

ユーザの作成

設定値
Username login_user
Credientials login_user
temporary off

client skopesの作成

設定値
name test_scope

clientの作成

設定値
Client ID test_client
Client authentication On
Authentication flow Standard flow
Direct access grants
Root URL http://localhost:18081
Client secret pVQeYoinH2dGaB1VxZeplZWCMgYPthOu
Client scope test_scopeを追加

アクセストークンの発行

エンドポイント:Keycloak server OIDC URI endpoints参照
<書式>
curl http://localhost:18081/realms/testRealm/protocol/openid-connect/token -d "grant_type=password&client_id=test_client&client_secret=pVQeYoinH2dGaB1VxZeplZWCMgYPthOu&username=login_user&password=login_user&scope=openid"

<レスポンス>
{
"access_token": "eyJhbGciOiJSUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICI3SnFXcGlHNm4xTWVsSi1ISnZRbzBWdkQyYlpxdlJxZWNlTWtWMGFaSnc0In0.eyJleHAiOjE2OTg2MTQ4OTAsImlhdCI6MTY5ODYxNDU5MCwianRpIjoiYjUyMDM5NTgtYzNiMi00MTQxLWFkOTUtZTU1NWYxNGYyNzA4IiwiaXNzIjoiaHR0cDovL2xvY2FsaG9zdDoxODA4MS9yZWFsbXMvdGVzdFJlYWxtIiwiYXVkIjoiYWNjb3VudCIsInN1YiI6IjQyM2EzNTU4LWU0MDMtNDQyZi05ZWM5LTIwYzkzYmUyMjNkMSIsInR5cCI6IkJlYXJlciIsImF6cCI6InRlc3RfY2xpZW50Iiwic2Vzc2lvbl9zdGF0ZSI6ImU5NDdkMzdhLTIwNjQtNDUzMS1hZjNkLTVmNDUyODVmNzc3NSIsImFjciI6IjEiLCJhbGxvd2VkLW9yaWdpbnMiOlsiaHR0cDovL2xvY2FsaG9zdDoxODA4MSJdLCJyZWFsbV9hY2Nlc3MiOnsicm9sZXMiOlsib2ZmbGluZV9hY2Nlc3MiLCJ1bWFfYXV0aG9yaXphdGlvbiIsImRlZmF1bHQtcm9sZXMtdGVzdHJlYWxtIl19LCJyZXNvdXJjZV9hY2Nlc3MiOnsiYWNjb3VudCI6eyJyb2xlcyI6WyJtYW5hZ2UtYWNjb3VudCIsIm1hbmFnZS1hY2NvdW50LWxpbmtzIiwidmlldy1wcm9maWxlIl19fSwic2NvcGUiOiJvcGVuaWQgcHJvZmlsZSB0ZXN0X3Njb3BlIGVtYWlsIiwic2lkIjoiZTk0N2QzN2EtMjA2NC00NTMxLWFmM2QtNWY0NTI4NWY3Nzc1IiwiZW1haWxfdmVyaWZpZWQiOmZhbHNlLCJwcmVmZXJyZWRfdXNlcm5hbWUiOiJsb2dpbl91c2VyIn0.Y1k01GKU4DPB7VTuXZ51yfh5_vNXf0ZZ7sBGrLvhHbHdEOMLcx9M6iTdGNpMJikvhHpu2JZyfkQlq1aLCtt5U1o5DELMk_ycaCtOTSvRo6rVt0xFJPgHlHRUksPPPaBY7SY2U0pniUzMU7Vt9Z016jXMuNeU-UiKw5xc6GSh5UUllFv-_1190r5Vc3NKy9ojLR_vZRuFp82eN0flGBfRYjlXeXLmpiDkYU7gWb-6-8NzFHqF5eBmdISNY2xNTSaUowBYOdLxpH2V7mxAdc8ZmGqZ46jAkd-VuNqm37tzfA3cd1ntfPHgufJaQn3bpwLyKMqDYZtPTpzvqhhqxuMAAQ",
"expires_in": 300,
"refresh_expires_in": 1800,
"refresh_token": "eyJhbGciOiJIUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICJmNzRmNWU2My05NGVhLTRjZDUtODA4ZS04ZmZiOWQ3ZmZkZWMifQ.eyJleHAiOjE2OTg2MTYzOTAsImlhdCI6MTY5ODYxNDU5MCwianRpIjoiODZlNDgxNWEtYWQ1Mi00ZWNmLTliZjItN2E4ZDgwYWRhZjYyIiwiaXNzIjoiaHR0cDovL2xvY2FsaG9zdDoxODA4MS9yZWFsbXMvdGVzdFJlYWxtIiwiYXVkIjoiaHR0cDovL2xvY2FsaG9zdDoxODA4MS9yZWFsbXMvdGVzdFJlYWxtIiwic3ViIjoiNDIzYTM1NTgtZTQwMy00NDJmLTllYzktMjBjOTNiZTIyM2QxIiwidHlwIjoiUmVmcmVzaCIsImF6cCI6InRlc3RfY2xpZW50Iiwic2Vzc2lvbl9zdGF0ZSI6ImU5NDdkMzdhLTIwNjQtNDUzMS1hZjNkLTVmNDUyODVmNzc3NSIsInNjb3BlIjoib3BlbmlkIHByb2ZpbGUgdGVzdF9zY29wZSBlbWFpbCIsInNpZCI6ImU5NDdkMzdhLTIwNjQtNDUzMS1hZjNkLTVmNDUyODVmNzc3NSJ9.1VG7fWJNLtkLhXp0d-7ZcjpEE1ec-NogFnw20syL7V8",
"token_type": "Bearer",
"id_token": "eyJhbGciOiJSUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICI3SnFXcGlHNm4xTWVsSi1ISnZRbzBWdkQyYlpxdlJxZWNlTWtWMGFaSnc0In0.eyJleHAiOjE2OTg2MTQ4OTAsImlhdCI6MTY5ODYxNDU5MCwiYXV0aF90aW1lIjowLCJqdGkiOiI0ZWNkZjkxNS1jZTg1LTQwZTAtOGUxNi1jNWUwYzIxNGU0ODAiLCJpc3MiOiJodHRwOi8vbG9jYWxob3N0OjE4MDgxL3JlYWxtcy90ZXN0UmVhbG0iLCJhdWQiOiJ0ZXN0X2NsaWVudCIsInN1YiI6IjQyM2EzNTU4LWU0MDMtNDQyZi05ZWM5LTIwYzkzYmUyMjNkMSIsInR5cCI6IklEIiwiYXpwIjoidGVzdF9jbGllbnQiLCJzZXNzaW9uX3N0YXRlIjoiZTk0N2QzN2EtMjA2NC00NTMxLWFmM2QtNWY0NTI4NWY3Nzc1IiwiYXRfaGFzaCI6ImJwYTRmTHZ5NGVjQndUaEZfTU40dVEiLCJhY3IiOiIxIiwic2lkIjoiZTk0N2QzN2EtMjA2NC00NTMxLWFmM2QtNWY0NTI4NWY3Nzc1IiwiZW1haWxfdmVyaWZpZWQiOmZhbHNlLCJwcmVmZXJyZWRfdXNlcm5hbWUiOiJsb2dpbl91c2VyIn0.oneCzFrgXNWQW8QMw_FfCJMrNqavipvhrpcPikm0_NO3rGIpfEnbhIvC0SYxYgLllVC4nc9SvR7uVzaJQQ1K50h6XbIKyDs9DC_9P17GgawwN7GfVUWdNC2dL4ROaiI4bOhShSgqhSpmJxittc_7r2Lc0wdbtSDBxe7-bcOjw7iKU9gphrs3wgHXf21s8pTc-vuUbO4rxsGUdG-wogg59ozLrlyT1z_JsGJbcPf3gM1pnluVtvZ0T2akRp9JbLhgblcGdlyrKCHb59_tTc5QdmXJoQdFp5OGmZZ2a8kC4-MO2YGq1DeMGD9TJPArKpMiX9BDYyutXR3tZ6qGkHRlng",
"not-before-policy": 0,
"session_state": "e947d37a-2064-4531-af3d-5f45285f7775",
"scope": "openid profile test_scope email"
}

アクセストークンを利用してアクセス

curl -H 'Authorization: Bearer eyJhbGciOiJSUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICI3SnFXcGlHNm4xTWVsSi1ISnZRbzBWdkQyYlpxdlJxZWNlTWtWMGFaSnc0In0.eyJleHAiOjE2OTg2MTQ4OTAsImlhdCI6MTY5ODYxNDU5MCwianRpIjoiYjUyMDM5NTgtYzNiMi00MTQxLWFkOTUtZTU1NWYxNGYyNzA4IiwiaXNzIjoiaHR0cDovL2xvY2FsaG9zdDoxODA4MS9yZWFsbXMvdGVzdFJlYWxtIiwiYXVkIjoiYWNjb3VudCIsInN1YiI6IjQyM2EzNTU4LWU0MDMtNDQyZi05ZWM5LTIwYzkzYmUyMjNkMSIsInR5cCI6IkJlYXJlciIsImF6cCI6InRlc3RfY2xpZW50Iiwic2Vzc2lvbl9zdGF0ZSI6ImU5NDdkMzdhLTIwNjQtNDUzMS1hZjNkLTVmNDUyODVmNzc3NSIsImFjciI6IjEiLCJhbGxvd2VkLW9yaWdpbnMiOlsiaHR0cDovL2xvY2FsaG9zdDoxODA4MSJdLCJyZWFsbV9hY2Nlc3MiOnsicm9sZXMiOlsib2ZmbGluZV9hY2Nlc3MiLCJ1bWFfYXV0aG9yaXphdGlvbiIsImRlZmF1bHQtcm9sZXMtdGVzdHJlYWxtIl19LCJyZXNvdXJjZV9hY2Nlc3MiOnsiYWNjb3VudCI6eyJyb2xlcyI6WyJtYW5hZ2UtYWNjb3VudCIsIm1hbmFnZS1hY2NvdW50LWxpbmtzIiwidmlldy1wcm9maWxlIl19fSwic2NvcGUiOiJvcGVuaWQgcHJvZmlsZSB0ZXN0X3Njb3BlIGVtYWlsIiwic2lkIjoiZTk0N2QzN2EtMjA2NC00NTMxLWFmM2QtNWY0NTI4NWY3Nzc1IiwiZW1haWxfdmVyaWZpZWQiOmZhbHNlLCJwcmVmZXJyZWRfdXNlcm5hbWUiOiJsb2dpbl91c2VyIn0.Y1k01GKU4DPB7VTuXZ51yfh5_vNXf0ZZ7sBGrLvhHbHdEOMLcx9M6iTdGNpMJikvhHpu2JZyfkQlq1aLCtt5U1o5DELMk_ycaCtOTSvRo6rVt0xFJPgHlHRUksPPPaBY7SY2U0pniUzMU7Vt9Z016jXMuNeU-UiKw5xc6GSh5UUllFv-_1190r5Vc3NKy9ojLR_vZRuFp82eN0flGBfRYjlXeXLmpiDkYU7gWb-6-8NzFHqF5eBmdISNY2xNTSaUowBYOdLxpH2V7mxAdc8ZmGqZ46jAkd-VuNqm37tzfA3cd1ntfPHgufJaQn3bpwLyKMqDYZtPTpzvqhhqxuMAAQ' http://localhost:18081/realms/testRealm/scim/v2/Users

curl: (6) Could not resolve host: Bearer

curl -H 'Authorization: {アクセストークン}'

curl -H "Authorization: {アクセストークン}"

{"detail":"not authenticated","schemas":["urn:ietf:params:scim:api:messages:2.0:Error"],"status":401,"scimType":"unauthenticated"}

んーアクセストークンが違うかな

Creating an OIDC Client Secret Rotation Policy やってみる

clientの作成

設定値
Authentication flow Standard flow
Direct access grants
Service accounts roles

<書式>
-H "Authorization:Basic <BASE64エンコードした<ID>:<PASS>>"
<実際>
userのID、パスの場合
curl -X POST -H "Authorization: BASIC bG9naW5fdXNlcjpsb2dpbl91c2Vy" http://localhost:18081/realms/testRealm/protocol/openid-connect/token -d "grant_type=client_credentials"
{"error":"invalid_client","error_description":"Invalid client or Invalid client credentials"}
clientのID、クライアントシークレットの場合
test_client:pVQeYoinH2dGaB1VxZeplZWCMgYPthOu
curl -X POST -H "Authorization: BASIC dGVzdF9jbGllbnQ6cFZRZVlvaW5IMmRHYUIxVnhaZXBsWldDTWdZUHRoT3U=" http://localhost:18081/realms/testRealm/protocol/openid-connect/token -d "grant_type=client_credentials"

{
"access_token": "eyJhbGciOiJSUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICI3SnFXcGlHNm4xTWVsSi1ISnZRbzBWdkQyYlpxdlJxZWNlTWtWMGFaSnc0In0.eyJleHAiOjE2OTg2MTk2MjksImlhdCI6MTY5ODYxOTMyOSwianRpIjoiZDJmNjI5MTQtZDY2ZS00NmViLWJkOTItZjhkOGM3ZWNiZjQ4IiwiaXNzIjoiaHR0cDovL2xvY2FsaG9zdDoxODA4MS9yZWFsbXMvdGVzdFJlYWxtIiwiYXVkIjoiYWNjb3VudCIsInN1YiI6IjUxZmVmNGJlLTJlODQtNDczNi04M2VkLTQ5YTMyZmNkYjIxNSIsInR5cCI6IkJlYXJlciIsImF6cCI6InRlc3RfY2xpZW50IiwiYWNyIjoiMSIsImFsbG93ZWQtb3JpZ2lucyI6WyJodHRwOi8vbG9jYWxob3N0OjE4MDgxIl0sInJlYWxtX2FjY2VzcyI6eyJyb2xlcyI6WyJvZmZsaW5lX2FjY2VzcyIsInVtYV9hdXRob3JpemF0aW9uIiwiZGVmYXVsdC1yb2xlcy10ZXN0cmVhbG0iXX0sInJlc291cmNlX2FjY2VzcyI6eyJhY2NvdW50Ijp7InJvbGVzIjpbIm1hbmFnZS1hY2NvdW50IiwibWFuYWdlLWFjY291bnQtbGlua3MiLCJ2aWV3LXByb2ZpbGUiXX19LCJzY29wZSI6InByb2ZpbGUgdGVzdF9zY29wZSBlbWFpbCIsImVtYWlsX3ZlcmlmaWVkIjpmYWxzZSwiY2xpZW50SG9zdCI6IjE3Mi4xNy4wLjEiLCJwcmVmZXJyZWRfdXNlcm5hbWUiOiJzZXJ2aWNlLWFjY291bnQtdGVzdF9jbGllbnQiLCJjbGllbnRBZGRyZXNzIjoiMTcyLjE3LjAuMSIsImNsaWVudF9pZCI6InRlc3RfY2xpZW50In0.QpbX0xh1CK-t40kFmSMaQ7OZvsGzieDfvvbNjCfQf6C1w8tQlBlE4DqJEY4AbQTylLq_7GFS4aeeRwGjLd508MUgdZbTXkixtPyy88vCN83T9Nt9cYI9L1v-rPCVgEbby91AJjik07OTlz0Zk8QWsSBVygP9MoRJMJB62Tj1p63UI5w_3rqKYm_Ibi1zjUi4b0RKKOhmNIpbFNDuimaH23EHJXlqqYOycsk6bfCWh17hswWYZ1KgpQ3-PyuB7HBFn38gtrODej7z2X-xC86BwVPvozJPr1p5fCW1nS6jvAPbaL4HimESp3_alcG8kav82KDd8VebpZl-ZtKWRknqmA",
"expires_in": 300,
"refresh_expires_in": 0,
"token_type": "Bearer",
"not-before-policy": 0,
"scope": "profile test_scope email"
}

curl -v -H "Authorization: Bearer eyJhbGciOiJSUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICI3SnFXcGlHNm4xTWVsSi1ISnZRbzBWdkQyYlpxdlJxZWNlTWtWMGFaSnc0In0.eyJleHAiOjE2OTg2MTk2MjksImlhdCI6MTY5ODYxOTMyOSwianRpIjoiZDJmNjI5MTQtZDY2ZS00NmViLWJkOTItZjhkOGM3ZWNiZjQ4IiwiaXNzIjoiaHR0cDovL2xvY2FsaG9zdDoxODA4MS9yZWFsbXMvdGVzdFJlYWxtIiwiYXVkIjoiYWNjb3VudCIsInN1YiI6IjUxZmVmNGJlLTJlODQtNDczNi04M2VkLTQ5YTMyZmNkYjIxNSIsInR5cCI6IkJlYXJlciIsImF6cCI6InRlc3RfY2xpZW50IiwiYWNyIjoiMSIsImFsbG93ZWQtb3JpZ2lucyI6WyJodHRwOi8vbG9jYWxob3N0OjE4MDgxIl0sInJlYWxtX2FjY2VzcyI6eyJyb2xlcyI6WyJvZmZsaW5lX2FjY2VzcyIsInVtYV9hdXRob3JpemF0aW9uIiwiZGVmYXVsdC1yb2xlcy10ZXN0cmVhbG0iXX0sInJlc291cmNlX2FjY2VzcyI6eyJhY2NvdW50Ijp7InJvbGVzIjpbIm1hbmFnZS1hY2NvdW50IiwibWFuYWdlLWFjY291bnQtbGlua3MiLCJ2aWV3LXByb2ZpbGUiXX19LCJzY29wZSI6InByb2ZpbGUgdGVzdF9zY29wZSBlbWFpbCIsImVtYWlsX3ZlcmlmaWVkIjpmYWxzZSwiY2xpZW50SG9zdCI6IjE3Mi4xNy4wLjEiLCJwcmVmZXJyZWRfdXNlcm5hbWUiOiJzZXJ2aWNlLWFjY291bnQtdGVzdF9jbGllbnQiLCJjbGllbnRBZGRyZXNzIjoiMTcyLjE3LjAuMSIsImNsaWVudF9pZCI6InRlc3RfY2xpZW50In0.QpbX0xh1CK-t40kFmSMaQ7OZvsGzieDfvvbNjCfQf6C1w8tQlBlE4DqJEY4AbQTylLq_7GFS4aeeRwGjLd508MUgdZbTXkixtPyy88vCN83T9Nt9cYI9L1v-rPCVgEbby91AJjik07OTlz0Zk8QWsSBVygP9MoRJMJB62Tj1p63UI5w_3rqKYm_Ibi1zjUi4b0RKKOhmNIpbFNDuimaH23EHJXlqqYOycsk6bfCWh17hswWYZ1KgpQ3-PyuB7HBFn38gtrODej7z2X-xC86BwVPvozJPr1p5fCW1nS6jvAPbaL4HimESp3_alcG8kav82KDd8VebpZl-ZtKWRknqmA" http://localhost:18081/realms/testRealm/scim/v2/Users

< HTTP/1.1 401 Unauthorized
< Referrer-Policy: no-referrer
< Strict-Transport-Security: max-age=31536000; includeSubDomains
< X-Content-Type-Options: nosniff
< WWW-Authenticate: Keycloak Access Tokens realm="testRealm"
< X-XSS-Protection: 1; mode=block
< Content-Type: application/scim+json
< content-length: 130
<
{"detail":"not authenticated","schemas":["urn:ietf:params:scim:api:messages:2.0:Error"],"status":401,"scimType":"unauthenticated"}* Connection #0 to host localhost left intact

curl -v -H "Authorization: Bearer eyJhbGciOiJSUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICI3SnFXcGlHNm4xTWVsSi1ISnZRbzBWdkQyYlpxdlJxZWNlTWtWMGFaSnc0In0.eyJleHAiOjE2OTg2MjA1MDgsImlhdCI6MTY5ODYyMDIwOCwianRpIjoiMTA4ZDcwMDQtNmNiOS00NWZjLWE2NTMtOGMwMDUzODg5NTg2IiwiaXNzIjoiaHR0cDovL2xvY2FsaG9zdDoxODA4MS9yZWFsbXMvdGVzdFJlYWxtIiwiYXVkIjoiYWNjb3VudCIsInN1YiI6IjUxZmVmNGJlLTJlODQtNDczNi04M2VkLTQ5YTMyZmNkYjIxNSIsInR5cCI6IkJlYXJlciIsImF6cCI6InRlc3RfY2xpZW50IiwiYWNyIjoiMSIsImFsbG93ZWQtb3JpZ2lucyI6WyJodHRwOi8vbG9jYWxob3N0OjE4MDgxIl0sInJlYWxtX2FjY2VzcyI6eyJyb2xlcyI6WyJvZmZsaW5lX2FjY2VzcyIsInVtYV9hdXRob3JpemF0aW9uIiwiZGVmYXVsdC1yb2xlcy10ZXN0cmVhbG0iXX0sInJlc291cmNlX2FjY2VzcyI6eyJhY2NvdW50Ijp7InJvbGVzIjpbIm1hbmFnZS1hY2NvdW50IiwibWFuYWdlLWFjY291bnQtbGlua3MiLCJ2aWV3LXByb2ZpbGUiXX19LCJzY29wZSI6InByb2ZpbGUgdGVzdF9zY29wZSBlbWFpbCIsImVtYWlsX3ZlcmlmaWVkIjpmYWxzZSwiY2xpZW50SG9zdCI6IjE3Mi4xNy4wLjEiLCJwcmVmZXJyZWRfdXNlcm5hbWUiOiJzZXJ2aWNlLWFjY291bnQtdGVzdF9jbGllbnQiLCJjbGllbnRBZGRyZXNzIjoiMTcyLjE3LjAuMSIsImNsaWVudF9pZCI6InRlc3RfY2xpZW50In0.hQ2Wv0D0Agwj4gAf8wcuhA3oLoR2Mw59BmJb79LVQMVtylXW-M5A1-6Dnw3aasONGCXzUlOjEw41EXtrvLyn6ycBWvttviETfgvehBuCXFV4MuMnaa9IelN4E5dfzOA9DTHZa6MWOJeH4G93heF4iUiP6GCPVQ92Og7xy5goNa8o8VcpZytgGOhIe1FBFscV1v1QilQ3Z0OWKOzDoLoO8LNTfkAEg2CxiNecJLIgKA0UEKgU01HjYctoHP7C2DB6PUh4zcPPJmSsvHRQ5977SMa5llbIvyoxKeWtSzPohIHhkgFLjqXuC7lKA-Ybb1yaNU6rAPNA9HVyMB64qHHOBg" http://localhost:18081/realms/testRealm/scim/v2/ResourceTypes

< HTTP/1.1 200 OK
< Referrer-Policy: no-referrer
< Strict-Transport-Security: max-age=31536000; includeSubDomains
< X-XSS-Protection: 1; mode=block
< X-Content-Type-Options: nosniff
< Content-Type: application/scim+json
< content-length: 4121
<
{"schemas":["urn:ietf:params:scim:api:messages:2.0:ListResponse"],"totalResults":5,"itemsPerPage":5,"startIndex":1,"Resources":[{"id":"Group","name":"Group","description":"Group","endpoint":"/Groups","schema":"urn:ietf:params:scim:schemas:core:2.0:Group","schemas":["urn:ietf:params:scim:schemas:core:2.0:ResourceType","urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures"],"urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures":{"autoFiltering":false,"autoSorting":false,"etag":{"enabled":false},"endpointControl":{"disableCreate":false,"disableGet":false,"disableList":false,"disableUpdate":false,"disableDelete":false},"authorization":{"authenticated":true,"useOrOnRoles":false}},"meta":{"resourceType":"ResourceType","created":"2023-10-29T21:31:15.899849Z","lastModified":"2023-10-29T21:31:15.899849Z","location":"http://localhost:18081/realms/testRealm/scim/v2/ResourceTypes/Group"}},{"id":"Schema","name":"Schema","description":"Schema endpoint description","endpoint":"/Schemas","schema":"urn:ietf:params:scim:schemas:core:2.0:Schema","schemas":["urn:ietf:params:scim:schemas:core:2.0:ResourceType","urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures"],"urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures":{"singletonEndpoint":false,"autoFiltering":true,"autoSorting":true,"authorization":{"authenticated":false}},"meta":{"resourceType":"ResourceType","created":"2019-10-18T12:51:11Z","lastModified":"2019-10-18T12:51:11Z","location":"http://localhost:18081/realms/testRealm/scim/v2/ResourceTypes/Schema"}},{"id":"ServiceProviderConfig","name":"ServiceProviderConfig","description":"the service providers configuration","endpoint":"/ServiceProviderConfig","schema":"urn:ietf:params:scim:schemas:core:2.0:ServiceProviderConfig","schemas":["urn:ietf:params:scim:schemas:core:2.0:ResourceType","urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures"],"urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures":{"singletonEndpoint":true,"autoFiltering":false,"autoSorting":false,"endpointControl":{"disableCreate":true,"disableList":true,"disableUpdate":true,"disableDelete":true},"authorization":{"authenticated":false}},"meta":{"resourceType":"ResourceType","created":"2019-10-18T12:51:11Z","lastModified":"2019-10-18T12:51:11Z","location":"http://localhost:18081/realms/testRealm/scim/v2/ResourceTypes/ServiceProviderConfig"}},{"id":"ResourceType","name":"ResourceType","description":"ResourceType","endpoint":"/ResourceTypes","schema":"urn:ietf:params:scim:schemas:core:2.0:ResourceType","schemaExtensions":[{"schema":"urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures","required":false}],"schemas":["urn:ietf:params:scim:schemas:core:2.0:ResourceType","urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures"],"urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures":{"singletonEndpoint":false,"autoFiltering":true,"autoSorting":true,"authorization":{"authenticated":false}},"meta":{"resourceType":"ResourceType","created":"2019-10-18T12:51:11Z","lastModified":"2019-10-18T12:51:11Z","location":"http://localhost:18081/realms/testRealm/scim/v2/ResourceTypes/ResourceType"}},{"id":"User","name":"User","description":"User Account","endpoint":"/Users","schema":"urn:ietf:params:scim:schemas:core:2.0:User","schemaExtensions":[{"schema":"urn:ietf:params:scim:schemas:extension:enterprise:2.0:User","required":false}],"schemas":["urn:ietf:params:scim:schemas:core:2.0:ResourceType","urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures"],"urn:gold:params:scim:schemas:extension:url:2.0:ResourceTypeFeatures":{"autoFiltering":false,"autoSorting":false,"etag":{"enabled":false},"endpointControl":{"disableCreate":false,"disableGet":false,"disableList":false,"disableUpdate":false,"disableDelete":false},"authorization":{"authenticated":true,"useOrOnRoles":false}},"meta":{"resourceType":"ResourceType","created":"2023-10-29T21:31:15.899942Z","lastModified":"2023-10-29T21:31:15.899942Z","location":"http://localhost:18081/realms/testRealm/scim/v2/ResourceTypes/User"}}]}* Connection #0 to host localhost left intact

ってことはトークンはちゃんと発行できてるってことか

設定値
ResourceTypes.Authorization.Authentication off

< HTTP/1.1 200 OK
< Referrer-Policy: no-referrer
< Strict-Transport-Security: max-age=31536000; includeSubDomains
< X-XSS-Protection: 1; mode=block
< X-Content-Type-Options: nosniff
< Content-Type: application/scim+json
< content-length: 484
<
{"schemas":["urn:ietf:params:scim:api:messages:2.0:ListResponse"],"totalResults":1,"itemsPerPage":1,"startIndex":1,"Resources":[{"schemas":["urn:ietf:params:scim:schemas:core:2.0:User"],"id":"423a3558-e403-442f-9ec9-20c93be223d1","userName":"login_user","active":true,"meta":{"resourceType":"User","created":"2023-10-29T17:13:07.819Z","lastModified":"2023-10-29T17:13:07.819Z","location":"http://localhost:18081/realms/testRealm/scim/v2/Users/423a3558-e403-442f-9ec9-20c93be223d1"}}]}* Connection #0 to host localhost left intact

ログを出力

cd /opt/keycloak/bin
./kc.sh start --log="console,file"

アクセストークン

JWT形式
HEADER.PAYLOAD.SIGNATURE
それぞれの部分をBase64でエンコードしている

エラー情報

./kc.sh start-dev
下記エラー
ERROR: Unexpected error when starting the server in (production) mode
ERROR: Failed to start quarkus
ERROR: Strict hostname resolution configured but no hostname setting provided
For more details run the same command passing the '--verbose' option. Also you can use '--help' to see the details about the usage of the particular command.
→どうやらhttps化などが必要のようなので、開発者モードで起動するstart-dev
https://www.mastertheboss.com/keycloak/getting-started-with-keycloak-powered-by-quarkus/

認証フロー

OAuth 2.0承認フレームワーク(RFC6749)にて定義されている。

用語

clients Keycloakにユーザの認証を要求できるエンティティ(オブジェクト)。SSOを利用したいアプリケーション。また、アクセストークンを要求するクライアントとしても機能する。
IDtoken
Access token
OIDC OpenID Connectの略

"token_type":"bearer",

Discussion