私はundertow、jersey、およびCDIを使用してセットアップした残りのエンドポイントでロールベースのアクセス制御を有効にしようとしています。次のように私は、サーブレットの配備を初期化します。Undertowサーブレットハンドラが既に認証された有効なSecurityContextをキークローンによって管理されています
DeploymentInfo servletBuilder = Servlets.deployment()
.setClassLoader(Main.class.getClassLoader())
.setContextPath("/rest")
.setDeploymentName("sv.war")
.addListeners(listener(Listener.class))
.setLoginConfig(new LoginConfig("KEYCLOAK", "some-realm"))
.setAuthorizationManager(auth) // my dummy for testing
.addServlets(servlet("jerseyServlet", ServletContainer.class)
.setLoadOnStartup(1)
.addInitParam("javax.ws.rs.Application", SystemViewApplication.class.getName())
.addMapping("/api/*"));
私はthis example codeに基づいkecloakの認証を可能にしました。
だから、私のサーバーは次のように開始されます。
二つの方法sessionHandling()
と
addSecurity()
が、私は上記のリンクした例から持ち上げている
DeploymentManager manager = Servlets.defaultContainer().addDeployment(servletBuilder);
manager.deploy();
PathHandler path = Handlers.path(Handlers.resource(staticResources).setDirectoryListingEnabled(false).setWelcomeFiles("index.html"))
.addPrefixPath("/rest", manager.start());
Undertow server = Undertow.builder()
.addHttpListener(8087, "localhost")
.setHandler(sessionHandling(addSecurity(exchange -> {
final SecurityContext context = exchange.getSecurityContext();
if (!context.isAuthenticated()) {
exchange.endExchange();
return;
}
log.info("Authenticated: {} {} {}", context.getMechanismName(), context.getAuthenticatedAccount().getPrincipal().getName(), context.getAuthenticatedAccount().getRoles());
// propagate the request
path.handleRequest(exchange);
})))
.build();
server.start();
。
認証が動作し、強制的にログインし、Authenticated: ..
ロギングラインが正しい詳細で出力されます。しかし、いったんサーブレット処理に当たれば、セキュリティコンテキスト(およびアカウント)は失われます。この呼び出しをたどったところ、パスに沿ったある時点で、ヌルアカウントを持つ新しいSecurityContext
に置き換えられました。
私の質問 - キークローキ認証後に状態を伝播するいくつかの認証メカニズムがありますか、またはアンダートコードを修正できますか?SecurityContext
で、渡されたコンテキストがすでに正しく認証されているその状態と移動? (サーブレットデプロイメントの認証が異なる可能性があるため、後者は正しいとは思えません)もしそうなら、サーブレットデプロイメントを接続して、すでにキークローキ認証が行われていることを確認する方法はありますか?