Closed GuliyevFarid closed 1 year ago
@GuliyevFarid please see some background information here: #1716
For a WAR example, please see https://github.com/ops4j/org.ops4j.pax.web/tree/web-8.0.20/samples/samples-war/war-keycloak - it is a WAR with /WEB-INF/keycloak.json
embedded and related realm configuration is available in src/main/config/PaxWeb-realm-export.json
.
And before I see your setup (or find some time this week to check it myself on pure Karaf 4.4.x), here's a documented example using Red Hat Fuse 7.12 (which is based on Karaf 4.4.x): https://github.com/jboss-fuse/karaf-quickstarts/tree/7.x.redhat-7-x/security/keycloak/keycloak-cxf org.ops4j.pax.web.context-cxf.cfg contains the factory PID with necessary configuration.
Please check it and if this still doesn't work, let me know - I'll try to help here.
Thanks a lot for your reply.
Just would like to mention that, I use keycloak with undertow container almost 4 years and it works very well. I have configured the security with context URLs and ROLEs using whiteboard. As karaf version is upgraded, so I had to upgrade my servers as well. Now I use karaf 4.4.3 and pax-web 8.0.20.
This time, I tried a lot, to integrate keycloak adapter with jetty container. But it did not work at all.
Next I tried to install undertow container using cxf-http-undertow. After disabling the SSL in pax-web configuration, finally I was able to run undertow container and my services.
Now, I try again install keycloak adapter and configure my security via context. For this, I tried to install keycloak-osgi-adapter (to use HierarchicalPathBasedKeycloakConfigResolver), but unfortunately that bundle requires http-whiteboard till version 8. But in karaf 4.4.3, the version is 8.0.20. So, I cannot use that configresolver for the keycloak.
After that, I tried to install the pax-web-undertow-keycloak18. The installation of the bundle was successful. But as soon as I add pax-web configuration for my contexts, the services return HTTP 404, even /services context.
I checked the logs and saw that karaf stops undertow context "/" and does not start that again, so, I receive 404. ERROR in karaf: Stopping Undertow context "/"
Now, the first problem is that, I want to use hierarchical path based config resolver, but due to version cannot use that. How can I solve that issue? The second problem is that as soon as there is a pax-web configuration, undertow container stops. how can I fix that issue? The third, if there is still a possibility to use keycloak with jetty container, using whiteboard context security configuration?
NOTE: I have read all the above links that you mentioned. As I mentioned, my purpose is to set up a general security layer via whiteboard, so, all deployed services under predefined contexts will require authentication and authorization.
For this, I tried to install keycloak-osgi-adapter (to use HierarchicalPathBasedKeycloakConfigResolver), but unfortunately that bundle requires http-whiteboard till version 8.
keycloak-osgi-adapter version 18 has this import:
Import-Package: org.ops4j.pax.web.service;version="[3.0,8)"
This is special commit for Keycloak 18 where I export relevant package at the version expected by Keycloak (the interface used by Keycloak didn't change): 596577b106a811cbcb2864e9ce4d7475c62eeb45 and it's available since pax-web 8.0.16:
$ git tag --contains 596577b106a811cbcb2864e9ce4d7475c62eeb45
web-8.0.16
web-8.0.17
web-8.0.18
web-8.0.19
web-8.0.20
web-8.0.21
web-8.0.22
as soon as I add pax-web configuration for my contexts, the services return HTTP 404, even /services context.
I'd have to see more logs to check what has happened. With https://github.com/jboss-fuse/karaf-quickstarts/tree/7.x.redhat-7-x/security/keycloak/keycloak-cxf I checked Keycloak 18 and Pax Web 8 and it worked, so I'll be happy to help here.
The commit you have mentioned is related to Jetty+Keycloak18 integration.
When I try to do that integration, I do the following steps:
I check the current installed jetty bundles:
Next I start to install the keycloak features for version 18.
feature:repo-add mvn:org.keycloak/keycloak-osgi-features/18.0.2/xml/features
Next I install pax-web-jetty-keycloak18
feature:install pax-web-jetty-keycloak18
And it is successfully installed.
Next I add new file into etc folder: org.ops4j.pax.web.context-services.cfg with the following content:
bundle.symbolicName = org.apache.cxf.cxf-rt-transports-http
context.id = default
context.param.keycloak.config.resolver = org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
login.config.authMethod = KEYCLOAK
security.services.common.url = /services/*
security.services.common.roles = admin, user
In the log I see the following issue with Keycloak:
2023-09-19T17:47:01,640 | INFO | paxweb-context-7-thread-1 | extProcessing$HttpContextTracker 408 | 318 - org.ops4j.pax.web.pax-web-runtime - 8.0.20 | Registering login configuration in OsgiContextModel{HS,id=OCM-58,name='default',path='/',bundle=org.apache.cxf.cxf-rt-transports-http,context=DefaultHttpContext{bundle=org.apache.cxf.cxf-rt-transports-http_3.5.6 [182],contextId='default'}}: method=KEYCLOAK, realm=default
2023-09-19T17:47:01,641 | INFO | paxweb-context-7-thread-1 | extProcessing$HttpContextTracker 427 | 318 - org.ops4j.pax.web.pax-web-runtime - 8.0.20 | Registering security mappings in OsgiContextModel{HS,id=OCM-58,name='default',path='/',bundle=org.apache.cxf.cxf-rt-transports-http,context=DefaultHttpContext{bundle=org.apache.cxf.cxf-rt-transports-http_3.5.6 [182],contextId='default'}}
2023-09-19T17:47:01,643 | INFO | paxweb-config-1-thread-1 | y.internal.JettyServerController 162 | 317 - org.ops4j.pax.web.pax-web-jetty - 8.0.20 | Receiving Batch{"Processing context "default" for bundle org.apache.cxf.cxf-rt-transports-http", size=4}
2023-09-19T17:47:01,643 | INFO | paxweb-config-1-thread-1 | etty.internal.JettyServerWrapper 2078 | 317 - org.ops4j.pax.web.pax-web-jetty - 8.0.20 | Stopping Jetty context "/"
2023-09-19T17:47:01,644 | INFO | paxweb-config-1-thread-1 | etty.internal.JettyServerWrapper 2091 | 317 - org.ops4j.pax.web.pax-web-jetty - 8.0.20 | Adding init parameters to OsgiContextModel{HS,id=OCM-58,name='default',path='/',bundle=org.apache.cxf.cxf-rt-transports-http,context=DefaultHttpContext{bundle=org.apache.cxf.cxf-rt-transports-http_3.5.6 [182],contextId='default'}}: {keycloak.config.resolver=org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver}
2023-09-19T17:47:01,644 | INFO | paxweb-config-1-thread-1 | etty.internal.JettyServerWrapper 2109 | 317 - org.ops4j.pax.web.pax-web-jetty - 8.0.20 | Adding security configuration to OsgiContextModel{HS,id=OCM-58,name='default',path='/',bundle=org.apache.cxf.cxf-rt-transports-http,context=DefaultHttpContext{bundle=org.apache.cxf.cxf-rt-transports-http_3.5.6 [182],contextId='default'}}
2023-09-19T17:47:01,645 | INFO | paxweb-config-1-thread-1 | etty.internal.JettyServerWrapper 2173 | 317 - org.ops4j.pax.web.pax-web-jetty - 8.0.20 | Starting Jetty context "/" with default Osgi Context OsgiContextModel{HS,id=OCM-51,name='default',path='/',bundle=org.apache.karaf.webconsole.console,context=DefaultHttpContext{bundle=org.apache.karaf.webconsole.console_4.4.3.20230726 [241],contextId='default'}}
2023-09-19T17:47:01,655 | INFO | paxweb-config-1-thread-1 | stractKeycloakJettyAuthenticator 240 | 580 - org.keycloak.keycloak-jetty-core - 18.0.2 | The specified resolver org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver could NOT be loaded. Keycloak is unconfigured and will deny all requests. Reason: org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
2023-09-19T17:47:01,662 | INFO | paxweb-config-1-thread-1 | nternal.web.JettyResourceServlet 75 | 317 - org.ops4j.pax.web.pax-web-jetty - 8.0.20 | Initialized Jetty Resource Servlet for base="res" with cache maxSize=4096kB, maxEntrySize=2048kB, maxEntries=2048
2023-09-19T17:47:16,646 | INFO | fileinstall-/opt/TalendRuntime-8.0.1-R2023-08-RT/runtime/etc | install.internal.Util$OsgiLogger 205 | 18 - org.apache.felix.fileinstall - 3.7.4 | Removing READ_ONLY attribute from configuration {org.ops4j.pax.web.context~services} from /opt/TalendRuntime-8.0.1-R2023-08-RT/runtime/etc/org.ops4j.pax.web.context-services.cfg
ERROR: The specified resolver org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver could NOT be loaded. Keycloak is unconfigured and will deny all requests. Reason: org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
this check is within pax-web-jetty-keycloak
if (this.configResolver == null && theServletContext != null) {
String configResolverClass = theServletContext.getInitParameter("keycloak.config.resolver");
if (configResolverClass != null)
try {
this.configResolver = (KeycloakConfigResolver)ContextHandler.getCurrentContext().getClassLoader().loadClass(configResolverClass).newInstance();
log.infov("Using {0} to resolve Keycloak configuration on a per-request basis.", configResolverClass);
} catch (Exception ex) {
log.infov("The specified resolver {0} could NOT be loaded. Keycloak is unconfigured and will deny all requests. Reason: {1}", new Object[] { configResolverClass, ex.getMessage() });
}
}
As it cannot find required resolver, (which is part of keycloak-osgi-adapter) so I try to install that specific bundle.
feature:install keycloak-osgi-adapter
And it fails.
As my current http-whiteboard is version 8.0.20.
As you said that it works for you the Jetty+Keycloak integration, so, do I miss something there?
When I try to do the Undertow+Keycloak integration, based on the link that you provided: https://github.com/jboss-fuse/karaf-quickstarts/tree/7.x.redhat-7-x/security/keycloak/keycloak-cxf
I do the following steps:
I install required undertow features
Next I install keycloak as mentioned in the documentation that you sent.
feature:repo-add mvn:org.keycloak/keycloak-osgi-features/18.0.2/xml/features
feature:install -v keycloak-pax-http-undertow
In this case, installation of keycloak-pax-http-undertow stuck and does not continue. In the logs I found the following conflict
2023-09-19T18:12:21,635 | DEBUG | features-2-thread-1 | ternal.resolver.Slf4jResolverLog 45 | 19 - org.apache.karaf.features.core - 4.4.3 | Candidate permutation failed due to a conflict between imports; will try another if possible. (Uses constraint violation. Unable to resolve resource org.ops4j.pax.web.pax-web-undertow [org.ops4j.pax.web.pax-web-undertow/8.0.20] because it is exposed to package 'io.undertow.connector' from resources io.undertow.core [io.undertow.core/2.2.24.Final] and io.undertow.core [io.undertow.core/1.4.28.Final] via two dependency chains.
Chain 1:
org.ops4j.pax.web.pax-web-undertow [org.ops4j.pax.web.pax-web-undertow/8.0.20]
import: (&(osgi.wiring.package=io.undertow.connector)(version>=2.2.0)(!(version>=3.0.0)))
|
export: osgi.wiring.package: io.undertow.connector
io.undertow.core [io.undertow.core/2.2.24.Final]
Chain 2:
org.ops4j.pax.web.pax-web-undertow [org.ops4j.pax.web.pax-web-undertow/8.0.20]
import: (&(osgi.wiring.package=org.keycloak.adapters.undertow)(version>=18.0.2))
|
export: osgi.wiring.package=org.keycloak.adapters.undertow; uses:=io.undertow.security.api
org.keycloak.keycloak-undertow-adapter [org.keycloak.keycloak-undertow-adapter/18.0.2]
import: (&(osgi.wiring.package=io.undertow.security.api)(version>=1.4.0)(!(version>=3.0.0)))
|
export: osgi.wiring.package: io.undertow.security.api; uses:=io.undertow.connector
export: osgi.wiring.package=io.undertow.connector
io.undertow.core [io.undertow.core/1.4.28.Final])
I do not know why there is a conflict. could you tell me which part I do incorrect, please?
Thanks for the details - I already see you have ancient Undertow 1.4.28 bundle installed, but I'll check more (and maybe update the quickstarts) tomorrow, or later this week...
Thanks for the details - I already see you have ancient Undertow 1.4.28 bundle installed, but I'll check more (and maybe update the quickstarts) tomorrow, or later this week...
any news on that topic?
I'm sorry @GuliyevFarid but I have a lot of work recently. I'd have to setup full example and Keycloak server to check it on Jetty/Tomcat/Undertow. I will do it, but not immediately.
In the meantime - can you check where did you get Undertow 1.4.28 from?
Checking with Karaf 4.4.4, Pax Web 8.0.22 and CXF 3.5.5
karaf@root()> repo-add mvn:org.apache.karaf.examples/karaf-rest-example-features/4.4.4/xml
Adding feature url mvn:org.apache.karaf.examples/karaf-rest-example-features/4.4.4/xml
karaf@root()> feature:install karaf-rest-example-blueprint
karaf@root()> la -l | grep pax
4 │ Active │ 5 │ 2.6.14 │ mvn:org.ops4j.pax.url/pax-url-aether/2.6.14
5 │ Active │ 8 │ 2.2.3 │ mvn:org.ops4j.pax.logging/pax-logging-log4j2/2.2.3
7 │ Active │ 8 │ 2.2.3 │ mvn:org.ops4j.pax.logging/pax-logging-api/2.2.3
51 │ Active │ 10 │ 2.6.14 │ mvn:org.ops4j.pax.url/pax-url-wrap/2.6.14/jar/uber
113 │ Active │ 30 │ 8.0.22 │ mvn:org.ops4j.pax.web/pax-web-api/8.0.22
114 │ Resolved │ 30 │ 8.0.22 │ mvn:org.ops4j.pax.web/pax-web-compatibility-servlet31/8.0.22
115 │ Active │ 30 │ 8.0.22 │ mvn:org.ops4j.pax.web/pax-web-jetty/8.0.22
116 │ Active │ 30 │ 8.0.22 │ mvn:org.ops4j.pax.web/pax-web-runtime/8.0.22
117 │ Active │ 30 │ 8.0.22 │ mvn:org.ops4j.pax.web/pax-web-spi/8.0.22
118 │ Active │ 30 │ 8.0.22 │ mvn:org.ops4j.pax.web/pax-web-tomcat-common/8.0.22
karaf@root()> feature:install pax-web-karaf
karaf@root()> web:servlet-list
Bundle ID │ Name │ Class │ Context Path(s) │ URLs │ Type
──────────┼────────────────────────────┼──────────────────────────────────────────────────────┼─────────────────┼────────┼────────────
78 │ cxf-osgi-transport-servlet │ org.apache.cxf.transport.servlet.CXFNonSpringServlet │ / │ /cxf/* │ HttpService
karaf@root()> web:context-list
Bundle ID │ Symbolic Name │ Context Path │ Context Name │ Rank │ Service ID │ Type │ Scope │ Registration Properties
──────────┼───────────────────────────────────────┼──────────────┼──────────────┼──────┼────────────┼─────────────┼─────────┼─────────────────────────────────────────────────
78 │ org.apache.cxf.cxf-rt-transports-http │ / │ default │ MAX │ 0 │ HttpService │ static* │ httpContext.id=default
│ │ │ │ │ │ │ │ httpContext.path=/
│ │ │ │ │ │ │ │ osgi.http.whiteboard.context.httpservice=default
│ │ │ │ │ │ │ │ osgi.http.whiteboard.context.path=/
*) This context is using ServletContextHelper/HttpContext without resolving an org.osgi.framework.ServiceReference.
As you can see, after installing karaf-rest-example-blueprint
feature, I see pax-web-http-jetty
feature installed (with its relevant bundles).
Does it work?
$ curl -XPOST -H'Content-Type: application/json' --data '{"id":"42","customer":"pax-web","flight":"0000-0001"}' -i http://localhost:8181/cxf/booking
HTTP/1.1 204 No Content
Date: Tue, 26 Sep 2023 14:13:42 GMT
$ curl -i http://localhost:8181/cxf/booking/42
HTTP/1.1 200 OK
Date: Tue, 26 Sep 2023 14:13:48 GMT
Content-Type: application/json
Transfer-Encoding: chunked
{"id":42,"customer":"pax-web","flight":"0000-0001"}[ggrzybek@everfree] /data/servers/apache-karaf-4.4.4
That's the preparation. See more comments soon.
@GuliyevFarid btw, have you seen https://github.com/ops4j/org.ops4j.pax.web/blob/pax-web-8.0.x/pax-web-keycloak/readme.adoc ?
I started fresh Keycloak 22.0.3 server:
$ bin/kc.sh start-dev --http-port 8180
And imported https://github.com/ops4j/org.ops4j.pax.web/blob/pax-web-8.0.x/pax-web-keycloak/realm-export.json as paxweb
realm.
I added cxf
client with "Direct Access Grants" only.
Installed pax-web-jetty-keycloak
feature
karaf@root()> feature:install pax-web-jetty-keycloak
After adding this to etc/org.ops4j.pax.web.context-cxf.cfg
:
bundle.symbolicName = org.apache.cxf.cxf-rt-transports-http
context.id = default
context.param.keycloak.config.resolver = org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
login.config.authMethod = KEYCLOAK
security.cxf.url = /cxf/*
security.cxf.roles = paxweb-admin, paxweb-viewer
And this to etc/keycloak.json
:
{
"realm": "paxweb",
"auth-server-url": "http://localhost:8180/auth",
"ssl-required": "external",
"resource": "cxf",
"use-resource-role-mappings": true,
"confidential-port": 0,
"principal-attribute": "preferred_username",
"bearer-only": true
}
I'm seeing this in logs:
2023-09-26T16:40:44,579 | INFO | paxweb-config-1-thread-1 | JettyServerWrapper | 115 - org.ops4j.pax.web.pax-web-jetty - 8.0.22 | Adding init parameters to OsgiContextModel{HS,id=OCM-16,name='default',path='/',bundle=org.apache.cxf.cxf-rt-transports-http,context=DefaultHttpContext{bundle=org.apache.cxf.cxf-rt-transports-http [78],contextId='default'}}: {keycloak.config.resolver=org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver}
2023-09-26T16:40:44,579 | INFO | paxweb-config-1-thread-1 | JettyServerWrapper | 115 - org.ops4j.pax.web.pax-web-jetty - 8.0.22 | Adding security configuration to OsgiContextModel{HS,id=OCM-16,name='default',path='/',bundle=org.apache.cxf.cxf-rt-transports-http,context=DefaultHttpContext{bundle=org.apache.cxf.cxf-rt-transports-http [78],contextId='default'}}
2023-09-26T16:40:44,580 | INFO | paxweb-config-1-thread-1 | JettyServerWrapper | 115 - org.ops4j.pax.web.pax-web-jetty - 8.0.22 | Starting Jetty context "/" with default Osgi Context OsgiContextModel{HS,id=OCM-16,name='default',path='/',bundle=org.apache.cxf.cxf-rt-transports-http,context=DefaultHttpContext{bundle=org.apache.cxf.cxf-rt-transports-http [78],contextId='default'}}
2023-09-26T16:40:44,590 | INFO | paxweb-config-1-thread-1 | AbstractKeycloakJettyAuthenticator | 115 - org.ops4j.pax.web.pax-web-jetty - 8.0.22 | The specified resolver org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver could NOT be loaded. Keycloak is unconfigured and will deny all requests. Reason: org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
And the reason is that ClassLoader for /
ServletContext sees only 2 bundles:
result = {org.ops4j.pax.web.service.spi.servlet.OsgiServletContextClassLoader@11715}
assertionLock: java.lang.Object = {org.ops4j.pax.web.service.spi.servlet.OsgiServletContextClassLoader@11715}
bundles: java.util.List = {java.util.Collections$UnmodifiableRandomAccessList@11723} size = 2
0 = {org.apache.felix.framework.BundleImpl@11739} "org.apache.cxf.cxf-rt-transports-http [78]"
1 = {org.apache.felix.framework.BundleImpl@11740} "org.ops4j.pax.web.pax-web-jetty [115]"
In Karaf 4.3 and earlier and in Pax Web 7 the classloader management was a bit broken (when talking about compliance with Whiteboard specification) and I don't remember exactly how it worked with Jetty.
Same problem with pax-web-http-undertow
:
result = {org.ops4j.pax.web.service.spi.servlet.OsgiServletContextClassLoader@14008}
assertionLock: java.lang.Object = {org.ops4j.pax.web.service.spi.servlet.OsgiServletContextClassLoader@14008}
bundles: java.util.List = {java.util.Collections$UnmodifiableRandomAccessList@14009} size = 2
0 = {org.apache.felix.framework.BundleImpl@14027} "org.apache.cxf.cxf-rt-transports-http [161]"
1 = {org.apache.felix.framework.BundleImpl@14028} "org.ops4j.pax.web.pax-web-undertow [135]"
To install pax-web-http-undertow
, you have to blacklist pax-web-http-jetty
feature first, by adding this to etc/org.apache.karaf.features.xml
:
<blacklistedFeatures>
<feature>pax-web-http-jetty</feature>
</blacklistedFeatures>
The reason is this chain of feature dependencies: cxf-jaxrs
→ cxf-http
→ http
→ pax-web-http
→ pax-web-http-jetty
And finally the same for pax-web-http-tomcat
:
result = {org.apache.catalina.loader.ParallelWebappClassLoader@17539} "ParallelWebappClassLoader\r\n context: ROOT ...
...
java.lang.ClassLoader.parent: java.lang.ClassLoader = {org.ops4j.pax.web.service.spi.servlet.OsgiServletContextClassLoader@17553}
assertionLock: java.lang.Object = {org.ops4j.pax.web.service.spi.servlet.OsgiServletContextClassLoader@17553}
bundles: java.util.List = {java.util.Collections$UnmodifiableRandomAccessList@17580} size = 2
0 = {org.apache.felix.framework.BundleImpl@17590} "org.apache.cxf.cxf-rt-transports-http [161]"
1 = {org.apache.felix.framework.BundleImpl@17591} "org.ops4j.pax.web.pax-web-tomcat [205]"
Tomorrow I'll check with Keycloak 18.
Here's an answer why it works with Keycloak 18:
bundles: java.util.List = {java.util.Collections$UnmodifiableRandomAccessList@16534} size = 5
0 = {org.apache.felix.framework.BundleImpl@16448} "org.apache.cxf.cxf-rt-transports-http [122]"
1 = {org.apache.felix.framework.BundleImpl@16465} "org.ops4j.pax.web.pax-web-undertow [238]"
...
m_revisions: java.util.List = {java.util.ArrayList@16601} size = 1
0 = {org.apache.felix.framework.BundleRevisionImpl@16602} "org.ops4j.pax.web.pax-web-undertow [238](R 238.0)"
...
m_wiring: org.apache.felix.framework.BundleWiringImpl = {org.apache.felix.framework.BundleWiringImpl@16467} "org.ops4j.pax.web.pax-web-undertow [238]"
...
m_fragments: java.util.List = {java.util.ArrayList@16631} size = 1
0 = {org.apache.felix.framework.BundleRevisionImpl@16800} "org.keycloak.keycloak-pax-web-undertow [256](R 256.0)"
2 = {org.apache.felix.framework.BundleImpl@16591} "org.ops4j.pax.web.pax-web-jsp [233]"
3 = {org.apache.felix.framework.BundleImpl@16592} "io.undertow.websockets-jsr [51]"
4 = {org.apache.felix.framework.BundleImpl@16593} "org.ops4j.pax.web.pax-web-undertow-websocket [239]"
org.keycloak.keycloak-pax-web-undertow
is a fragment attached to org.ops4j.pax.web.pax-web-undertow
bundle:
karaf@root()> la | grep Undertow
...
238 │ Active │ 30 │ 8.0.22 │ OPS4J Pax Web - Undertow, Fragments: 256
...
256 │ Resolved │ 80 │ 18.0.6.redhat-00001 │ Keycloak Fuse 7.0 Adapter - Undertow, Hosts: 238
So org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
is loaded via the fragment content.
I'll do two things:
Rest example feature repo:
karaf@root()> repo-add mvn:org.apache.karaf.examples/karaf-rest-example-features/4.4.4/xml
Adding feature url mvn:org.apache.karaf.examples/karaf-rest-example-features/4.4.4/xml
Jetty:
karaf@root()> feature:install pax-web-http-jetty pax-web-karaf
The example feature:
karaf@root()> feature:install karaf-rest-example-blueprint
karaf@root()> web:servlet-list
Bundle ID │ Name │ Class │ Context Path(s) │ URLs │ Type
──────────┼────────────────────────────┼──────────────────────────────────────────────────────┼─────────────────┼────────┼────────────
99 │ cxf-osgi-transport-servlet │ org.apache.cxf.transport.servlet.CXFNonSpringServlet │ / │ /cxf/* │ HttpService
Keycloak 18 features:
karaf@root()> feature:repo-add mvn:org.keycloak/keycloak-osgi-features/18.0.2/xml/features
Adding feature url mvn:org.keycloak/keycloak-osgi-features/18.0.2/xml/features
karaf@root()> feature:install -v keycloak-adapter-core
Adding features: keycloak-adapter-core/[18.0.2,18.0.2]
Changes to perform:
Region: root
Bundles to install:
mvn:org.apache.httpcomponents/httpclient-osgi/4.5.2
mvn:org.apache.httpcomponents/httpcore-osgi/4.4.4
mvn:org.keycloak/keycloak-adapter-core/18.0.2
mvn:org.keycloak/keycloak-adapter-spi/18.0.2
mvn:org.keycloak/keycloak-authz-client/18.0.2
mvn:org.keycloak/keycloak-common/18.0.2
mvn:org.keycloak/keycloak-core/18.0.2
...
etc/keycloak.json
:
{
"realm": "paxweb",
"auth-server-url": "http://localhost:8180/auth",
"ssl-required": "external",
"resource": "cxf",
"use-resource-role-mappings": true,
"confidential-port": 0,
"principal-attribute": "preferred_username",
"bearer-only": true
}
Jetty bundles (because there's no proper Keycloak feature related to Jetty):
karaf@root()> install mvn:org.keycloak/keycloak-osgi-adapter/18.0.2
Bundle ID: 130
karaf@root()> install mvn:org.keycloak/keycloak-jetty-adapter-spi/18.0.2
Bundle ID: 131
karaf@root()> install mvn:org.keycloak/keycloak-jetty-core/18.0.2
Bundle ID: 132
karaf@root()> install mvn:org.keycloak/keycloak-jetty94-adapter/18.0.2
Bundle ID: 133
karaf@root()> install mvn:org.keycloak/keycloak-pax-web-jetty94/18.0.2
Bundle ID: 134
etc/org.ops4j.pax.web.context-cxf.cfg
:
bundle.symbolicName = org.apache.cxf.cxf-rt-transports-http
context.id = default
context.param.keycloak.config.resolver = org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
login.config.authMethod = KEYCLOAK
security.cxf.url = /cxf/*
security.cxf.roles = paxweb-admin, paxweb-viewer
However I see the same problem again:
2023-09-27T10:56:54,624 | INFO | paxweb-config-1-thread-1 | AbstractKeycloakJettyAuthenticator | 132 - org.keycloak.keycloak-jetty-core - 18.0.2 | The specified resolver org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver could NOT be loaded. Keycloak is unconfigured and will deny all requests. Reason: org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
The reason is that org.keycloak.keycloak-pax-web-jetty94
fragment attached to pax-web-jetty
bundle doesn't have org.keycloak.adapters.osgi
import:
m_fragments: java.util.List = {java.util.ArrayList@10911} size = 1
0 = {org.apache.felix.framework.BundleRevisionImpl@10926} "org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)"
m_activationExcludes: java.util.List = null
m_activationIncludes: java.util.List = null
m_bundle: org.apache.felix.framework.BundleImpl = {org.apache.felix.framework.BundleImpl@10935} "org.keycloak.keycloak-pax-web-jetty94 [134]"
m_content: org.apache.felix.framework.cache.Content = {org.apache.felix.framework.cache.JarContent@10936} "JAR /data/servers/apache-karaf-4.4.4/data/cache/bundle134/version0.0/bundle.jar"
m_contentPath: java.util.List = null
m_declaredActivationPolicy: int = 0
m_declaredCaps: java.util.List = {java.util.ArrayList@10933} size = 2
m_declaredNativeLibs: java.util.List = null
m_declaredReqs: java.util.List = {java.util.ArrayList@10934} size = 10
0 = {org.apache.felix.framework.wiring.BundleRequirementImpl@10945} "[org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)] osgi.wiring.host; (&(osgi.wiring.host=org.ops4j.pax.web.pax-web-jetty)(bundle-version>=0.0.0))"
1 = {org.apache.felix.framework.wiring.BundleRequirementImpl@10946} "[org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)] osgi.wiring.package; (&(osgi.wiring.package=org.eclipse.jetty.security)(version>=9.4.0)(!(version>=10.0.0)))"
2 = {org.apache.felix.framework.wiring.BundleRequirementImpl@10947} "[org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)] osgi.wiring.package; (&(osgi.wiring.package=org.eclipse.jetty.util.security)(version>=9.4.0)(!(version>=10.0.0)))"
3 = {org.apache.felix.framework.wiring.BundleRequirementImpl@10948} "[org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)] osgi.wiring.package; (&(osgi.wiring.package=org.jboss.logging)(version>=3.4.0)(!(version>=4.0.0)))"
4 = {org.apache.felix.framework.wiring.BundleRequirementImpl@10949} "[org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)] osgi.wiring.package; (&(osgi.wiring.package=org.keycloak.adapters.jetty)(version>=18.0.2))"
5 = {org.apache.felix.framework.wiring.BundleRequirementImpl@10950} "[org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)] osgi.wiring.package; (&(osgi.wiring.package=org.ops4j.pax.web.service)(version>=7.1.0)(!(version>=9.0.0)))"
6 = {org.apache.felix.framework.wiring.BundleRequirementImpl@10951} "[org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)] osgi.wiring.package; (&(osgi.wiring.package=org.ops4j.pax.web.service.spi.model)(version>=7.1.0)(!(version>=9.0.0)))"
7 = {org.apache.felix.framework.wiring.BundleRequirementImpl@10952} "[org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)] osgi.wiring.package; (&(osgi.wiring.package=org.osgi.framework)(version>=1.5.0)(!(version>=2.0.0)))"
8 = {org.apache.felix.framework.wiring.BundleRequirementImpl@10953} "[org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)] osgi.wiring.package; (&(osgi.wiring.package=org.osgi.service.http)(version>=1.2.0)(!(version>=2.0.0)))"
9 = {org.apache.felix.framework.wiring.BundleRequirementImpl@10954} "[org.keycloak.keycloak-pax-web-jetty94 [134](R 134.0)] osgi.wiring.package; (&(osgi.wiring.package=org.osgi.util.tracker)(version>=1.4.0)(!(version>=2.0.0)))"
I tried to fix it with https://issues.redhat.com/browse/KEYCLOAK-19939 and didn't review it when implementing it in Pax Web itself.
However if you create a fragment attached to org.ops4j.pax.web.pax-web-jetty
bundle with additional:
Import-Package: org.keycloak.adapters.osgi
it should work.
Checking with Tomcat now.
Add this to etc/org.apache.karaf.features.xml
:
<blacklistedFeatures>
<feature>pax-web-jetty</feature>
<feature>pax-web-http-jetty</feature>
</blacklistedFeatures>
Switch from Jetty to Tomcat (based on setup from previous comment):
karaf@root()> uninstall org.keycloak.keycloak-jetty-adapter-spi
karaf@root()> uninstall org.keycloak.keycloak-jetty-core
karaf@root()> uninstall org.keycloak.keycloak-jetty94-adapter
karaf@root()> uninstall org.keycloak.keycloak-pax-web-jetty94
karaf@root()> feature:refresh
karaf@root()> feature:install pax-web-tomcat-keycloak18
4 previous Jetty related bundles from Keycloak are now replaced with 1 Pax Web related pax-web-tomcat-keycloak18
feature to fix OSGi problems on Keycloak side.
However the problem is still there:
2023-09-27T11:06:39,808 | ERROR | paxweb-config-1-thread-1 | AbstractKeycloakAuthenticatorValve | 136 - org.ops4j.pax.web.pax-web-tomcat - 8.0.22 | The specified resolver org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver could NOT be loaded. Keycloak is unconfigured and will deny all requests. Reason: org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
However I could easily fix this on Pax Web side and get:
2023-09-27T11:15:00,929 | DEBUG | paxweb-config-1-thread-1 | AbstractKeycloakAuthenticatorValve | 136 - org.ops4j.pax.web.pax-web-tomcat - 8.0.22 | Using org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver to resolve Keycloak configuration on a per-request basis.
With my little fix, I could get proper Keycloak response:
$ curl -XPOST -H'Content-Type: application/json' --data '{"id":"42","customer":"pax-web","flight":"0000-0001"}' -i http://localhost:8181/cxf/booking
HTTP/1.1 401
WWW-Authenticate: Bearer realm="paxweb"
Content-Type: text/html;charset=utf-8
Content-Language: en
Content-Length: 686
Date: Wed, 27 Sep 2023 09:16:27 GMT
Checking with Undertow.
karaf@root()> feature:uninstall pax-web-tomcat-keycloak18
karaf@root()> feature:uninstall pax-web-http-tomcat
karaf@root()> feature:install pax-web-http-undertow
karaf@root()> feature:install pax-web-undertow-keycloak18
And it should work out of the box. Logs:
2023-09-27T11:24:13,176 | INFO | paxweb-config-1-thread-1 | KeycloakServletExtension | 153 - org.keycloak.keycloak-undertow-adapter - 18.0.2 | Using org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver to resolve Keycloak configuration on a per-request basis.
Request:
$ curl -XPOST -H'Content-Type: application/json' --data '{"id":"42","customer":"pax-web","flight":"0000-0001"}' -i http://localhost:8181/cxf/booking
HTTP/1.1 401 Unauthorized
Expires: 0
Connection: keep-alive
WWW-Authenticate: Bearer realm="paxweb"
Cache-Control: no-cache, no-store, must-revalidate
Pragma: no-cache
Content-Type: text/html;charset=UTF-8
Content-Length: 71
Date: Wed, 27 Sep 2023 09:24:45 GMT
<html><head><title>Error</title></head><body>Unauthorized</body></html>
So I agree:
Import-Package: org.keycloak.adapters.osgi
- however I can fix all 3 on Pax Web side.Without using org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
, everything should work - see:
samples/samples-whiteboard/whiteboard-security
sample has proper:
<Import-Package>
...
<!-- Needed to use org.keycloak.adapters.osgi.PathBasedKeycloakConfigResolver -->
org.keycloak.adapters.osgi;version="[18,22)";resolution:=optional
</Import-Package>
So the problems with CXF are not occurring.
@grgrzybek thanks a lot. I will check and proceed with the instructions you mentioned for Pax Web + Undertow + Keycloak 18.
@grgrzybek I have checked Pax Web + Undertow + Keycloak 18 integration using your instructions, and it worked for me. I was missing the following command to install the bundle, which was crucial for Configresolver.
karaf@root()> install mvn:org.keycloak/keycloak-osgi-adapter/18.0.2
Thanks a lot. this solved my problem.
It would also be great to have Pax Web + Jetty + Keycloak 18 integration.
Thanks a lot. this solved my problem.
Great to hear!
It would also be great to have Pax Web + Jetty + Keycloak 18 integration.
I'm afraid it'll be much easier to simply fix Pax Web + Jetty/Tomcat/Undertow on latest Keycloak version (which dropped Pax Web support) than to fix it for Keycloak 18 - but I'll see what can I do.
Another instruction for pax-web-jetty after new fixes:
Start with fresh Karaf 4.4.4.
Rest example feature repo:
karaf@root()> repo-add mvn:org.apache.karaf.examples/karaf-rest-example-features/4.4.4/xml
Adding feature url mvn:org.apache.karaf.examples/karaf-rest-example-features/4.4.4/xml
Jetty:
karaf@root()> feature:install pax-web-http-jetty pax-web-karaf
The example feature:
karaf@root()> feature:install karaf-rest-example-blueprint
karaf@root()> web:servlet-list
Bundle ID │ Name │ Class │ Context Path(s) │ URLs │ Type
──────────┼────────────────────────────┼──────────────────────────────────────────────────────┼─────────────────┼────────┼────────────
99 │ cxf-osgi-transport-servlet │ org.apache.cxf.transport.servlet.CXFNonSpringServlet │ / │ /cxf/* │ HttpService
Keycloak 18 features:
karaf@root()> feature:repo-add mvn:org.keycloak/keycloak-osgi-features/18.0.2/xml/features
Adding feature url mvn:org.keycloak/keycloak-osgi-features/18.0.2/xml/features
Now new pax-web-jetty-keycloak18
feature:
karaf@root()> feature:install -v -t pax-web-jetty-keycloak18
Adding features: pax-web-jetty-keycloak18/[8.0.23.SNAPSHOT,8.0.23.SNAPSHOT]
Changes to perform:
Region: root
Bundles to update:
org.eclipse.jetty.servlet/9.4.52.v20230823 with mvn:org.eclipse.jetty/jetty-servlet/9.4.53.v20231009
org.eclipse.jetty.servlets/9.4.52.v20230823 with mvn:org.eclipse.jetty/jetty-servlets/9.4.53.v20231009
org.eclipse.jetty.io/9.4.52.v20230823 with mvn:org.eclipse.jetty/jetty-io/9.4.53.v20231009
...
Bundles to install:
mvn:org.apache.httpcomponents/httpclient-osgi/4.5.14
mvn:org.apache.httpcomponents/httpcore-osgi/4.4.16
mvn:org.keycloak/keycloak-adapter-core/18.0.2
mvn:org.keycloak/keycloak-adapter-spi/18.0.2
mvn:org.keycloak/keycloak-authz-client/18.0.2
mvn:org.keycloak/keycloak-common/18.0.2
mvn:org.keycloak/keycloak-core/18.0.2
mvn:org.keycloak/keycloak-osgi-adapter/18.0.2
mvn:org.ops4j.pax.web/pax-web-jetty-keycloak18/8.0.23-SNAPSHOT
This is a new feature which should be installed instead of separate Keycloak bundles. It includes only one bundle now: pax-web-jetty-keycloak18
which repackages Keycloak 18 bundles and adds required import to find org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
.
etc/keycloak.json
:
{
"realm": "paxweb",
"auth-server-url": "http://localhost:8180/auth",
"ssl-required": "external",
"resource": "cxf",
"use-resource-role-mappings": true,
"confidential-port": 0,
"principal-attribute": "preferred_username",
"bearer-only": true
}
etc/org.ops4j.pax.web.context-cxf.cfg
:
bundle.symbolicName = org.apache.cxf.cxf-rt-transports-http
context.id = default
context.param.keycloak.config.resolver = org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
login.config.authMethod = KEYCLOAK
security.cxf.url = /cxf/*
security.cxf.roles = paxweb-admin, paxweb-viewer
Now I see:
2023-10-11T15:14:52,745 | INFO | paxweb-config-1-thread-1 | JettyServerWrapper | 69 - org.ops4j.pax.web.pax-web-jetty - 8.0.22 | Starting Jetty context "/" with default Osgi Context OsgiContextModel{HS,id=OCM-4,name='default',path='/',bundle=org.apache.cxf.cxf-rt-transports-http,context=DefaultHttpContext{bundle=org.apache.cxf.cxf-rt-transports-http [99],contextId='default'}}
2023-10-11T15:14:52,969 | INFO | paxweb-config-1-thread-1 | AbstractKeycloakJettyAuthenticator | 69 - org.ops4j.pax.web.pax-web-jetty - 8.0.22 | Using org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver to resolve Keycloak configuration on a per-request basis.
2023-10-11T15:14:52,972 | INFO | paxweb-config-1-thread-1 | ContextHandler | 63 - org.eclipse.jetty.util - 9.4.53.v20231009 | Started o.o.p.w.s.j.i.PaxWebServletContextHandler@7c2de19c{/,null,AVAILABLE}
And it seems to work:
$ curl -XPOST -H'Content-Type: application/json' --data '{"id":"42","customer":"pax-web","flight":"0000-0001"}' -i http://localhost:8181/cxf/booking
HTTP/1.1 401 Unauthorized
WWW-Authenticate: Bearer realm="paxweb"
Cache-Control: must-revalidate,no-cache,no-store
Content-Type: text/html;charset=iso-8859-1
Content-Length: 402
<html>
<head>
<meta http-equiv="Content-Type" content="text/html;charset=ISO-8859-1"/>
<title>Error 401 Unauthorized</title>
</head>
<body><h2>HTTP ERROR 401 Unauthorized</h2>
<table>
<tr><th>URI:</th><td>/cxf/booking</td></tr>
<tr><th>STATUS:</th><td>401</td></tr>
<tr><th>MESSAGE:</th><td>Unauthorized</td></tr>
<tr><th>SERVLET:</th><td>cxf-osgi-transport-servlet</td></tr>
</table>
</body>
</html>
For Tomcat, after fixing pax-web-tomcat-keycloak18
bundle installed with pax-web-tomcat-keycloak18
feature, I also see correct configuration:
2023-10-11T15:23:39,031 | DEBUG | paxweb-config-1-thread-1 | AbstractKeycloakAuthenticatorValve | 133 - org.ops4j.pax.web.pax-web-tomcat - 8.0.23.SNAPSHOT | Using org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver to resolve Keycloak configuration on a per-request basis.
$ curl -XPOST -H'Content-Type: application/json' --data '{"id":"42","customer":"pax-web","flight":"0000-0001"}' -i http://localhost:8181/cxf/booking
HTTP/1.1 401
WWW-Authenticate: Bearer realm="paxweb"
Content-Type: text/html;charset=utf-8
Content-Language: en
Content-Length: 686
Date: Wed, 11 Oct 2023 13:24:45 GMT
<!doctype html><html lang="en"><head><title>HTTP Status 401 – Unauthorized</title><style type="text/css">body {font-family:Tahoma,Arial,sans-serif;} h1, h2, h3, b {color:white;background-color:#525D76;} h1 {font-size:22px;} h2 {font-size:16px;} h3 {font-size:14px;} p {font-size:12px;} a {color:black;} .line {height:1px;background-color:#525D76;border:none;}</style></head><body><h1>HTTP Status 401 – Unauthorized</h1><hr class="line" /><p><b>Type</b> Status Report</p><p><b>Description</b> The request has not been applied to the target resource because it lacks valid authentication credentials for that resource.</p><hr class="line" /><h3>Apache Tomcat/9.0.80</h3></body></html>
(sorry, bad commit message for Upgrade to Tomcat 9.0.82
commit)
Checking with 22.0.4:
I started fresh Keycloak 22.0.4 server (JDK 17 required):
$ bin/kc.sh start-dev --http-port 8180
Browse to http://localhost:8180/, create administrator user and browse to http://localhost:8180/admin/master/console/.
Import https://github.com/ops4j/org.ops4j.pax.web/blob/pax-web-8.0.x/pax-web-keycloak/realm-export.json as paxweb
realm.
I added another client cxf
with "Direct Access Grants" only and http://127.0.0.1:8181
root/home/admin URLs.
This client has to have "Client authentication" enabled and on "Credentials" tab, "Client ID and secret" has to be selected.
Install pax-web-jetty-keycloak
feature:
karaf@root()> feature:install pax-web-jetty-keycloak
Install rest example:
karaf@root()> repo-add mvn:org.apache.karaf.examples/karaf-rest-example-features/4.4.4/xml
Adding feature url mvn:org.apache.karaf.examples/karaf-rest-example-features/4.4.4/xml
karaf@root()> feature:install karaf-rest-example-blueprint
After adding this to etc/org.ops4j.pax.web.context-cxf.cfg
:
bundle.symbolicName = org.apache.cxf.cxf-rt-transports-http
context.id = default
context.param.keycloak.config.resolver = org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
login.config.authMethod = KEYCLOAK
security.cxf.url = /cxf/*
security.cxf.roles = paxweb-admin, paxweb-viewer
And this to etc/keycloak.json
:
{
"realm": "paxweb",
"auth-server-url": "http://localhost:8180/",
"ssl-required": "external",
"resource": "cxf",
"confidential-port": 0,
"principal-attribute": "preferred_username",
"bearer-only": true
}
I'm seeing this in logs:
2023-10-12T11:15:53,387 | INFO | paxweb-config-1-thread-1 | AbstractKeycloakJettyAuthenticator | 80 - org.ops4j.pax.web.pax-web-jetty - 8.0.23.SNAPSHOT | Using org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver to resolve Keycloak configuration on a per-request basis.
And this with CURL I see authentication problem:
$ curl -XPOST -H'Content-Type: application/json' --data '{"id":"42","customer":"pax-web","flight":"0000-0001"}' -i http://localhost:8181/cxf/booking
HTTP/1.1 401 Unauthorized
WWW-Authenticate: Bearer realm="paxweb"
Cache-Control: must-revalidate,no-cache,no-store
Content-Type: text/html;charset=iso-8859-1
Content-Length: 402
<html>
<head>
<meta http-equiv="Content-Type" content="text/html;charset=ISO-8859-1"/>
<title>Error 401 Unauthorized</title>
</head>
<body><h2>HTTP ERROR 401 Unauthorized</h2>
<table>
<tr><th>URI:</th><td>/cxf/booking</td></tr>
<tr><th>STATUS:</th><td>401</td></tr>
<tr><th>MESSAGE:</th><td>Unauthorized</td></tr>
<tr><th>SERVLET:</th><td>cxf-osgi-transport-servlet</td></tr>
</table>
</body>
</html>
However I can log in using cxf
client's secret (from Keycloak configuration of cxf
client - here it's 0f7nPJ7iK93BUirCIR6LFJgRQ6XvcNgm
):
$ curl -v -XPOST -u cxf:0f7nPJ7iK93BUirCIR6LFJgRQ6XvcNgm -H'Content-Type: application/x-www-form-urlencoded' -d 'grant_type=password&username=admin&password=passw0rd' http://127.0.0.1:8180/realms/paxweb/protocol/openid-connect/token
Note: Unnecessary use of -X or --request, POST is already inferred.
* Trying 127.0.0.1:8180...
* Connected to 127.0.0.1 (127.0.0.1) port 8180 (#0)
* Server auth using Basic with user 'cxf'
> POST /realms/paxweb/protocol/openid-connect/token HTTP/1.1
> Host: 127.0.0.1:8180
> Authorization: Basic Y3hmOjBmN25QSjdpSzkzQlVpckNJUjZMRkpnUlE2WHZjTmdt
> User-Agent: curl/8.0.1
> Accept: */*
> Content-Type: application/x-www-form-urlencoded
> Content-Length: 52
>
< HTTP/1.1 200 OK
< Referrer-Policy: no-referrer
< X-Frame-Options: SAMEORIGIN
< Strict-Transport-Security: max-age=31536000; includeSubDomains
< Cache-Control: no-store
< X-Content-Type-Options: nosniff
< Set-Cookie: KEYCLOAK_LOCALE=; Version=1; Comment=Expiring cookie; Expires=Thu, 01-Jan-1970 00:00:10 GMT; Max-Age=0; Path=/realms/paxweb/; HttpOnly
< Set-Cookie: KC_RESTART=; Version=1; Expires=Thu, 01-Jan-1970 00:00:10 GMT; Max-Age=0; Path=/realms/paxweb/; HttpOnly
< Pragma: no-cache
< X-XSS-Protection: 1; mode=block
< Content-Type: application/json
< content-length: 2192
<
{"access_token":"eyJhbGciOiJSUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICJlSFJadVhvTW8tZ0NmcG5Xd19qNVJLX3RuQWphLWRHR25oWWJvWVNWMXI4In0.eyJleHAiOjE2OTcxMDUwODYsImlhdCI6MTY5NzEwNDc4NiwianRpIjoiODMzZGRhMGUtMDgzZC00NGM3LWJhMDItMzg1OTNmZThlODI3IiwiaXNzIjoiaHR0cDovLzEyNy4wLjAuMTo4MTgwL3JlYWxtcy9wYXh3ZWIiLCJhdWQiOiJhY2NvdW50Iiwic3ViIjoiZGVkNjRmYmItMGFiYy00ZWIyLThiNDItNjczOTEyMmJhMTRlIiwidHlwIjoiQmVhcmVyIiwiYXpwIjoiY3hmIiwic2Vzc2lvbl9zdGF0ZSI6IjIzZmJkMTZlLWE4MTctNDM0Ny1hMTRhLTVjNDdkMzcxN2MyNiIsImFjciI6IjEiLCJhbGxvd2VkLW9yaWdpbnMiOlsiaHR0cDovLzEyNy4wLjAuMTo4MTgxIl0sInJlYWxtX2FjY2VzcyI6eyJyb2xlcyI6WyJkZWZhdWx0LXJvbGVzLXBheHdlYiIsIm9mZmxpbmVfYWNjZXNzIiwicGF4d2ViLWFkbWluIiwidW1hX2F1dGhvcml6YXRpb24iXX0sInJlc291cmNlX2FjY2VzcyI6eyJhY2NvdW50Ijp7InJvbGVzIjpbIm1hbmFnZS1hY2NvdW50IiwibWFuYWdlLWFjY291bnQtbGlua3MiLCJ2aWV3LXByb2ZpbGUiXX19LCJzY29wZSI6ImVtYWlsIHByb2ZpbGUiLCJzaWQiOiIyM2ZiZDE2ZS1hODE3LTQzNDctYTE0YS01YzQ3ZDM3MTdjMjYiLCJlbWFpbF92ZXJpZmllZCI6ZmFsc2UsInByZWZlcnJlZF91c2VybmFtZSI6ImFkbWluIiwiZ2l2ZW5fbmFtZSI6IiIsImZhbWlseV9uYW1lIjoiIn0.KvpSrPRqmvhm8v7G-LFUsG6V8Fu5cr5CHf7k7YEkEFBFNvzBIMGEaMGtNUfek8BfXmGGPQWbdg2cRA_C5wBfnv8c-dTcVONW8egTrUnRAfJP9P-ST6eWI-x4dR4fjVLIq4aneOzSX-L3025A1rlXg8VXlI8TarvlE1BzQu-ngLILnrPI0Tp7tjTN0cUe4UjdblMULdoSa0nM4jULW83IP7Kk-CPp_cLmS3lwl5FeMAYB9MAlzsRkffUIryxVooFqXKoEl5SU7rjAWJPmH1UMT7dt0p2FVuo1b9BHYAwyGiXtrNNqdoahQk8X1-xDFFQdYKxgUmNZqf1xdEofYug1HQ","expires_in":300,"refresh_expires_in":1800,"refresh_token":"eyJhbGciOiJIUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICI1YTcxMDE2OS0yMjQyLTRhNDUtYjc2OC02ZWVlZTFjOTQ5NGUifQ.eyJleHAiOjE2OTcxMDY1ODYsImlhdCI6MTY5NzEwNDc4NiwianRpIjoiM2Q2NTNlZGYtZTJhMi00ZmI1LThkZjQtOGFjNWMzMThkZTBlIiwiaXNzIjoiaHR0cDovLzEyNy4wLjAuMTo4MTgwL3JlYWxtcy9wYXh3ZWIiLCJhdWQiOiJodHRwOi8vMTI3LjAuMC4xOjgxODAvcmVhbG1zL3BheHdlYiIsInN1YiI6ImRlZDY0ZmJiLTBhYmMtNGViMi04YjQyLTY3MzkxMjJiYTE0ZSIsInR5cCI6IlJlZnJlc2giLCJhenAiOiJjeGYiLCJzZXNzaW9uX3N0YXRlIjoiMjNmYmQxNmUtYTgxNy00MzQ3LWExNGEtNWM0N2QzNzE3YzI2Iiwic2NvcGUiOiJlbWFpbCBwcm9maWxlIiwic2lkIjoiMjNmYmQxNmUtYTgxNy00MzQ3LWExNGEtNWM0N2QzNzE3YzI2In0.uscsweXuT3vSqchmpp_EtTcO* Connection #0 to host 127.0.0.1 left intact
9t8XfSqYe5YnCVqesJU","token_type":"Bearer","not-before-policy":0,"session_state":"23fbd16e-a817-4347-a14a-5c47d3717c26","scope":"email profile"}
$ export T=eyJhbGciOiJSUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICJlSFJadVhvTW8tZ0NmcG5Xd19qNVJLX3RuQWphLWRHR25oWWJvWVNWMXI4In0.eyJleHAiOjE2OTcxMDUwODYsImlhdCI6MTY5NzEwNDc4NiwianRpIjoiODMzZGRhMGUtMDgzZC00NGM3LWJhMDItMzg1OTNmZThlODI3IiwiaXNzIjoiaHR0cDovLzEyNy4wLjAuMTo4MTgwL3JlYWxtcy9wYXh3ZWIiLCJhdWQiOiJhY2NvdW50Iiwic3ViIjoiZGVkNjRmYmItMGFiYy00ZWIyLThiNDItNjczOTEyMmJhMTRlIiwidHlwIjoiQmVhcmVyIiwiYXpwIjoiY3hmIiwic2Vzc2lvbl9zdGF0ZSI6IjIzZmJkMTZlLWE4MTctNDM0Ny1hMTRhLTVjNDdkMzcxN2MyNiIsImFjciI6IjEiLCJhbGxvd2VkLW9yaWdpbnMiOlsiaHR0cDovLzEyNy4wLjAuMTo4MTgxIl0sInJlYWxtX2FjY2VzcyI6eyJyb2xlcyI6WyJkZWZhdWx0LXJvbGVzLXBheHdlYiIsIm9mZmxpbmVfYWNjZXNzIiwicGF4d2ViLWFkbWluIiwidW1hX2F1dGhvcml6YXRpb24iXX0sInJlc291cmNlX2FjY2VzcyI6eyJhY2NvdW50Ijp7InJvbGVzIjpbIm1hbmFnZS1hY2NvdW50IiwibWFuYWdlLWFjY291bnQtbGlua3MiLCJ2aWV3LXByb2ZpbGUiXX19LCJzY29wZSI6ImVtYWlsIHByb2ZpbGUiLCJzaWQiOiIyM2ZiZDE2ZS1hODE3LTQzNDctYTE0YS01YzQ3ZDM3MTdjMjYiLCJlbWFpbF92ZXJpZmllZCI6ZmFsc2UsInByZWZlcnJlZF91c2VybmFtZSI6ImFkbWluIiwiZ2l2ZW5fbmFtZSI6IiIsImZhbWlseV9uYW1lIjoiIn0.KvpSrPRqmvhm8v7G-LFUsG6V8Fu5cr5CHf7k7YEkEFBFNvzBIMGEaMGtNUfek8BfXmGGPQWbdg2cRA_C5wBfnv8c-dTcVONW8egTrUnRAfJP9P-ST6eWI-x4dR4fjVLIq4aneOzSX-L3025A1rlXg8VXlI8TarvlE1BzQu-ngLILnrPI0Tp7tjTN0cUe4UjdblMULdoSa0nM4jULW83IP7Kk-CPp_cLmS3lwl5FeMAYB9MAlzsRkffUIryxVooFqXKoEl5SU7rjAWJPmH1UMT7dt0p2FVuo1b9BHYAwyGiXtrNNqdoahQk8X1-xDFFQdYKxgUmNZqf1xdEofYug1HQ
And now I can access CXF endpoint:
$ curl -XPOST -H"Authorization: Bearer $T" -H 'Content-Type: application/json' --data '{"id":"42","customer":"pax-web","flight":"0000-0001"}' -i http://127.0.0.1:8181/cxf/booking
HTTP/1.1 204 No Content
Date: Thu, 12 Oct 2023 10:00:05 GMT
$ curl -XGET -H"Authorization: Bearer $T" -i http://127.0.0.1:8181/cxf/booking/42
HTTP/1.1 200 OK
Date: Thu, 12 Oct 2023 10:00:26 GMT
Content-Type: application/json
Transfer-Encoding: chunked
{"id":42,"customer":"pax-web","flight":"0000-0001"}
And I can't access it without the token:
$ curl -XGET -i http://127.0.0.1:8181/cxf/booking/42
HTTP/1.1 401 Unauthorized
WWW-Authenticate: Bearer realm="paxweb"
Cache-Control: must-revalidate,no-cache,no-store
Content-Type: text/html;charset=iso-8859-1
Content-Length: 405
<html>
<head>
<meta http-equiv="Content-Type" content="text/html;charset=ISO-8859-1"/>
<title>Error 401 Unauthorized</title>
</head>
<body><h2>HTTP ERROR 401 Unauthorized</h2>
<table>
<tr><th>URI:</th><td>/cxf/booking/42</td></tr>
<tr><th>STATUS:</th><td>401</td></tr>
<tr><th>MESSAGE:</th><td>Unauthorized</td></tr>
<tr><th>SERVLET:</th><td>cxf-osgi-transport-servlet</td></tr>
</table>
</body>
</html>
It works with Tomcat and Undertow as well.
Hello,
I use keycloak authentication with apache karaf almost 4 years. Previously I was using keycloak with undertow, but currently we upgraded the karaf version and now I see that there is a pax-web-jetty-keycloak feature with looks like support keycloak integration with jetty 9.4. I have installed the pax-web-jetty-keycloak and also created a keycloak.json file. Additionally I have created a org.ops4j.pax.web.context-services.cfg file with the following content:
NOTE: previously I also used the following parameter which I removed this time, as this property looks that is not available any more.
context.param.keycloak.config.resolver = org.keycloak.adapters.osgi.HierarchicalPathBasedKeycloakConfigResolver
But, unfortunately I receive the following error during the service call:
ERROR: keycloak deployment isn't configured return false
is is an issue there? or do I miss some configurations?
BR, Farid