標準のwildflyベースのKeycloakアダプターを使用して、Keycloakでエンタープライズアプリケーションを保護しました。私が直面している問題は、残りのWebサービスが呼び出されたときに、現在ログインしているユーザー名を知る必要があるということです。Keycloakからログインユーザー情報を取得するにはどうすればよいですか?
SecurityContext
、WebListener
などを使用してみましたが、どれも必要な詳細を提供できません。
セキュリティコンテキストからすべてのユーザー情報を取得します。
例:
public class Greeter {
@Context
SecurityContext sc;
@GET
@Produces(MediaType.APPLICATION_JSON)
public String sayHello() {
// this will set the user id as userName
String userName = sc.getUserPrincipal().getName();
if (sc.getUserPrincipal() instanceof KeycloakPrincipal) {
KeycloakPrincipal<KeycloakSecurityContext> kp = (KeycloakPrincipal<KeycloakSecurityContext>) sc.getUserPrincipal();
// this is how to get the real userName (or rather the login name)
userName = kp.getKeycloakSecurityContext().getIdToken().getPreferredUsername();
}
return "{ message : \"Hello " + userName + "\" }";
}
セキュリティコンテキストを伝播するには、次の説明に従ってセキュリティドメインを構成する必要があります。 JBoss/Wildfly Adapter configuration
また、Webアプリのprincipal-attribute
ファイルのkeycloak.json
プロパティをpreferred_username
に設定することもできます。
Standalone.xmlを次の行に追加する必要があります:
<principal-attribute>preferred_username</principal-attribute>
例:
<subsystem xmlns="urn:jboss:domain:keycloak:1.1">
<secure-deployment name="war-name.war">
<realm>realm-name</realm>
<resource>resource-name</resource>
<public-client>true</public-client>
<auth-server-url>https://keycloak-hostname/auth</auth-server-url>
<ssl-required>EXTERNAL</ssl-required>
<principal-attribute>preferred_username</principal-attribute>
</secure-deployment>
</subsystem>
Keycloak 3.4.3では(以前のバージョンでも動作する可能性があります)、ユーザー名をsub
トークンのクレーム名にマップできました。 Keycloak管理インターフェイスから、これはClients > [your-client] > Mappers > username
で行われ、Token Claim Name
フィールドにsub
と入力します。これには、 other answer のようにクライアント側を調整するのではなく、Keycloakによって返されるID token
の内容を実際に変更するという利点があります。これは、Keycloakが提供するアダプターではなく標準のOpenID Connectライブラリを使用している場合に特に便利です。
私の場合、このようにトークンから優先ユーザー名を取得していました
keycloakPrincipal.getKeycloakSecurityContext().getToken();
token.getPreferredUsername();
機能するために、キークロークに行ってクライアントテンプレートにビルトインを追加する必要がありました。
組み込み、クライアントテンプレート->マッパーのユーザー名を確認します。
うまくいったらその後!