keycloak-aplcache
Changes
core/pom.xml 41(+41 -0)
distribution/osgi/jaas/pom.xml 4(+2 -2)
distribution/osgi/pom.xml 2(+1 -1)
distribution/osgi/thirdparty/pom.xml 53(+14 -39)
examples/fuse/camel/pom.xml 79(+79 -0)
examples/fuse/customer-app-fuse/pom.xml 121(+121 -0)
examples/fuse/cxf-jaxrs/pom.xml 86(+86 -0)
examples/fuse/cxf-jaxws/pom.xml 107(+107 -0)
examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/GetPersonResponse.java 120(+120 -0)
examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/UnknownPersonFault.java 64(+64 -0)
examples/fuse/features/pom.xml 62(+62 -0)
examples/fuse/pom.xml 37(+37 -0)
examples/fuse/product-app-fuse/pom.xml 83(+83 -0)
examples/fuse/product-app-fuse/src/main/java/org/keycloak/example/ProductPortalServlet.java 95(+95 -0)
examples/fuse/README.md 33(+33 -0)
examples/fuse/testrealm.json 137(+137 -0)
examples/pom.xml 1(+1 -0)
integration/adapter-core/pom.xml 44(+44 -0)
integration/jetty/jetty8.1/pom.xml 41(+41 -0)
integration/jetty/jetty8.1/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java 1(+1 -0)
integration/jetty/jetty8.1/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java 1(+1 -0)
integration/jetty/jetty9.1/pom.xml 42(+42 -0)
integration/jetty/jetty9.1/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java 1(+1 -0)
integration/jetty/jetty9.1/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java 1(+1 -0)
integration/jetty/jetty9.2/pom.xml 42(+42 -0)
integration/jetty/jetty9.2/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java 2(+1 -1)
integration/jetty/jetty9.2/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java 1(+1 -0)
integration/jetty/jetty-core/pom.xml 42(+42 -0)
integration/jetty/jetty-core/src/main/java/org/keycloak/adapters/jetty/core/AbstractJettySessionTokenStore.java 5(+1 -4)
integration/jetty/jetty-core/src/main/java/org/keycloak/adapters/jetty/core/AbstractKeycloakJettyAuthenticator.java 18(+14 -4)
integration/jetty/jetty-core/src/main/java/org/keycloak/adapters/jetty/core/JettyCookieTokenStore.java 2(+1 -1)
integration/jetty/jetty-core/src/main/java/org/keycloak/adapters/jetty/core/JettyHttpFacade.java 2(+1 -1)
integration/jetty/jetty-core/src/main/java/org/keycloak/adapters/jetty/core/JettyRequestAuthenticator.java 2(+1 -1)
integration/jetty/jetty-core/src/main/java/org/keycloak/adapters/jetty/core/JettyUserSessionManagement.java 2(+1 -1)
integration/jetty/jetty-core/src/main/java/org/keycloak/adapters/jetty/core/WrappingSessionHandler.java 30(+30 -0)
integration/osgi-adapter/pom.xml 104(+104 -0)
integration/osgi-adapter/src/main/java/org/keycloak/adapters/osgi/PaxWebIntegrationService.java 163(+163 -0)
integration/osgi-adapter/src/main/java/org/keycloak/adapters/osgi/ServletUnregistrationService.java 100(+100 -0)
integration/pom.xml 1(+1 -0)
pom.xml 20(+19 -1)
Details
core/pom.xml 41(+41 -0)
diff --git a/core/pom.xml b/core/pom.xml
index df6da12..294024a 100755
--- a/core/pom.xml
+++ b/core/pom.xml
@@ -11,11 +11,19 @@
<artifactId>keycloak-core</artifactId>
<name>Keycloak Core</name>
+ <packaging>jar</packaging>
<description/>
<properties>
<timestamp>${maven.build.timestamp}</timestamp>
<maven.build.timestamp.format>yyyy-MM-dd HH:mm</maven.build.timestamp.format>
+ <keycloak.osgi.export>
+ org.keycloak.*
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ net.iharder;version=${base64.version},
+ *;resolution:=optional
+ </keycloak.osgi.import>
</properties>
<dependencies>
<dependency>
@@ -60,6 +68,39 @@
<target>${maven.compiler.target}</target>
</configuration>
</plugin>
+
+ <!-- Adding OSGI metadata to the JAR without changing the packaging type. -->
+ <plugin>
+ <artifactId>maven-jar-plugin</artifactId>
+ <configuration>
+ <archive>
+ <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
+ </archive>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <executions>
+ <execution>
+ <id>bundle-manifest</id>
+ <phase>process-classes</phase>
+ <goals>
+ <goal>manifest</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <instructions>
+ <Bundle-ClassPath>.</Bundle-ClassPath>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
</plugins>
</build>
diff --git a/distribution/examples-docs-zip/build.xml b/distribution/examples-docs-zip/build.xml
index 503dc8e..3725160 100755
--- a/distribution/examples-docs-zip/build.xml
+++ b/distribution/examples-docs-zip/build.xml
@@ -93,6 +93,12 @@
<exclude name="**/README.md"/>
</fileset>
</copy>
+ <copy todir="target/examples/fuse" overwrite="true">
+ <fileset dir="../../examples/fuse">
+ <exclude name="**/target/**"/>
+ <exclude name="**/*.iml"/>
+ </fileset>
+ </copy>
<copy file="../../examples/README.md" tofile="target/examples/README.md"/>
<move file="target/examples/unconfigured-demo/README.md.unconfigured" tofile="target/examples/unconfigured-demo/README.md"/>
<move file="target/examples/unconfigured-demo/customer-app/src/main/webapp/WEB-INF/web.xml.unconfigured" tofile="target/examples/unconfigured-demo/customer-app/src/main/webapp/WEB-INF/web.xml"/>
diff --git a/distribution/osgi/features/src/main/resources/features.xml b/distribution/osgi/features/src/main/resources/features.xml
index f72ac8d..d56602b 100644
--- a/distribution/osgi/features/src/main/resources/features.xml
+++ b/distribution/osgi/features/src/main/resources/features.xml
@@ -1,15 +1,53 @@
<?xml version='1.0' encoding='UTF-8'?>
<features xmlns="http://karaf.apache.org/xmlns/features/v1.0.0" name="keycloak-${project.version}">
- <feature name="keycloak-core-adapter" version="${project.version}" resolver="(obr)">
- <details>The keycloak core adapter stuff</details>
- <bundle>mvn:org.keycloak/keycloak-osgi-core-adapter/${project.version}</bundle>
+ <feature name="keycloak-adapter-core" version="${project.version}" resolver="(obr)">
+ <details>The keycloak adapter core stuff</details>
+ <bundle dependency="true">mvn:org.keycloak/keycloak-osgi-thirdparty/${project.version}</bundle>
+ <bundle dependency="true">mvn:org.bouncycastle/bcprov-jdk16/${bouncycastle.version}</bundle>
+ <bundle dependency="true">mvn:org.codehaus.jackson/jackson-core-asl/${jackson.version}</bundle>
+ <bundle dependency="true">mvn:org.codehaus.jackson/jackson-mapper-asl/${jackson.version}</bundle>
+ <bundle dependency="true">mvn:org.codehaus.jackson/jackson-xc/${jackson.version}</bundle>
+ <bundle dependency="true">mvn:org.jboss.logging/jboss-logging/${jboss.logging.version}</bundle>
+ <bundle>mvn:org.keycloak/keycloak-core/${project.version}</bundle>
+ <bundle>mvn:org.keycloak/keycloak-adapter-core/${project.version}</bundle>
+ </feature>
+
+ <feature name="keycloak-osgi-adapter" version="${project.version}" resolver="(obr)">
+ <details>The keycloak adapter core stuff</details>
+ <feature>keycloak-adapter-core</feature>
+ <feature version="[2.3,4)">http-whiteboard</feature>
+ <bundle>mvn:org.keycloak/keycloak-osgi-adapter/${project.version}</bundle>
+ </feature>
+
+ <feature name="keycloak-jetty8-adapter" version="${project.version}" resolver="(obr)">
+ <details>The keycloak Jetty8 adapter</details>
+ <feature>keycloak-adapter-core</feature>
+ <feature version="[8.1,9)">jetty</feature>
+ <bundle>mvn:org.keycloak/keycloak-jetty-core/${project.version}</bundle>
+ <bundle>mvn:org.keycloak/keycloak-jetty81-adapter/${project.version}</bundle>
</feature>
<feature name="keycloak-jaas" version="${project.version}" resolver="(obr)">
<details>The keycloak JAAS configuration</details>
- <feature>keycloak-core-adapter</feature>
+ <feature>keycloak-adapter-core</feature>
<bundle>mvn:org.keycloak/keycloak-osgi-jaas/${project.version}</bundle>
</feature>
+ <feature name="keycloak" version="${project.version}" resolver="(obr)">
+ <details>The keycloak adapter core stuff</details>
+ <feature>keycloak-osgi-adapter</feature>
+ <feature>keycloak-jetty8-adapter</feature>
+ <feature>keycloak-jaas</feature>
+ </feature>
+
+ <!-- This is just simplification to upgrade paxweb to 3.1.2 in JBoss Fuse 6.1 or Karaf 2.3.X environment -->
+ <feature name="keycloak-pax-web-upgrade" version="${project.version}" resolver="(obr)">
+ <details>This is just simplification to upgrade paxweb to 3.1.2 in JBoss Fuse 6.1 or Karaf 2.3.X environment</details>
+ <bundle>mvn:org.ow2.asm/asm-all/5.0</bundle>
+ <bundle>mvn:org.apache.xbean/xbean-bundleutils/3.18</bundle>
+ <bundle>mvn:org.apache.xbean/xbean-reflect/3.18</bundle>
+ <bundle>mvn:org.apache.xbean/xbean-finder/3.18</bundle>
+ </feature>
+
</features>
\ No newline at end of file
distribution/osgi/jaas/pom.xml 4(+2 -2)
diff --git a/distribution/osgi/jaas/pom.xml b/distribution/osgi/jaas/pom.xml
index ae9bc5e..dfac9c4 100755
--- a/distribution/osgi/jaas/pom.xml
+++ b/distribution/osgi/jaas/pom.xml
@@ -7,7 +7,7 @@
<version>1.1.0.Final-SNAPSHOT</version>
<relativePath>../../../pom.xml</relativePath>
</parent>
- <name>Keycloak OSGI JAAS</name>
+ <name>Keycloak OSGI JAAS Realm Configuration</name>
<description/>
<modelVersion>4.0.0</modelVersion>
@@ -53,7 +53,7 @@
<Embed-Dependency>*;scope=compile|runtime</Embed-Dependency>
<Embed-Transitive>false</Embed-Transitive>
<Bundle-ClassPath>.</Bundle-ClassPath> -->
- <Bundle-Name>${project.description}</Bundle-Name>
+ <Bundle-Name>${project.name}</Bundle-Name>
<Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
<Import-Package>${keycloak.osgi.import}</Import-Package>
<Export-Package>${keycloak.osgi.export}</Export-Package>
distribution/osgi/pom.xml 2(+1 -1)
diff --git a/distribution/osgi/pom.xml b/distribution/osgi/pom.xml
index 2185002..3f5ebd9 100755
--- a/distribution/osgi/pom.xml
+++ b/distribution/osgi/pom.xml
@@ -17,7 +17,7 @@
<modules>
<module>features</module>
<module>jaas</module>
- <module>core-adapter</module>
+ <module>thirdparty</module>
</modules>
</project>
\ No newline at end of file
examples/fuse/camel/pom.xml 79(+79 -0)
diff --git a/examples/fuse/camel/pom.xml b/examples/fuse/camel/pom.xml
new file mode 100644
index 0000000..2909e42
--- /dev/null
+++ b/examples/fuse/camel/pom.xml
@@ -0,0 +1,79 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <parent>
+ <artifactId>keycloak-parent</artifactId>
+ <groupId>org.keycloak</groupId>
+ <version>1.1.0.Final-SNAPSHOT</version>
+ <relativePath>../../../pom.xml</relativePath>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.keycloak.example.demo</groupId>
+ <artifactId>camel-endpoint-example</artifactId>
+ <packaging>bundle</packaging>
+ <name>Camel endpoint example - Secured in Karaf/Fuse</name>
+ <description/>
+
+ <properties>
+ <camel.version>2.12.5</camel.version>
+ <keycloak.osgi.export>
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ org.eclipse.jetty.security;version="[8.1,10)",
+ org.eclipse.jetty.util.security;version="[8.1,10)",
+ org.keycloak.*;version="${project.version}",
+ *;resolution:=optional
+ </keycloak.osgi.import>
+ <keycloak.osgi.private>
+ org.keycloak.example.*
+ </keycloak.osgi.private>
+ </properties>
+
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.camel</groupId>
+ <artifactId>camel-core</artifactId>
+ <version>${camel.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.camel</groupId>
+ <artifactId>camel-blueprint</artifactId>
+ <version>${camel.version}</version>
+ </dependency>
+ <dependency><groupId>org.apache.camel</groupId>
+ <artifactId>camel-jetty</artifactId>
+ <version>${camel.version}</version>
+ </dependency>
+ </dependencies>
+
+ <build>
+ <defaultGoal>install</defaultGoal>
+
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <configuration>
+ <source>${maven.compiler.source}</source>
+ <target>${maven.compiler.target}</target>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <configuration>
+ <instructions>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Private-Package>${keycloak.osgi.private}</Private-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
+
+ </plugins>
+ </build>
+
+</project>
diff --git a/examples/fuse/camel/src/main/java/org/keycloak/example/CamelHelloBean.java b/examples/fuse/camel/src/main/java/org/keycloak/example/CamelHelloBean.java
new file mode 100644
index 0000000..df5c472
--- /dev/null
+++ b/examples/fuse/camel/src/main/java/org/keycloak/example/CamelHelloBean.java
@@ -0,0 +1,15 @@
+package org.keycloak.example;
+
+import java.text.SimpleDateFormat;
+import java.util.Date;
+
+/**
+ * @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
+ */
+public class CamelHelloBean {
+
+ public String hello() {
+ SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
+ return "Hello admin! It's " + sdf.format(new Date());
+ }
+}
diff --git a/examples/fuse/camel/src/main/resources/OSGI-INF/blueprint/blueprint.xml b/examples/fuse/camel/src/main/resources/OSGI-INF/blueprint/blueprint.xml
new file mode 100644
index 0000000..0dc0fdd
--- /dev/null
+++ b/examples/fuse/camel/src/main/resources/OSGI-INF/blueprint/blueprint.xml
@@ -0,0 +1,67 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xmlns:camel="http://camel.apache.org/schema/blueprint"
+ xsi:schemaLocation="
+ http://www.osgi.org/xmlns/blueprint/v1.0.0 http://www.osgi.org/xmlns/blueprint/v1.0.0/blueprint.xsd
+ http://camel.apache.org/schema/blueprint http://camel.apache.org/schema/blueprint/camel-blueprint.xsd">
+
+ <bean id="kcAdapterConfig" class="org.keycloak.representations.adapters.config.AdapterConfig">
+ <property name="realm" value="demo"/>
+ <property name="resource" value="admin-camel-endpoint"/>
+ <property name="realmKey" value="MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCrVrCuTtArbgaZzL1hvh0xtL5mc7o0NqPVnYXkLvgcwiC3BjLGw1tGEGoJaXDuSaRllobm53JBhjx33UNv+5z/UMG4kytBWxheNVKnL6GgqlNabMaFfPLPCF8kAgKnsi79NMo+n6KnSY8YeUmec/p2vjO2NjsSAVcWEQMVhJ31LwIDAQAB"/>
+ <property name="bearerOnly" value="true"/>
+ <property name="sslRequired" value="EXTERNAL"/>
+ </bean>
+
+ <bean id="keycloakAuthenticator" class="org.keycloak.adapters.jetty.KeycloakJettyAuthenticator">
+ <property name="adapterConfig" ref="kcAdapterConfig"/>
+ </bean>
+
+ <bean id="constraint" class="org.eclipse.jetty.util.security.Constraint">
+ <property name="name" value="Customers"/>
+ <property name="roles">
+ <list>
+ <value>admin</value>
+ </list>
+ </property>
+ <property name="authenticate" value="true"/>
+ <property name="dataConstraint" value="0"/>
+ </bean>
+
+ <bean id="constraintMapping" class="org.eclipse.jetty.security.ConstraintMapping">
+ <property name="constraint" ref="constraint"/>
+ <property name="pathSpec" value="/*"/>
+ </bean>
+
+ <bean id="securityHandler" class="org.eclipse.jetty.security.ConstraintSecurityHandler">
+ <property name="authenticator" ref="keycloakAuthenticator" />
+ <property name="constraintMappings">
+ <list>
+ <ref component-id="constraintMapping" />
+ </list>
+ </property>
+ <property name="authMethod" value="BASIC"/>
+ <property name="realmName" value="does-not-matter"/>
+ </bean>
+
+ <bean id="sessionHandler" class="org.keycloak.adapters.jetty.core.WrappingSessionHandler">
+ <property name="handler" ref="securityHandler" />
+ </bean>
+
+ <bean id="helloBean" class="org.keycloak.example.CamelHelloBean" />
+
+ <camelContext id="blueprintContext"
+ trace="false"
+ xmlns="http://camel.apache.org/schema/blueprint">
+ <route id="httpBridge">
+ <from uri="jetty:http://0.0.0.0:8383/admin-camel-endpoint?handlers=sessionHandler&matchOnUriPrefix=true" />
+ <setBody>
+ <method ref="helloBean" method="hello"/>
+ </setBody>
+ <log message="The message from camel endpoint contains ${body}"/>
+ <to uri="mock:result"/>
+ </route>
+ </camelContext>
+
+</blueprint>
\ No newline at end of file
examples/fuse/customer-app-fuse/pom.xml 121(+121 -0)
diff --git a/examples/fuse/customer-app-fuse/pom.xml b/examples/fuse/customer-app-fuse/pom.xml
new file mode 100644
index 0000000..cd5e4dc
--- /dev/null
+++ b/examples/fuse/customer-app-fuse/pom.xml
@@ -0,0 +1,121 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <parent>
+ <artifactId>keycloak-parent</artifactId>
+ <groupId>org.keycloak</groupId>
+ <version>1.1.0.Final-SNAPSHOT</version>
+ <relativePath>../../../pom.xml</relativePath>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.keycloak.example.demo</groupId>
+ <artifactId>customer-portal-fuse-example</artifactId>
+ <packaging>war</packaging>
+ <name>Customer Portal - Secured in Karaf/Fuse</name>
+ <description/>
+
+ <properties>
+ <keycloak.osgi.export>
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ org.apache.http.*;version=${keycloak.apache.httpcomponents.version},
+ javax.servlet.*;version="[2.5,4)",
+ org.keycloak.adapters.jetty;version="${project.version}",
+ org.keycloak.adapters;version="${project.version}",
+ org.keycloak.constants;version="${project.version}",
+ org.keycloak.util;version="${project.version}",
+ org.keycloak.*;version="${project.version}",
+ *;resolution:=optional
+ </keycloak.osgi.import>
+ <keycloak.osgi.private>
+ org.keycloak.example.*
+ </keycloak.osgi.private>
+ </properties>
+
+ <dependencies>
+ <dependency>
+ <groupId>org.jboss.spec.javax.servlet</groupId>
+ <artifactId>jboss-servlet-api_3.0_spec</artifactId>
+ <scope>provided</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.keycloak</groupId>
+ <artifactId>keycloak-core</artifactId>
+ <version>${project.version}</version>
+ <scope>provided</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.keycloak</groupId>
+ <artifactId>keycloak-adapter-core</artifactId>
+ <version>${project.version}</version>
+ <scope>provided</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.httpcomponents</groupId>
+ <artifactId>httpclient</artifactId>
+ <version>${keycloak.apache.httpcomponents.version}</version>
+ <scope>provided</scope>
+ </dependency>
+ </dependencies>
+
+ <build>
+ <finalName>customer-portal-fuse</finalName>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-deploy-plugin</artifactId>
+ <configuration>
+ <skip>true</skip>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <configuration>
+ <source>${maven.compiler.source}</source>
+ <target>${maven.compiler.target}</target>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-war-plugin</artifactId>
+ <configuration>
+ <archive>
+ <manifestFile>${basedir}/target/classes/META-INF/MANIFEST.MF</manifestFile>
+ </archive>
+ </configuration>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <executions>
+ <execution>
+ <id>bundle-manifest</id>
+ <phase>process-classes</phase>
+ <goals>
+ <goal>manifest</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <supportedProjectTypes>
+ <supportedProjectType>war</supportedProjectType>
+ </supportedProjectTypes>
+ <instructions>
+ <Webapp-Context>customer-portal</Webapp-Context>
+ <Web-ContextPath>customer-portal</Web-ContextPath>
+ <Embed-Directory>WEB-INF/lib</Embed-Directory>
+ <Bundle-ClassPath>.,WEB-INF/classes</Bundle-ClassPath>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Private-Package>${keycloak.osgi.private}</Private-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+</project>
diff --git a/examples/fuse/customer-app-fuse/src/main/java/org/keycloak/example/CamelClient.java b/examples/fuse/customer-app-fuse/src/main/java/org/keycloak/example/CamelClient.java
new file mode 100644
index 0000000..9ddb8f1
--- /dev/null
+++ b/examples/fuse/customer-app-fuse/src/main/java/org/keycloak/example/CamelClient.java
@@ -0,0 +1,74 @@
+package org.keycloak.example;
+
+import java.io.BufferedReader;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+
+import javax.servlet.http.HttpServletRequest;
+
+import org.apache.http.HttpEntity;
+import org.apache.http.HttpResponse;
+import org.apache.http.client.HttpClient;
+import org.apache.http.client.methods.HttpGet;
+import org.keycloak.KeycloakSecurityContext;
+import org.keycloak.adapters.HttpClientBuilder;
+
+/**
+ * @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
+ */
+public class CamelClient {
+
+ public static String sendRequest(HttpServletRequest req) throws CxfRsClient.Failure {
+ KeycloakSecurityContext session = (KeycloakSecurityContext) req.getAttribute(KeycloakSecurityContext.class.getName());
+
+ HttpClient client = new HttpClientBuilder()
+ .disableTrustManager().build();
+ try {
+ HttpGet get = new HttpGet("http://localhost:8383/admin-camel-endpoint");
+ get.addHeader("Authorization", "Bearer " + session.getTokenString());
+ try {
+ HttpResponse response = client.execute(get);
+ if (response.getStatusLine().getStatusCode() != 200) {
+ return "There was a failure processing request. You either didn't configure Keycloak properly or you don't have enought permission? Status code is "
+ + response.getStatusLine().getStatusCode();
+ }
+ HttpEntity entity = response.getEntity();
+ InputStream is = entity.getContent();
+ try {
+ return getStringFromInputStream(is);
+ } finally {
+ is.close();
+ }
+ } catch (IOException e) {
+ throw new RuntimeException(e);
+ }
+ } finally {
+ client.getConnectionManager().shutdown();
+ }
+ }
+
+ private static String getStringFromInputStream(InputStream is) {
+ BufferedReader br = null;
+ StringBuilder sb = new StringBuilder();
+ String line;
+ try {
+ br = new BufferedReader(new InputStreamReader(is));
+ while ((line = br.readLine()) != null) {
+ sb.append(line);
+ }
+ } catch (IOException e) {
+ throw new RuntimeException(e);
+ } finally {
+ if (br != null) {
+ try {
+ br.close();
+ } catch (IOException e) {
+ throw new RuntimeException(e);
+ }
+ }
+ }
+ return sb.toString();
+
+ }
+}
diff --git a/examples/fuse/customer-app-fuse/src/main/java/org/keycloak/example/CxfRsClient.java b/examples/fuse/customer-app-fuse/src/main/java/org/keycloak/example/CxfRsClient.java
new file mode 100644
index 0000000..4d64429
--- /dev/null
+++ b/examples/fuse/customer-app-fuse/src/main/java/org/keycloak/example/CxfRsClient.java
@@ -0,0 +1,75 @@
+package org.keycloak.example;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.servlet.http.HttpServletRequest;
+
+import org.apache.http.HttpEntity;
+import org.apache.http.HttpResponse;
+import org.apache.http.client.HttpClient;
+import org.apache.http.client.methods.HttpGet;
+import org.keycloak.KeycloakSecurityContext;
+import org.keycloak.adapters.HttpClientBuilder;
+import org.keycloak.representations.IDToken;
+import org.keycloak.util.JsonSerialization;
+import org.keycloak.util.UriUtils;
+
+/**
+ * @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
+ * @version $Revision: 1 $
+ */
+public class CxfRsClient {
+
+ static class TypedList extends ArrayList<String> {
+ }
+
+ public static class Failure extends Exception {
+ private int status;
+
+ public Failure(int status) {
+ this.status = status;
+ }
+
+ public int getStatus() {
+ return status;
+ }
+ }
+
+ public static IDToken getIDToken(HttpServletRequest req) {
+ KeycloakSecurityContext session = (KeycloakSecurityContext) req.getAttribute(KeycloakSecurityContext.class.getName());
+ return session.getIdToken();
+
+ }
+
+ public static List<String> getCustomers(HttpServletRequest req) throws Failure {
+ KeycloakSecurityContext session = (KeycloakSecurityContext) req.getAttribute(KeycloakSecurityContext.class.getName());
+
+ HttpClient client = new HttpClientBuilder()
+ .disableTrustManager().build();
+ try {
+ HttpGet get = new HttpGet(UriUtils.getOrigin(req.getRequestURL().toString()) + "/cxf/customerservice/customers");
+ get.addHeader("Authorization", "Bearer " + session.getTokenString());
+ try {
+ HttpResponse response = client.execute(get);
+ if (response.getStatusLine().getStatusCode() != 200) {
+ throw new Failure(response.getStatusLine().getStatusCode());
+ }
+ HttpEntity entity = response.getEntity();
+ InputStream is = entity.getContent();
+ try {
+ return JsonSerialization.readValue(is, TypedList.class);
+ } finally {
+ is.close();
+ }
+ } catch (IOException e) {
+ throw new RuntimeException(e);
+ }
+ } finally {
+ client.getConnectionManager().shutdown();
+ }
+ }
+
+}
diff --git a/examples/fuse/customer-app-fuse/src/main/webapp/customers/camel.jsp b/examples/fuse/customer-app-fuse/src/main/webapp/customers/camel.jsp
new file mode 100755
index 0000000..1d29927
--- /dev/null
+++ b/examples/fuse/customer-app-fuse/src/main/webapp/customers/camel.jsp
@@ -0,0 +1,15 @@
+<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
+ pageEncoding="ISO-8859-1" %>
+<%@ page import="org.keycloak.constants.ServiceUrlConstants" %>
+<%@ page import="org.keycloak.example.CamelClient" %>
+<%@ page import="org.keycloak.representations.IDToken" %>
+<html>
+ <head>
+ <title>Camel page</title>
+ </head>
+ <body bgcolor="#E3F6CE">
+ <p>You will receive info from camel endpoint. Endpoint is accessible just for admin user</p>
+ <p>Response from camel: <b><%= CamelClient.sendRequest(request) %></b> </p>
+ <br><br>
+ </body>
+</html>
\ No newline at end of file
diff --git a/examples/fuse/customer-app-fuse/src/main/webapp/customers/cxf-ws.jsp b/examples/fuse/customer-app-fuse/src/main/webapp/customers/cxf-ws.jsp
new file mode 100755
index 0000000..45c5dcb
--- /dev/null
+++ b/examples/fuse/customer-app-fuse/src/main/webapp/customers/cxf-ws.jsp
@@ -0,0 +1,50 @@
+<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
+ pageEncoding="ISO-8859-1" %>
+<%@ page import="org.keycloak.constants.ServiceUrlConstants" %>
+<%@ page import="org.keycloak.example.CxfRsClient" %>
+<%@ page import="org.keycloak.representations.IDToken" %>
+<%@ page import="org.keycloak.util.KeycloakUriBuilder" %>
+<%@ page session="false" %>
+<html>
+<head>
+ <title>Customer View Page</title>
+</head>
+<body bgcolor="#E3F6CE">
+<%
+ String logoutUri = KeycloakUriBuilder.fromUri("http://localhost:8080/auth").path(ServiceUrlConstants.TOKEN_SERVICE_LOGOUT_PATH)
+ .queryParam("redirect_uri", "http://localhost:8181/customer-portal").build("demo").toString();
+ String acctUri = KeycloakUriBuilder.fromUri("http://localhost:8080/auth").path(ServiceUrlConstants.ACCOUNT_SERVICE_PATH)
+ .queryParam("referrer", "customer-portal").build("demo").toString();
+ IDToken idToken = CxfRsClient.getIDToken(request);
+%>
+<p>Goto: <a href="/product-portal">products</a> | <a href="<%=logoutUri%>">logout</a> | <a
+ href="<%=acctUri%>">manage acct</a></p>
+Servlet User Principal <b><%=request.getUserPrincipal().getName()%>
+</b> made this request.
+<p><b>Caller IDToken values</b> (<i>You can specify what is returned in IDToken in the customer-portal claims page in the admin console</i>:</p>
+<p>Username: <%=idToken.getPreferredUsername()%></p>
+<p>Email: <%=idToken.getEmail()%></p>
+<p>Full Name: <%=idToken.getName()%></p>
+<p>First: <%=idToken.getGivenName()%></p>
+<p>Last: <%=idToken.getFamilyName()%></p>
+<h2>Customer Listing</h2>
+<%
+ java.util.List<String> list = null;
+ try {
+ list = CxfRsClient.getCustomers(request);
+ } catch (CxfRsClient.Failure failure) {
+ out.println("There was a failure processing request. You either didn't configure Keycloak properly, or maybe" +
+ "you just forgot to secure the cxf ws service?");
+ out.println("Status from cxf ws service invocation was: " + failure.getStatus());
+ return;
+ }
+ for (String cust : list) {
+ out.print("<p>");
+ out.print(cust);
+ out.println("</p>");
+
+ }
+%>
+<br><br>
+</body>
+</html>
\ No newline at end of file
diff --git a/examples/fuse/customer-app-fuse/src/main/webapp/index.html b/examples/fuse/customer-app-fuse/src/main/webapp/index.html
new file mode 100755
index 0000000..3da0d42
--- /dev/null
+++ b/examples/fuse/customer-app-fuse/src/main/webapp/index.html
@@ -0,0 +1,15 @@
+<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
+ "http://www.w3.org/TR/html4/loose.dtd">
+<html>
+ <head>
+ <title>Customer portal on Karaf/Fuse</title>
+ </head>
+ <body bgcolor="#E3F6CE">
+ <h1>Customer Portal</h1>
+
+ <p><a href="customers/cxf-ws.jsp">Customer Listing - CXF WS endpoint</a></p>
+
+ <p><a href="customers/camel.jsp">Admin Interface - Apache Camel endpoint</a></p>
+
+ </body>
+</html>
\ No newline at end of file
diff --git a/examples/fuse/customer-app-fuse/src/main/webapp/WEB-INF/jetty-web.xml b/examples/fuse/customer-app-fuse/src/main/webapp/WEB-INF/jetty-web.xml
new file mode 100644
index 0000000..e3d87a2
--- /dev/null
+++ b/examples/fuse/customer-app-fuse/src/main/webapp/WEB-INF/jetty-web.xml
@@ -0,0 +1,10 @@
+<?xml version="1.0"?>
+<!DOCTYPE Configure PUBLIC "-//Mort Bay Consulting//DTD Configure//EN" "http://www.eclipse.org/jetty/configure_9_0.dtd">
+<Configure class="org.eclipse.jetty.webapp.WebAppContext">
+ <Get name="securityHandler">
+ <Set name="authenticator">
+ <New class="org.keycloak.adapters.jetty.KeycloakJettyAuthenticator">
+ </New>
+ </Set>
+ </Get>
+</Configure>
\ No newline at end of file
diff --git a/examples/fuse/customer-app-fuse/src/main/webapp/WEB-INF/keycloak.json b/examples/fuse/customer-app-fuse/src/main/webapp/WEB-INF/keycloak.json
new file mode 100755
index 0000000..b5d6b30
--- /dev/null
+++ b/examples/fuse/customer-app-fuse/src/main/webapp/WEB-INF/keycloak.json
@@ -0,0 +1,10 @@
+{
+ "realm": "demo",
+ "resource": "customer-portal",
+ "realm-public-key": "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCrVrCuTtArbgaZzL1hvh0xtL5mc7o0NqPVnYXkLvgcwiC3BjLGw1tGEGoJaXDuSaRllobm53JBhjx33UNv+5z/UMG4kytBWxheNVKnL6GgqlNabMaFfPLPCF8kAgKnsi79NMo+n6KnSY8YeUmec/p2vjO2NjsSAVcWEQMVhJ31LwIDAQAB",
+ "auth-server-url": "http://localhost:8080/auth",
+ "ssl-required" : "external",
+ "credentials": {
+ "secret": "password"
+ }
+}
diff --git a/examples/fuse/customer-app-fuse/src/main/webapp/WEB-INF/web.xml b/examples/fuse/customer-app-fuse/src/main/webapp/WEB-INF/web.xml
new file mode 100755
index 0000000..6fb7590
--- /dev/null
+++ b/examples/fuse/customer-app-fuse/src/main/webapp/WEB-INF/web.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<web-app xmlns="http://java.sun.com/xml/ns/javaee"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd"
+ version="3.0">
+
+ <module-name>customer-portal</module-name>
+
+ <welcome-file-list>
+ <welcome-file>index.html</welcome-file>
+ </welcome-file-list>
+
+ <security-constraint>
+ <web-resource-collection>
+ <web-resource-name>Customers</web-resource-name>
+ <url-pattern>/customers/*</url-pattern>
+ </web-resource-collection>
+ <auth-constraint>
+ <role-name>user</role-name>
+ </auth-constraint>
+ </security-constraint>
+
+ <login-config>
+ <auth-method>BASIC</auth-method>
+ <realm-name>does-not-matter</realm-name>
+ </login-config>
+
+ <security-role>
+ <role-name>admin</role-name>
+ </security-role>
+ <security-role>
+ <role-name>user</role-name>
+ </security-role>
+</web-app>
examples/fuse/cxf-jaxrs/pom.xml 86(+86 -0)
diff --git a/examples/fuse/cxf-jaxrs/pom.xml b/examples/fuse/cxf-jaxrs/pom.xml
new file mode 100644
index 0000000..d96c78f
--- /dev/null
+++ b/examples/fuse/cxf-jaxrs/pom.xml
@@ -0,0 +1,86 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <parent>
+ <artifactId>keycloak-parent</artifactId>
+ <groupId>org.keycloak</groupId>
+ <version>1.1.0.Final-SNAPSHOT</version>
+ <relativePath>../../../pom.xml</relativePath>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.keycloak.example.demo</groupId>
+ <artifactId>cxf-jaxrs-example</artifactId>
+ <packaging>bundle</packaging>
+ <name>CXF JAXRS Example - Secured in Karaf/Fuse</name>
+
+ <properties>
+ <cxf.version>2.7.14</cxf.version>
+ <keycloak.osgi.export>
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ META-INF.cxf,
+ META-INF.cxf.osgi,
+ org.apache.cxf.bus,
+ org.apache.cxf.bus.spring,
+ org.apache.cxf.bus.resource,
+ org.apache.cxf.resource,
+ org.apache.cxf.jaxrs,
+ org.apache.cxf.transport.http,
+ org.codehaus.jackson.jaxrs;version="${jackson.version}",
+ org.keycloak.adapters.jetty;version="${project.version}",
+ org.keycloak.adapters;version="${project.version}",
+ *
+ </keycloak.osgi.import>
+ <keycloak.osgi.private>
+ org.keycloak.example.rs.*
+ </keycloak.osgi.private>
+ </properties>
+
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.cxf</groupId>
+ <artifactId>cxf-rt-frontend-jaxrs</artifactId>
+ <version>${cxf.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.cxf</groupId>
+ <artifactId>cxf-rt-transports-http</artifactId>
+ <version>${cxf.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.cxf</groupId>
+ <artifactId>cxf-rt-transports-http-jetty</artifactId>
+ <version>${cxf.version}</version>
+ </dependency>
+ </dependencies>
+
+ <build>
+ <defaultGoal>install</defaultGoal>
+
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <configuration>
+ <source>${maven.compiler.source}</source>
+ <target>${maven.compiler.target}</target>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <configuration>
+ <instructions>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Private-Package>${keycloak.osgi.private}</Private-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
+
+ </plugins>
+ </build>
+</project>
diff --git a/examples/fuse/cxf-jaxrs/src/main/java/org/keycloak/example/rs/CxfCustomerService.java b/examples/fuse/cxf-jaxrs/src/main/java/org/keycloak/example/rs/CxfCustomerService.java
new file mode 100644
index 0000000..c761556
--- /dev/null
+++ b/examples/fuse/cxf-jaxrs/src/main/java/org/keycloak/example/rs/CxfCustomerService.java
@@ -0,0 +1,30 @@
+package org.keycloak.example.rs;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.ws.rs.GET;
+import javax.ws.rs.Path;
+import javax.ws.rs.Produces;
+
+/**
+ * @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
+ * @version $Revision: 1 $
+ */
+@Path("/customers")
+public class CxfCustomerService {
+
+ @GET
+ @Produces("application/json")
+ public List<String> getCustomers() {
+ ArrayList<String> rtn = new ArrayList<String>();
+ rtn.add("Bill Burke");
+ rtn.add("Stian Thorgersen");
+ rtn.add("Stan Silvert");
+ rtn.add("Gabriel Cardoso");
+ rtn.add("Viliam Rockai");
+ rtn.add("Marek Posolda");
+ rtn.add("Boleslaw Dawidowicz");
+ return rtn;
+ }
+}
diff --git a/examples/fuse/cxf-jaxrs/src/main/resources/OSGI-INF/blueprint/blueprint.xml b/examples/fuse/cxf-jaxrs/src/main/resources/OSGI-INF/blueprint/blueprint.xml
new file mode 100644
index 0000000..1515416
--- /dev/null
+++ b/examples/fuse/cxf-jaxrs/src/main/resources/OSGI-INF/blueprint/blueprint.xml
@@ -0,0 +1,106 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xmlns:jaxrs="http://cxf.apache.org/blueprint/jaxrs"
+ xmlns:cm="http://aries.apache.org/blueprint/xmlns/blueprint-cm/v1.0.0"
+ xsi:schemaLocation="
+ http://www.osgi.org/xmlns/blueprint/v1.0.0 http://www.osgi.org/xmlns/blueprint/v1.0.0/blueprint.xsd
+ http://cxf.apache.org/jaxrs http://cxf.apache.org/schemas/blueprint/jaxrs.xsd
+ http://www.osgi.org/xmlns/blueprint/v1.0.0 http://www.osgi.org/xmlns/blueprint/v1.0.0/blueprint.xsd">
+
+ <!-- JAXRS Application -->
+
+ <bean id="customerBean" class="org.keycloak.example.rs.CxfCustomerService" />
+
+ <jaxrs:server id="cxfJaxrsServer" address="/customerservice">
+ <jaxrs:providers>
+ <!--<bean class="com.fasterxml.jackson.jaxrs.json.JacksonJsonProvider" />-->
+ <bean class="org.codehaus.jackson.jaxrs.JacksonJsonProvider" />
+ </jaxrs:providers>
+ <jaxrs:serviceBeans>
+ <ref component-id="customerBean" />
+ </jaxrs:serviceBeans>
+ </jaxrs:server>
+
+ <!-- Securing of whole /cxf context by unregister default cxf servlet from paxweb and re-register with applied security constraints -->
+
+ <cm:property-placeholder persistent-id="org.apache.cxf.osgi" id="cxfOsgiPropertiesKCSecured">
+ <cm:default-properties>
+ <cm:property name="org.apache.cxf.servlet.context" value="/cxf"/>
+ <cm:property name="org.apache.cxf.servlet.name" value="cxf-osgi-transport-servlet"/>
+ <cm:property name="org.apache.cxf.servlet.hide-service-list-page" value="false"/>
+ <cm:property name="org.apache.cxf.servlet.disable-address-updates" value="false"/>
+ <cm:property name="org.apache.cxf.servlet.base-address" value=""/>
+ <cm:property name="org.apache.cxf.servlet.service-list-path" value=""/>
+ <cm:property name="org.apache.cxf.servlet.static-resources-list" value=""/>
+ <cm:property name="org.apache.cxf.servlet.redirects-list" value=""/>
+ <cm:property name="org.apache.cxf.servlet.redirect-servlet-name" value=""/>
+ <cm:property name="org.apache.cxf.servlet.redirect-servlet-path" value=""/>
+ <cm:property name="org.apache.cxf.servlet.service-list-all-contexts" value=""/>
+ <cm:property name="org.apache.cxf.servlet.service-list-page-authenticate" value="false"/>
+ <cm:property name="org.apache.cxf.servlet.service-list-page-authenticate-realm" value="karaf"/>
+ </cm:default-properties>
+ </cm:property-placeholder>
+
+ <bean id="cxfConstraintMapping" class="org.eclipse.jetty.security.ConstraintMapping">
+ <property name="constraint">
+ <bean class="org.eclipse.jetty.util.security.Constraint">
+ <property name="name" value="cst1"/>
+ <property name="roles">
+ <list>
+ <value>user</value>
+ </list>
+ </property>
+ <property name="authenticate" value="true"/>
+ <property name="dataConstraint" value="0"/>
+ </bean>
+ </property>
+ <property name="pathSpec" value="/cxf/*"/>
+ </bean>
+
+ <bean id="cxfKeycloakPaxWebIntegration" class="org.keycloak.adapters.osgi.PaxWebIntegrationService"
+ init-method="start" destroy-method="stop">
+ <property name="bundleContext" ref="blueprintBundleContext" />
+ <property name="jettyWebXmlLocation" value="/WEB-INF/jetty-web.xml" />
+ <property name="constraintMappings">
+ <list>
+ <ref component-id="cxfConstraintMapping" />
+ </list>
+ </property>
+ </bean>
+
+ <bean id="defaultCxfUnregistration" class="org.keycloak.adapters.osgi.ServletUnregistrationService"
+ init-method="start" destroy-method="stop">
+ <property name="bundleContext" ref="blueprintBundleContext" />
+ <property name="servletReference">
+ <reference interface="javax.servlet.Servlet" component-name="osgiServlet" />
+ </property>
+ </bean>
+
+ <bean id="osgiServletKCSecured" class="org.apache.cxf.transport.servlet.CXFNonSpringServlet" depends-on="cxfKeycloakPaxWebIntegration defaultCxfUnregistration">
+ <argument>
+ <reference interface="org.apache.cxf.transport.http.DestinationRegistry" timeout="5000"/>
+ </argument>
+ <argument value="false"/>
+ </bean>
+
+ <service ref="osgiServletKCSecured" interface="javax.servlet.Servlet">
+ <service-properties>
+ <entry key="alias" value="${org.apache.cxf.servlet.context}"/>
+ <entry key="servlet-name" value="${org.apache.cxf.servlet.name}"/>
+ <entry key="hide-service-list-page" value="${org.apache.cxf.servlet.hide-service-list-page}"/>
+ <entry key="disable-address-updates" value="${org.apache.cxf.servlet.disable-address-updates}"/>
+ <entry key="base-address" value="${org.apache.cxf.servlet.base-address}"/>
+ <entry key="service-list-path" value="${org.apache.cxf.servlet.service-list-path}"/>
+ <entry key="static-resources-list" value="${org.apache.cxf.servlet.static-resources-list}"/>
+ <entry key="redirects-list" value="${org.apache.cxf.servlet.redirects-list}"/>
+ <entry key="redirect-servlet-name" value="${org.apache.cxf.servlet.redirect-servlet-name}"/>
+ <entry key="redirect-servlet-path" value="${org.apache.cxf.servlet.redirect-servlet-path}"/>
+ <entry key="service-list-all-contexts" value="${org.apache.cxf.servlet.service-list-all-contexts}"/>
+ <entry key="service-list-page-authenticate" value="${org.apache.cxf.servlet.service-list-page-authenticate}"/>
+ <entry key="service-list-page-authenticate-realm" value="${org.apache.cxf.servlet.service-list-page-authenticate-realm}"/>
+ </service-properties>
+ </service>
+
+
+</blueprint>
\ No newline at end of file
diff --git a/examples/fuse/cxf-jaxrs/src/main/resources/WEB-INF/jetty-web.xml b/examples/fuse/cxf-jaxrs/src/main/resources/WEB-INF/jetty-web.xml
new file mode 100644
index 0000000..e3d87a2
--- /dev/null
+++ b/examples/fuse/cxf-jaxrs/src/main/resources/WEB-INF/jetty-web.xml
@@ -0,0 +1,10 @@
+<?xml version="1.0"?>
+<!DOCTYPE Configure PUBLIC "-//Mort Bay Consulting//DTD Configure//EN" "http://www.eclipse.org/jetty/configure_9_0.dtd">
+<Configure class="org.eclipse.jetty.webapp.WebAppContext">
+ <Get name="securityHandler">
+ <Set name="authenticator">
+ <New class="org.keycloak.adapters.jetty.KeycloakJettyAuthenticator">
+ </New>
+ </Set>
+ </Get>
+</Configure>
\ No newline at end of file
diff --git a/examples/fuse/cxf-jaxrs/src/main/resources/WEB-INF/keycloak.json b/examples/fuse/cxf-jaxrs/src/main/resources/WEB-INF/keycloak.json
new file mode 100644
index 0000000..f5d7e1a
--- /dev/null
+++ b/examples/fuse/cxf-jaxrs/src/main/resources/WEB-INF/keycloak.json
@@ -0,0 +1,10 @@
+{
+ "realm": "demo",
+ "resource": "builtin-cxf-app",
+ "realm-public-key": "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCrVrCuTtArbgaZzL1hvh0xtL5mc7o0NqPVnYXkLvgcwiC3BjLGw1tGEGoJaXDuSaRllobm53JBhjx33UNv+5z/UMG4kytBWxheNVKnL6GgqlNabMaFfPLPCF8kAgKnsi79NMo+n6KnSY8YeUmec/p2vjO2NjsSAVcWEQMVhJ31LwIDAQAB",
+ "auth-server-url": "http://localhost:8080/auth",
+ "ssl-required" : "external",
+ "credentials": {
+ "secret": "password"
+ }
+}
examples/fuse/cxf-jaxws/pom.xml 107(+107 -0)
diff --git a/examples/fuse/cxf-jaxws/pom.xml b/examples/fuse/cxf-jaxws/pom.xml
new file mode 100644
index 0000000..51ba1a4
--- /dev/null
+++ b/examples/fuse/cxf-jaxws/pom.xml
@@ -0,0 +1,107 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <parent>
+ <artifactId>keycloak-parent</artifactId>
+ <groupId>org.keycloak</groupId>
+ <version>1.1.0.Final-SNAPSHOT</version>
+ <relativePath>../../../pom.xml</relativePath>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.keycloak.example.demo</groupId>
+ <artifactId>cxf-jaxws-example</artifactId>
+ <packaging>bundle</packaging>
+ <name>CXF JAXWS Example - Secured in Karaf/Fuse</name>
+ <description/>
+
+ <properties>
+ <cxf.version>2.7.14</cxf.version>
+ <keycloak.osgi.export>
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ javax.jws;resolution:=optional,
+ javax.wsdl,
+ javax.xml.bind,
+ javax.xml.bind.annotation,
+ javax.xml.namespace,
+ javax.xml.ws,
+ META-INF.cxf,
+ META-INF.cxf.osgi,
+ org.apache.cxf.bus,
+ org.apache.cxf.bus.spring,
+ org.apache.cxf.bus.resource,
+ org.apache.cxf.configuration.spring,
+ org.apache.cxf.resource,
+ org.apache.cxf.jaxws,
+ org.apache.cxf.transport.http,
+ org.springframework.beans.factory.config,
+ *;resolution:=optional
+ </keycloak.osgi.import>
+ <keycloak.osgi.private>
+ org.keycloak.example.ws.*
+ </keycloak.osgi.private>
+ </properties>
+
+ <dependencies>
+ <dependency>
+ <groupId>org.apache.geronimo.specs</groupId>
+ <artifactId>geronimo-ws-metadata_2.0_spec</artifactId>
+ <version>1.1.2</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.geronimo.specs</groupId>
+ <artifactId>geronimo-jaxws_2.2_spec</artifactId>
+ <version>1.0</version>
+ </dependency>
+ <dependency>
+ <groupId>javax.xml.bind</groupId>
+ <artifactId>jaxb-api</artifactId>
+ <version>2.2</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.cxf</groupId>
+ <artifactId>cxf-rt-frontend-jaxws</artifactId>
+ <version>${cxf.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.cxf</groupId>
+ <artifactId>cxf-rt-transports-http</artifactId>
+ <version>${cxf.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.cxf</groupId>
+ <artifactId>cxf-rt-transports-http-jetty</artifactId>
+ <version>${cxf.version}</version>
+ </dependency>
+ </dependencies>
+
+ <build>
+ <defaultGoal>install</defaultGoal>
+
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <configuration>
+ <source>${maven.compiler.source}</source>
+ <target>${maven.compiler.target}</target>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <configuration>
+ <instructions>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Private-Package>${keycloak.osgi.private}</Private-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
+
+ </plugins>
+ </build>
+</project>
diff --git a/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/Person.java b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/Person.java
new file mode 100644
index 0000000..24926e0
--- /dev/null
+++ b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/Person.java
@@ -0,0 +1,27 @@
+package org.keycloak.example.ws;
+
+import javax.jws.WebMethod;
+import javax.jws.WebParam;
+import javax.jws.WebService;
+import javax.xml.bind.annotation.XmlSeeAlso;
+import javax.xml.ws.RequestWrapper;
+import javax.xml.ws.ResponseWrapper;
+
+import org.keycloak.example.ws.types.ObjectFactory;
+
+@WebService
+@XmlSeeAlso({ObjectFactory.class})
+public interface Person {
+
+ @RequestWrapper(localName = "GetPerson", className = "GetPerson")
+ @ResponseWrapper(localName = "GetPersonResponse", className = "GetPersonResponse")
+ @WebMethod(operationName = "GetPerson")
+ public void getPerson(
+ @WebParam(mode = WebParam.Mode.INOUT, name = "personId")
+ javax.xml.ws.Holder<String> personId,
+ @WebParam(mode = WebParam.Mode.OUT, name = "ssn")
+ javax.xml.ws.Holder<String> ssn,
+ @WebParam(mode = WebParam.Mode.OUT, name = "name")
+ javax.xml.ws.Holder<String> name
+ ) throws UnknownPersonFault;
+}
diff --git a/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/PersonImpl.java b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/PersonImpl.java
new file mode 100644
index 0000000..dcaf738
--- /dev/null
+++ b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/PersonImpl.java
@@ -0,0 +1,22 @@
+package org.keycloak.example.ws;
+
+import javax.jws.WebService;
+import javax.xml.ws.Holder;
+
+@WebService(serviceName = "PersonService", endpointInterface = "org.keycloak.example.ws.Person")
+public class PersonImpl implements Person {
+
+ public void getPerson(Holder<String> personId, Holder<String> ssn, Holder<String> name)
+ throws UnknownPersonFault
+ {
+ if (personId.value == null || personId.value.length() == 0) {
+ org.keycloak.example.ws.types.UnknownPersonFault fault = new org.keycloak.example.ws.types.UnknownPersonFault();
+ fault.setPersonId(personId.value);
+ throw new UnknownPersonFault(null,fault);
+ } else {
+ name.value = "John Doe";
+ ssn.value = "123-456-7890";
+ }
+ }
+
+}
diff --git a/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/GetPerson.java b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/GetPerson.java
new file mode 100644
index 0000000..2101b1b
--- /dev/null
+++ b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/GetPerson.java
@@ -0,0 +1,64 @@
+
+package org.keycloak.example.ws.types;
+
+import javax.xml.bind.annotation.XmlAccessType;
+import javax.xml.bind.annotation.XmlAccessorType;
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlRootElement;
+import javax.xml.bind.annotation.XmlType;
+
+
+/**
+ * <p>Java class for anonymous complex type.
+ *
+ * <p>The following schema fragment specifies the expected content contained within this class.
+ *
+ * <pre>
+ * <complexType>
+ * <complexContent>
+ * <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ * <sequence>
+ * <element name="personId" type="{http://www.w3.org/2001/XMLSchema}string"/>
+ * </sequence>
+ * </restriction>
+ * </complexContent>
+ * </complexType>
+ * </pre>
+ *
+ *
+ */
+@XmlAccessorType(XmlAccessType.FIELD)
+@XmlType(name = "", propOrder = {
+ "personId"
+})
+@XmlRootElement(name = "GetPerson")
+public class GetPerson {
+
+ @XmlElement(required = true)
+ protected String personId;
+
+ /**
+ * Gets the value of the personId property.
+ *
+ * @return
+ * possible object is
+ * {@link String }
+ *
+ */
+ public String getPersonId() {
+ return personId;
+ }
+
+ /**
+ * Sets the value of the personId property.
+ *
+ * @param value
+ * allowed object is
+ * {@link String }
+ *
+ */
+ public void setPersonId(String value) {
+ this.personId = value;
+ }
+
+}
diff --git a/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/GetPersonResponse.java b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/GetPersonResponse.java
new file mode 100644
index 0000000..fac5e6f
--- /dev/null
+++ b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/GetPersonResponse.java
@@ -0,0 +1,120 @@
+
+package org.keycloak.example.ws.types;
+
+import javax.xml.bind.annotation.XmlAccessType;
+import javax.xml.bind.annotation.XmlAccessorType;
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlRootElement;
+import javax.xml.bind.annotation.XmlType;
+
+
+/**
+ * <p>Java class for anonymous complex type.
+ *
+ * <p>The following schema fragment specifies the expected content contained within this class.
+ *
+ * <pre>
+ * <complexType>
+ * <complexContent>
+ * <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ * <sequence>
+ * <element name="personId" type="{http://www.w3.org/2001/XMLSchema}string"/>
+ * <element name="ssn" type="{http://www.w3.org/2001/XMLSchema}string"/>
+ * <element name="name" type="{http://www.w3.org/2001/XMLSchema}string"/>
+ * </sequence>
+ * </restriction>
+ * </complexContent>
+ * </complexType>
+ * </pre>
+ *
+ *
+ */
+@XmlAccessorType(XmlAccessType.FIELD)
+@XmlType(name = "", propOrder = {
+ "personId",
+ "ssn",
+ "name"
+})
+@XmlRootElement(name = "GetPersonResponse")
+public class GetPersonResponse {
+
+ @XmlElement(required = true)
+ protected String personId;
+ @XmlElement(required = true)
+ protected String ssn;
+ @XmlElement(required = true)
+ protected String name;
+
+ /**
+ * Gets the value of the personId property.
+ *
+ * @return
+ * possible object is
+ * {@link String }
+ *
+ */
+ public String getPersonId() {
+ return personId;
+ }
+
+ /**
+ * Sets the value of the personId property.
+ *
+ * @param value
+ * allowed object is
+ * {@link String }
+ *
+ */
+ public void setPersonId(String value) {
+ this.personId = value;
+ }
+
+ /**
+ * Gets the value of the ssn property.
+ *
+ * @return
+ * possible object is
+ * {@link String }
+ *
+ */
+ public String getSsn() {
+ return ssn;
+ }
+
+ /**
+ * Sets the value of the ssn property.
+ *
+ * @param value
+ * allowed object is
+ * {@link String }
+ *
+ */
+ public void setSsn(String value) {
+ this.ssn = value;
+ }
+
+ /**
+ * Gets the value of the name property.
+ *
+ * @return
+ * possible object is
+ * {@link String }
+ *
+ */
+ public String getName() {
+ return name;
+ }
+
+ /**
+ * Sets the value of the name property.
+ *
+ * @param value
+ * allowed object is
+ * {@link String }
+ *
+ */
+ public void setName(String value) {
+ this.name = value;
+ }
+
+}
diff --git a/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/ObjectFactory.java b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/ObjectFactory.java
new file mode 100644
index 0000000..dd2e74d
--- /dev/null
+++ b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/ObjectFactory.java
@@ -0,0 +1,56 @@
+
+package org.keycloak.example.ws.types;
+
+import javax.xml.bind.annotation.XmlRegistry;
+
+
+/**
+ * This object contains factory methods for each
+ * Java content interface and Java element interface
+ * generated in the org.apache.servicemix.samples.wsdl_first.types package.
+ * <p>An ObjectFactory allows you to programatically
+ * construct new instances of the Java representation
+ * for XML content. The Java representation of XML
+ * content can consist of schema derived interfaces
+ * and classes representing the binding of schema
+ * type definitions, element declarations and model
+ * groups. Factory methods for each of these are
+ * provided in this class.
+ *
+ */
+@XmlRegistry
+public class ObjectFactory {
+
+
+ /**
+ * Create a new ObjectFactory that can be used to create new instances of schema derived classes for package: org.apache.servicemix.samples.wsdl_first.types
+ *
+ */
+ public ObjectFactory() {
+ }
+
+ /**
+ * Create an instance of {@link GetPersonResponse }
+ *
+ */
+ public GetPersonResponse createGetPersonResponse() {
+ return new GetPersonResponse();
+ }
+
+ /**
+ * Create an instance of {@link GetPerson }
+ *
+ */
+ public GetPerson createGetPerson() {
+ return new GetPerson();
+ }
+
+ /**
+ * Create an instance of {@link UnknownPersonFault }
+ *
+ */
+ public UnknownPersonFault createUnknownPersonFault() {
+ return new UnknownPersonFault();
+ }
+
+}
diff --git a/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/package-info.java b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/package-info.java
new file mode 100644
index 0000000..877c2df
--- /dev/null
+++ b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/package-info.java
@@ -0,0 +1 @@
+package org.keycloak.example.ws.types;
diff --git a/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/UnknownPersonFault.java b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/UnknownPersonFault.java
new file mode 100644
index 0000000..ba40a42
--- /dev/null
+++ b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/types/UnknownPersonFault.java
@@ -0,0 +1,64 @@
+
+package org.keycloak.example.ws.types;
+
+import javax.xml.bind.annotation.XmlAccessType;
+import javax.xml.bind.annotation.XmlAccessorType;
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlRootElement;
+import javax.xml.bind.annotation.XmlType;
+
+
+/**
+ * <p>Java class for anonymous complex type.
+ *
+ * <p>The following schema fragment specifies the expected content contained within this class.
+ *
+ * <pre>
+ * <complexType>
+ * <complexContent>
+ * <restriction base="{http://www.w3.org/2001/XMLSchema}anyType">
+ * <sequence>
+ * <element name="personId" type="{http://www.w3.org/2001/XMLSchema}string"/>
+ * </sequence>
+ * </restriction>
+ * </complexContent>
+ * </complexType>
+ * </pre>
+ *
+ *
+ */
+@XmlAccessorType(XmlAccessType.FIELD)
+@XmlType(name = "", propOrder = {
+ "personId"
+})
+@XmlRootElement(name = "UnknownPersonFault")
+public class UnknownPersonFault {
+
+ @XmlElement(required = true)
+ protected String personId;
+
+ /**
+ * Gets the value of the personId property.
+ *
+ * @return
+ * possible object is
+ * {@link String }
+ *
+ */
+ public String getPersonId() {
+ return personId;
+ }
+
+ /**
+ * Sets the value of the personId property.
+ *
+ * @param value
+ * allowed object is
+ * {@link String }
+ *
+ */
+ public void setPersonId(String value) {
+ this.personId = value;
+ }
+
+}
diff --git a/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/UnknownPersonFault.java b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/UnknownPersonFault.java
new file mode 100644
index 0000000..f013657
--- /dev/null
+++ b/examples/fuse/cxf-jaxws/src/main/java/org/keycloak/example/ws/UnknownPersonFault.java
@@ -0,0 +1,36 @@
+package org.keycloak.example.ws;
+
+import javax.xml.ws.WebFault;
+
+@WebFault(name = "UnknownPersonFault")
+public class UnknownPersonFault extends Exception {
+ public static final long serialVersionUID = 20081110144906L;
+
+ private org.keycloak.example.ws.types.UnknownPersonFault unknownPersonFault;
+
+ public UnknownPersonFault() {
+ super();
+ }
+
+ public UnknownPersonFault(String message) {
+ super(message);
+ }
+
+ public UnknownPersonFault(String message, Throwable cause) {
+ super(message, cause);
+ }
+
+ public UnknownPersonFault(String message, org.keycloak.example.ws.types.UnknownPersonFault unknownPersonFault) {
+ super(message);
+ this.unknownPersonFault = unknownPersonFault;
+ }
+
+ public UnknownPersonFault(String message, org.keycloak.example.ws.types.UnknownPersonFault unknownPersonFault, Throwable cause) {
+ super(message, cause);
+ this.unknownPersonFault = unknownPersonFault;
+ }
+
+ public org.keycloak.example.ws.types.UnknownPersonFault getFaultInfo() {
+ return this.unknownPersonFault;
+ }
+}
diff --git a/examples/fuse/cxf-jaxws/src/main/resources/META-INF/spring/beans.xml b/examples/fuse/cxf-jaxws/src/main/resources/META-INF/spring/beans.xml
new file mode 100644
index 0000000..57a7eee
--- /dev/null
+++ b/examples/fuse/cxf-jaxws/src/main/resources/META-INF/spring/beans.xml
@@ -0,0 +1,69 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Generated by Apache ServiceMix Archetype -->
+<beans xmlns="http://www.springframework.org/schema/beans"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xmlns:jaxws="http://cxf.apache.org/jaxws"
+ xmlns:httpj="http://cxf.apache.org/transports/http-jetty/configuration"
+ xsi:schemaLocation="
+ http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
+ http://cxf.apache.org/jaxws http://cxf.apache.org/schemas/jaxws.xsd
+ http://www.springframework.org/schema/osgi http://www.springframework.org/schema/osgi/spring-osgi.xsd
+ http://cxf.apache.org/transports/http-jetty/configuration http://cxf.apache.org/schemas/configuration/http-jetty.xsd">
+
+ <import resource="classpath:META-INF/cxf/cxf.xml" />
+
+ <bean id="kcAdapterConfig" class="org.keycloak.representations.adapters.config.AdapterConfig">
+ <property name="realm" value="demo"/>
+ <property name="resource" value="custom-cxf-endpoint"/>
+ <property name="realmKey" value="MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCrVrCuTtArbgaZzL1hvh0xtL5mc7o0NqPVnYXkLvgcwiC3BjLGw1tGEGoJaXDuSaRllobm53JBhjx33UNv+5z/UMG4kytBWxheNVKnL6GgqlNabMaFfPLPCF8kAgKnsi79NMo+n6KnSY8YeUmec/p2vjO2NjsSAVcWEQMVhJ31LwIDAQAB"/>
+ <property name="bearerOnly" value="true"/>
+ <property name="sslRequired" value="EXTERNAL"/>
+ </bean>
+
+ <bean id="keycloakAuthenticator" class="org.keycloak.adapters.jetty.KeycloakJettyAuthenticator">
+ <property name="adapterConfig">
+ <ref local="kcAdapterConfig" />
+ </property>
+ </bean>
+
+ <bean id="constraint" class="org.eclipse.jetty.util.security.Constraint">
+ <property name="name" value="Customers"/>
+ <property name="roles">
+ <list>
+ <value>user</value>
+ </list>
+ </property>
+ <property name="authenticate" value="true"/>
+ <property name="dataConstraint" value="0"/>
+ </bean>
+
+ <bean id="constraintMapping" class="org.eclipse.jetty.security.ConstraintMapping">
+ <property name="constraint" ref="constraint"/>
+ <property name="pathSpec" value="/*"/>
+ </bean>
+
+ <bean id="securityHandler" class="org.eclipse.jetty.security.ConstraintSecurityHandler">
+ <property name="authenticator" ref="keycloakAuthenticator" />
+ <property name="constraintMappings">
+ <list>
+ <ref local="constraintMapping" />
+ </list>
+ </property>
+ <property name="authMethod" value="BASIC"/>
+ <property name="realmName" value="does-not-matter"/>
+ </bean>
+
+ <httpj:engine-factory bus="cxf" id="kc-cxf-endpoint">
+ <httpj:engine port="8282">
+ <httpj:handlers>
+ <ref local="securityHandler" />
+ </httpj:handlers>
+ <httpj:sessionSupport>true</httpj:sessionSupport>
+ </httpj:engine>
+ </httpj:engine-factory>
+
+ <jaxws:endpoint
+ implementor="org.keycloak.example.ws.PersonImpl"
+ address="http://localhost:8282/PersonServiceCF" depends-on="kc-cxf-endpoint"/>
+
+</beans>
\ No newline at end of file
examples/fuse/features/pom.xml 62(+62 -0)
diff --git a/examples/fuse/features/pom.xml b/examples/fuse/features/pom.xml
new file mode 100644
index 0000000..f86e711
--- /dev/null
+++ b/examples/fuse/features/pom.xml
@@ -0,0 +1,62 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <parent>
+ <artifactId>keycloak-parent</artifactId>
+ <groupId>org.keycloak</groupId>
+ <version>1.1.0.Final-SNAPSHOT</version>
+ <relativePath>../../../pom.xml</relativePath>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.keycloak.example.demo</groupId>
+ <artifactId>keycloak-fuse-example-features</artifactId>
+ <name>Keycloak Fuse Example - Features</name>
+ <description/>
+
+ <build>
+ <resources>
+ <resource>
+ <directory>src/main/resources</directory>
+ <filtering>true</filtering>
+ </resource>
+ </resources>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-resources-plugin</artifactId>
+ <executions>
+ <execution>
+ <id>filter</id>
+ <phase>generate-resources</phase>
+ <goals>
+ <goal>resources</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin>
+ <plugin>
+ <groupId>org.codehaus.mojo</groupId>
+ <artifactId>build-helper-maven-plugin</artifactId>
+ <executions>
+ <execution>
+ <id>attach-artifacts</id>
+ <phase>package</phase>
+ <goals>
+ <goal>attach-artifact</goal>
+ </goals>
+ <configuration>
+ <artifacts>
+ <artifact>
+ <file>target/classes/features.xml</file>
+ <type>xml</type>
+ <classifier>features</classifier>
+ </artifact>
+ </artifacts>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ </plugins>
+ </build>
+
+</project>
\ No newline at end of file
diff --git a/examples/fuse/features/src/main/resources/features.xml b/examples/fuse/features/src/main/resources/features.xml
new file mode 100644
index 0000000..f888574
--- /dev/null
+++ b/examples/fuse/features/src/main/resources/features.xml
@@ -0,0 +1,19 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<features xmlns="http://karaf.apache.org/xmlns/features/v1.0.0" name="keycloak-${project.version}">
+
+ <feature name="keycloak-fuse-example" version="${project.version}">
+ <details>The keycloak fuse example</details>
+ <feature>war</feature>
+ <feature>camel</feature>
+ <feature>camel-jetty</feature>
+ <feature>cxf</feature>
+ <feature>keycloak</feature>
+ <bundle dependency="true">mvn:org.codehaus.jackson/jackson-jaxrs/${jackson.version}</bundle>
+ <bundle>mvn:org.keycloak.example.demo/product-portal-fuse-example/${project.version}</bundle>
+ <bundle>mvn:org.keycloak.example.demo/customer-portal-fuse-example/${project.version}/war</bundle>
+ <bundle>mvn:org.keycloak.example.demo/camel-endpoint-example/${project.version}</bundle>
+ <bundle>mvn:org.keycloak.example.demo/cxf-jaxws-example/${project.version}</bundle>
+ <bundle>mvn:org.keycloak.example.demo/cxf-jaxrs-example/${project.version}</bundle>
+ </feature>
+
+</features>
\ No newline at end of file
examples/fuse/pom.xml 37(+37 -0)
diff --git a/examples/fuse/pom.xml b/examples/fuse/pom.xml
new file mode 100644
index 0000000..db54315
--- /dev/null
+++ b/examples/fuse/pom.xml
@@ -0,0 +1,37 @@
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <parent>
+ <artifactId>keycloak-parent</artifactId>
+ <groupId>org.keycloak</groupId>
+ <version>1.1.0.Final-SNAPSHOT</version>
+ <relativePath>../../pom.xml</relativePath>
+ </parent>
+ <name>Fuse examples</name>
+ <description/>
+ <modelVersion>4.0.0</modelVersion>
+
+ <artifactId>fuse-pom</artifactId>
+ <packaging>pom</packaging>
+
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-deploy-plugin</artifactId>
+ <configuration>
+ <skip>true</skip>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+
+ <modules>
+ <module>customer-app-fuse</module>
+ <module>product-app-fuse</module>
+ <module>cxf-jaxrs</module>
+ <module>cxf-jaxws</module>
+ <module>camel</module>
+ <module>features</module>
+ </modules>
+
+</project>
\ No newline at end of file
examples/fuse/product-app-fuse/pom.xml 83(+83 -0)
diff --git a/examples/fuse/product-app-fuse/pom.xml b/examples/fuse/product-app-fuse/pom.xml
new file mode 100644
index 0000000..d5ed253
--- /dev/null
+++ b/examples/fuse/product-app-fuse/pom.xml
@@ -0,0 +1,83 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <parent>
+ <artifactId>keycloak-parent</artifactId>
+ <groupId>org.keycloak</groupId>
+ <version>1.1.0.Final-SNAPSHOT</version>
+ <relativePath>../../../pom.xml</relativePath>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+ <groupId>org.keycloak.example.demo</groupId>
+ <artifactId>product-portal-fuse-example</artifactId>
+ <packaging>bundle</packaging>
+
+ <name>Product Portal - Secured in Karaf/Fuse</name>
+ <description/>
+
+ <properties>
+ <keycloak.osgi.export>
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ org.eclipse.jetty.security;version="[8.1,10)",
+ org.eclipse.jetty.util.security;version="[8.1,10)",
+ org.keycloak.adapters.jetty;version="${project.version}",
+ org.keycloak.*;version="${project.version}",
+ *;resolution:=optional
+ </keycloak.osgi.import>
+ <keycloak.osgi.private>
+ org.keycloak.example.*
+ </keycloak.osgi.private>
+ </properties>
+
+ <dependencies>
+ <dependency>
+ <groupId>org.jboss.spec.javax.servlet</groupId>
+ <artifactId>jboss-servlet-api_3.0_spec</artifactId>
+ </dependency>
+ <dependency>
+ <groupId>org.keycloak</groupId>
+ <artifactId>keycloak-core</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+
+ <!-- Dependency for jaxws client to allow sending request to jaxws endpoint provided by cxf-jaxws-example -->
+ <dependency>
+ <groupId>org.keycloak.example.demo</groupId>
+ <artifactId>cxf-jaxws-example</artifactId>
+ <version>${project.version}</version>
+ </dependency>
+ </dependencies>
+
+ <build>
+ <defaultGoal>install</defaultGoal>
+
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <configuration>
+ <source>${maven.compiler.source}</source>
+ <target>${maven.compiler.target}</target>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <configuration>
+ <instructions>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Private-Package>${keycloak.osgi.private}</Private-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ <Require-Bundle>org.apache.cxf.bundle</Require-Bundle>
+ </instructions>
+ </configuration>
+ </plugin>
+
+ </plugins>
+ </build>
+
+</project>
diff --git a/examples/fuse/product-app-fuse/src/main/java/org/keycloak/example/ProductPortalServlet.java b/examples/fuse/product-app-fuse/src/main/java/org/keycloak/example/ProductPortalServlet.java
new file mode 100644
index 0000000..85ecc42
--- /dev/null
+++ b/examples/fuse/product-app-fuse/src/main/java/org/keycloak/example/ProductPortalServlet.java
@@ -0,0 +1,95 @@
+package org.keycloak.example;
+
+import java.io.IOException;
+import java.io.PrintWriter;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import javax.servlet.ServletException;
+import javax.servlet.http.HttpServlet;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+import javax.xml.ws.WebServiceException;
+
+import org.apache.cxf.endpoint.Client;
+import org.apache.cxf.frontend.ClientProxy;
+import org.apache.cxf.jaxws.JaxWsProxyFactoryBean;
+import org.apache.cxf.message.Message;
+import org.keycloak.KeycloakSecurityContext;
+import org.keycloak.constants.ServiceUrlConstants;
+import org.keycloak.example.ws.Person;
+import org.keycloak.example.ws.UnknownPersonFault;
+import org.keycloak.util.KeycloakUriBuilder;
+
+/**
+ * Servlet for receiving informations about products from backend JAXWS service. Actually it's about "persons" not "products" :)
+ *
+ * @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
+ */
+public class ProductPortalServlet extends HttpServlet {
+
+ @Override
+ protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
+ resp.setContentType("text/html");
+
+ // Send jaxws request
+ PrintWriter out = resp.getWriter();
+ out.println("<html><head><title>Product Portal Page</title></head><body>");
+
+ String logoutUri = KeycloakUriBuilder.fromUri("http://localhost:8080/auth").path(ServiceUrlConstants.TOKEN_SERVICE_LOGOUT_PATH)
+ .queryParam("redirect_uri", "http://localhost:8181/product-portal").build("demo").toString();
+ String acctUri = KeycloakUriBuilder.fromUri("http://localhost:8080/auth").path(ServiceUrlConstants.ACCOUNT_SERVICE_PATH)
+ .queryParam("referrer", "product-portal").build("demo").toString();
+
+ out.println("<p>Goto: <a href=\"/customer-portal\">customers</a> | <a href=\"" + logoutUri + "\">logout</a> | <a href=\"" + acctUri + "\">manage acct</a></p>");
+ out.println("Servlet User Principal <b>" + req.getUserPrincipal() + "</b> made this request.");
+
+ String unsecuredWsClientResponse = sendWsReq(req, false);
+ String securedWsClientResponse = sendWsReq(req, true);
+
+ out.println("<p>Person with ID 1 - unsecured request: <b>" + unsecuredWsClientResponse + "</b></p>");
+ out.println("<p>Person with ID 1 - secured request: <b>" + securedWsClientResponse + "</b></p>");
+ out.println("</body></html>");
+ out.flush();
+ out.close();
+ }
+
+ private String sendWsReq(HttpServletRequest req, boolean secured) {
+ JaxWsProxyFactoryBean factory = new JaxWsProxyFactoryBean();
+ factory.setServiceClass(Person.class);
+ factory.setAddress("http://localhost:8282/PersonServiceCF");
+
+ Person simpleClient = (Person)factory.create();
+ java.lang.String _getPerson_personIdVal = "1";
+ javax.xml.ws.Holder<java.lang.String> _getPerson_personId = new javax.xml.ws.Holder<java.lang.String>(_getPerson_personIdVal);
+ javax.xml.ws.Holder<java.lang.String> _getPerson_ssn = new javax.xml.ws.Holder<java.lang.String>();
+ javax.xml.ws.Holder<java.lang.String> _getPerson_name = new javax.xml.ws.Holder<java.lang.String>();
+
+ // Attach Authorization header
+ if (secured) {
+ Client clientProxy = ClientProxy.getClient(simpleClient);
+
+ KeycloakSecurityContext session = (KeycloakSecurityContext) req.getAttribute(KeycloakSecurityContext.class.getName());
+ Map<String, List<String>> headers = new HashMap<String, List<String>>();
+ headers.put("Authorization", Arrays.asList("Bearer " + session.getTokenString()));
+
+ clientProxy.getRequestContext().put(Message.PROTOCOL_HEADERS, headers);
+ }
+
+ try {
+ simpleClient.getPerson(_getPerson_personId, _getPerson_ssn, _getPerson_name);
+ return String.format("Person received: id=%s, name=%s, ssn=%s", _getPerson_personId.value, _getPerson_name.value, _getPerson_ssn.value);
+ } catch (UnknownPersonFault upf) {
+ return "UnknownPersonFault has occurred. Details: " + upf.toString();
+ } catch (WebServiceException wse) {
+ String error = "Can't receive person. Reason: " + wse.getMessage();
+ if (wse.getCause() != null) {
+ Throwable cause = wse.getCause();
+ error = error + " Details: " + cause.getClass().getName() + ": " + cause.getMessage();
+ }
+ return error;
+ }
+ }
+}
diff --git a/examples/fuse/product-app-fuse/src/main/resources/OSGI-INF/blueprint/blueprint.xml b/examples/fuse/product-app-fuse/src/main/resources/OSGI-INF/blueprint/blueprint.xml
new file mode 100644
index 0000000..e6b0757
--- /dev/null
+++ b/examples/fuse/product-app-fuse/src/main/resources/OSGI-INF/blueprint/blueprint.xml
@@ -0,0 +1,45 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://www.osgi.org/xmlns/blueprint/v1.0.0 http://www.osgi.org/xmlns/blueprint/v1.0.0/blueprint.xsd">
+
+ <!-- USing jetty bean just for the compatibility with other fuse services -->
+ <bean id="servletConstraintMapping" class="org.eclipse.jetty.security.ConstraintMapping">
+ <property name="constraint">
+ <bean class="org.eclipse.jetty.util.security.Constraint">
+ <property name="name" value="cst1"/>
+ <property name="roles">
+ <list>
+ <value>user</value>
+ </list>
+ </property>
+ <property name="authenticate" value="true"/>
+ <property name="dataConstraint" value="0"/>
+ </bean>
+ </property>
+ <property name="pathSpec" value="/product-portal/*"/>
+ </bean>
+
+ <bean id="keycloakPaxWebIntegration" class="org.keycloak.adapters.osgi.PaxWebIntegrationService"
+ init-method="start" destroy-method="stop">
+ <property name="jettyWebXmlLocation" value="/WEB-INF/jetty-web.xml" />
+ <property name="bundleContext" ref="blueprintBundleContext" />
+ <property name="constraintMappings">
+ <list>
+ <ref component-id="servletConstraintMapping" />
+ </list>
+ </property>
+ </bean>
+
+ <bean id="productServlet" class="org.keycloak.example.ProductPortalServlet" depends-on="keycloakPaxWebIntegration">
+ </bean>
+
+ <service ref="productServlet" interface="javax.servlet.Servlet">
+ <service-properties>
+ <entry key="alias" value="/product-portal" />
+ <entry key="servlet-name" value="ProductServlet" />
+ <entry key="keycloak.config.file" value="/keycloak.json" />
+ </service-properties>
+ </service>
+
+</blueprint>
\ No newline at end of file
diff --git a/examples/fuse/product-app-fuse/src/main/resources/WEB-INF/jetty-web.xml b/examples/fuse/product-app-fuse/src/main/resources/WEB-INF/jetty-web.xml
new file mode 100644
index 0000000..e3d87a2
--- /dev/null
+++ b/examples/fuse/product-app-fuse/src/main/resources/WEB-INF/jetty-web.xml
@@ -0,0 +1,10 @@
+<?xml version="1.0"?>
+<!DOCTYPE Configure PUBLIC "-//Mort Bay Consulting//DTD Configure//EN" "http://www.eclipse.org/jetty/configure_9_0.dtd">
+<Configure class="org.eclipse.jetty.webapp.WebAppContext">
+ <Get name="securityHandler">
+ <Set name="authenticator">
+ <New class="org.keycloak.adapters.jetty.KeycloakJettyAuthenticator">
+ </New>
+ </Set>
+ </Get>
+</Configure>
\ No newline at end of file
diff --git a/examples/fuse/product-app-fuse/src/main/resources/WEB-INF/keycloak.json b/examples/fuse/product-app-fuse/src/main/resources/WEB-INF/keycloak.json
new file mode 100644
index 0000000..2a52d24
--- /dev/null
+++ b/examples/fuse/product-app-fuse/src/main/resources/WEB-INF/keycloak.json
@@ -0,0 +1,10 @@
+{
+ "realm": "demo",
+ "resource": "product-portal",
+ "realm-public-key": "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCrVrCuTtArbgaZzL1hvh0xtL5mc7o0NqPVnYXkLvgcwiC3BjLGw1tGEGoJaXDuSaRllobm53JBhjx33UNv+5z/UMG4kytBWxheNVKnL6GgqlNabMaFfPLPCF8kAgKnsi79NMo+n6KnSY8YeUmec/p2vjO2NjsSAVcWEQMVhJ31LwIDAQAB",
+ "auth-server-url": "http://localhost:8080/auth",
+ "ssl-required" : "external",
+ "credentials": {
+ "secret": "password"
+ }
+}
examples/fuse/README.md 33(+33 -0)
diff --git a/examples/fuse/README.md b/examples/fuse/README.md
new file mode 100644
index 0000000..20593e2
--- /dev/null
+++ b/examples/fuse/README.md
@@ -0,0 +1,33 @@
+1) First step is to run Keycloak server on localhost:8080 and import realm "demo" from the file testrealm.json in this directory (Directory "fuse").
+
+Running example on Karaf 3.0.2
+------------------------------
+
+feature:repo-add mvn:org.apache.camel.karaf/apache-camel/2.12.5/xml/features
+feature:repo-add mvn:org.apache.cxf.karaf/apache-cxf/2.7.14/xml/features
+feature:repo-add mvn:org.keycloak/keycloak-osgi-features/1.1.0.Final/xml/features
+feature:repo-add mvn:org.keycloak.example.demo/keycloak-fuse-example-features/1.1.0.Final/xml/features
+feature:install keycloak-fuse-example
+
+Running example on JBoss Fuse 6.1.0.redhat-379
+----------------------------------------------
+
+features:uninstall pax-war
+features:uninstall pax-http-whiteboard
+features:uninstall pax-http
+features:uninstall pax-jetty
+features:removeurl mvn:org.ops4j.pax.web/pax-web-features/3.0.6/xml/features
+features:addurl mvn:org.ops4j.pax.web/pax-web-features/3.1.2/xml/features
+
+features:addurl mvn:org.keycloak/keycloak-osgi-features/1.1.0.Final/xml/features
+features:addurl mvn:org.keycloak.example.demo/keycloak-fuse-example-features/1.1.0.Final/xml/features
+
+features:install keycloak-pax-web-upgrade
+features:install pax-http-whiteboard/3.1.2
+features:install pax-war/3.1.2
+
+features:uninstall cxf
+features:install cxf
+
+features:install keycloak-fuse-example
+
examples/fuse/testrealm.json 137(+137 -0)
diff --git a/examples/fuse/testrealm.json b/examples/fuse/testrealm.json
new file mode 100644
index 0000000..7ac0319
--- /dev/null
+++ b/examples/fuse/testrealm.json
@@ -0,0 +1,137 @@
+{
+ "realm": "demo",
+ "enabled": true,
+ "accessTokenLifespan": 60,
+ "accessCodeLifespan": 60,
+ "accessCodeLifespanUserAction": 300,
+ "ssoSessionIdleTimeout": 600,
+ "ssoSessionMaxLifespan": 36000,
+ "passwordCredentialGrantAllowed": true,
+ "sslRequired": "external",
+ "registrationAllowed": false,
+ "social": false,
+ "updateProfileOnInitialSocialLogin": false,
+ "privateKey": "MIICXAIBAAKBgQCrVrCuTtArbgaZzL1hvh0xtL5mc7o0NqPVnYXkLvgcwiC3BjLGw1tGEGoJaXDuSaRllobm53JBhjx33UNv+5z/UMG4kytBWxheNVKnL6GgqlNabMaFfPLPCF8kAgKnsi79NMo+n6KnSY8YeUmec/p2vjO2NjsSAVcWEQMVhJ31LwIDAQABAoGAfmO8gVhyBxdqlxmIuglbz8bcjQbhXJLR2EoS8ngTXmN1bo2L90M0mUKSdc7qF10LgETBzqL8jYlQIbt+e6TH8fcEpKCjUlyq0Mf/vVbfZSNaVycY13nTzo27iPyWQHK5NLuJzn1xvxxrUeXI6A2WFpGEBLbHjwpx5WQG9A+2scECQQDvdn9NE75HPTVPxBqsEd2z10TKkl9CZxu10Qby3iQQmWLEJ9LNmy3acvKrE3gMiYNWb6xHPKiIqOR1as7L24aTAkEAtyvQOlCvr5kAjVqrEKXalj0Tzewjweuxc0pskvArTI2Oo070h65GpoIKLc9jf+UA69cRtquwP93aZKtW06U8dQJAF2Y44ks/mK5+eyDqik3koCI08qaC8HYq2wVl7G2QkJ6sbAaILtcvD92ToOvyGyeE0flvmDZxMYlvaZnaQ0lcSQJBAKZU6umJi3/xeEbkJqMfeLclD27XGEFoPeNrmdx0q10Azp4NfJAY+Z8KRyQCR2BEG+oNitBOZ+YXF9KCpH3cdmECQHEigJhYg+ykOvr1aiZUMFT72HU0jnmQe2FVekuG+LJUt2Tm7GtMjTFoGpf0JwrVuZN39fOYAlo+nTixgeW7X8Y=",
+ "publicKey": "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCrVrCuTtArbgaZzL1hvh0xtL5mc7o0NqPVnYXkLvgcwiC3BjLGw1tGEGoJaXDuSaRllobm53JBhjx33UNv+5z/UMG4kytBWxheNVKnL6GgqlNabMaFfPLPCF8kAgKnsi79NMo+n6KnSY8YeUmec/p2vjO2NjsSAVcWEQMVhJ31LwIDAQAB",
+ "requiredCredentials": [ "password" ],
+ "users" : [
+ {
+ "username" : "bburke@redhat.com",
+ "enabled": true,
+ "email" : "bburke@redhat.com",
+ "firstName": "Bill",
+ "lastName": "Burke",
+ "credentials" : [
+ { "type" : "password",
+ "value" : "password" }
+ ],
+ "realmRoles": [ "user" ],
+ "applicationRoles": {
+ "account": [ "manage-account" ]
+ }
+ },
+ {
+ "username" : "stian",
+ "enabled": true,
+ "email" : "stian@redhat.com",
+ "firstName": "Stian",
+ "lastName": "Thorgersen",
+ "credentials" : [
+ { "type" : "password",
+ "value" : "password" }
+ ],
+ "realmRoles": [ "user" ],
+ "applicationRoles": {
+ "account": [ "manage-account" ]
+ }
+ },
+ {
+ "username" : "mposolda@redhat.com",
+ "enabled": true,
+ "email" : "mposolda@redhat.com",
+ "firstName": "Marek",
+ "lastName": "Posolda",
+ "credentials" : [
+ { "type" : "password",
+ "value" : "password" }
+ ],
+ "realmRoles": [ "user" ],
+ "applicationRoles": {
+ "account": [ "manage-account" ]
+ }
+ },
+ {
+ "username" : "admin",
+ "enabled": true,
+ "email" : "admin@admin.com",
+ "firstName": "Admin",
+ "lastName": "Burke",
+ "credentials" : [
+ { "type" : "password",
+ "value" : "password" }
+ ],
+ "realmRoles": [ "user","admin" ],
+ "applicationRoles": {
+ "realm-management": [ "realm-admin" ]
+ }
+ }
+ ],
+ "roles" : {
+ "realm" : [
+ {
+ "name": "user",
+ "description": "User privileges"
+ },
+ {
+ "name": "admin",
+ "description": "Administrator privileges"
+ }
+ ]
+ },
+ "applications": [
+ {
+ "name": "customer-portal",
+ "enabled": true,
+ "adminUrl": "http://localhost:8181/customer-portal",
+ "baseUrl": "http://localhost:8181/customer-portal",
+ "redirectUris": [
+ "http://localhost:8181/customer-portal/*"
+ ],
+ "secret": "password"
+ },
+ {
+ "name": "product-portal",
+ "enabled": true,
+ "adminUrl": "http://localhost:8181/product-portal",
+ "baseUrl": "http://localhost:8181/product-portal",
+ "redirectUris": [
+ "http://localhost:8181/product-portal/*"
+ ],
+ "secret": "password"
+ },
+ {
+ "name": "builtin-cxf-app",
+ "enabled": true,
+ "adminUrl": "http://localhost:8181/cxf",
+ "baseUrl": "http://localhost:8181/cxf",
+ "redirectUris": [
+ "http://localhost:8181/cxf/*"
+ ],
+ "secret": "password"
+ },
+ {
+ "name": "custom-cxf-endpoint",
+ "enabled": true,
+ "adminUrl": "http://localhost:8282/PersonServiceCF",
+ "baseUrl": "http://localhost:8282/PersonServiceCF",
+ "bearerOnly": true
+ },
+ {
+ "name": "admin-camel-endpoint",
+ "enabled": true,
+ "adminUrl": "http://localhost:8383/admin-camel-endpoint",
+ "baseUrl": "http://localhost:8383/admin-camel-endpoint",
+ "bearerOnly": true
+ }
+ ]
+}
\ No newline at end of file
examples/pom.xml 1(+1 -0)
diff --git a/examples/pom.xml b/examples/pom.xml
index 72439c5..4e6583d 100755
--- a/examples/pom.xml
+++ b/examples/pom.xml
@@ -32,5 +32,6 @@
<module>js-console</module>
<module>multi-tenant</module>
<module>basic-auth</module>
+ <module>fuse</module>
</modules>
</project>
integration/adapter-core/pom.xml 44(+44 -0)
diff --git a/integration/adapter-core/pom.xml b/integration/adapter-core/pom.xml
index bda770f..a9b88a4 100755
--- a/integration/adapter-core/pom.xml
+++ b/integration/adapter-core/pom.xml
@@ -13,6 +13,17 @@
<name>Keycloak Adapter Core</name>
<description/>
+ <properties>
+ <keycloak.osgi.export>
+ org.keycloak.adapters.*
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ org.keycloak.*;version="${project.version}",
+ org.apache.http.*;version=${keycloak.apache.httpcomponents.version},
+ *;resolution:=optional
+ </keycloak.osgi.import>
+ </properties>
+
<dependencies>
<dependency>
<groupId>org.bouncycastle</groupId>
@@ -73,6 +84,39 @@
<target>${maven.compiler.target}</target>
</configuration>
</plugin>
+
+ <!-- Adding OSGI metadata to the JAR without changing the packaging type. -->
+ <plugin>
+ <artifactId>maven-jar-plugin</artifactId>
+ <configuration>
+ <archive>
+ <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
+ </archive>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <executions>
+ <execution>
+ <id>bundle-manifest</id>
+ <phase>process-classes</phase>
+ <goals>
+ <goal>manifest</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <instructions>
+ <Bundle-ClassPath>.</Bundle-ClassPath>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
</plugins>
</build>
diff --git a/integration/jaxrs-oauth-client/pom.xml b/integration/jaxrs-oauth-client/pom.xml
index 2b6b79f..56b8d69 100755
--- a/integration/jaxrs-oauth-client/pom.xml
+++ b/integration/jaxrs-oauth-client/pom.xml
@@ -74,7 +74,6 @@
<dependency>
<groupId>org.osgi</groupId>
<artifactId>org.osgi.core</artifactId>
- <version>4.3.0</version>
<scope>provided</scope>
</dependency>
</dependencies>
integration/jetty/jetty8.1/pom.xml 41(+41 -0)
diff --git a/integration/jetty/jetty8.1/pom.xml b/integration/jetty/jetty8.1/pom.xml
index 0f74aaf..26af2c2 100755
--- a/integration/jetty/jetty8.1/pom.xml
+++ b/integration/jetty/jetty8.1/pom.xml
@@ -13,6 +13,14 @@
<name>Keycloak Jetty 8.1.x Integration</name>
<properties>
<jetty9.version>8.1.16.v20140903</jetty9.version>
+ <keycloak.osgi.export>
+ org.keycloak.adapters.jetty.*
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ javax.servlet.*;version="[2.5,4)";resolution:=optional,
+ org.keycloak.*;version="${project.version}",
+ *;resolution:=optional
+ </keycloak.osgi.import>
</properties>
<description />
@@ -99,6 +107,39 @@
<target>1.6</target>
</configuration>
</plugin>
+
+ <!-- Adding OSGI metadata to the JAR without changing the packaging type. -->
+ <plugin>
+ <artifactId>maven-jar-plugin</artifactId>
+ <configuration>
+ <archive>
+ <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
+ </archive>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <executions>
+ <execution>
+ <id>bundle-manifest</id>
+ <phase>process-classes</phase>
+ <goals>
+ <goal>manifest</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <instructions>
+ <Bundle-ClassPath>.</Bundle-ClassPath>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
</plugins>
</build>
diff --git a/integration/jetty/jetty8.1/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java b/integration/jetty/jetty8.1/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java
index e2dcfa5..38180aa 100755
--- a/integration/jetty/jetty8.1/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java
+++ b/integration/jetty/jetty8.1/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java
@@ -4,6 +4,7 @@ import org.eclipse.jetty.security.authentication.FormAuthenticator;
import org.eclipse.jetty.server.Request;
import org.eclipse.jetty.util.MultiMap;
import org.keycloak.adapters.KeycloakDeployment;
+import org.keycloak.adapters.jetty.core.AbstractJettySessionTokenStore;
import org.keycloak.util.MultivaluedHashMap;
import javax.servlet.http.HttpSession;
diff --git a/integration/jetty/jetty8.1/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java b/integration/jetty/jetty8.1/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java
index d1ae6e0..a3a5572 100755
--- a/integration/jetty/jetty8.1/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java
+++ b/integration/jetty/jetty8.1/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java
@@ -6,6 +6,7 @@ import org.eclipse.jetty.server.Request;
import org.eclipse.jetty.server.UserIdentity;
import org.keycloak.adapters.AdapterTokenStore;
import org.keycloak.adapters.KeycloakDeployment;
+import org.keycloak.adapters.jetty.core.AbstractKeycloakJettyAuthenticator;
import javax.servlet.ServletRequest;
integration/jetty/jetty9.1/pom.xml 42(+42 -0)
diff --git a/integration/jetty/jetty9.1/pom.xml b/integration/jetty/jetty9.1/pom.xml
index 6c23f5a..26688b8 100755
--- a/integration/jetty/jetty9.1/pom.xml
+++ b/integration/jetty/jetty9.1/pom.xml
@@ -13,6 +13,15 @@
<name>Keycloak Jetty 9.1.x Integration</name>
<properties>
<jetty9.version>9.1.5.v20140505</jetty9.version>
+ <keycloak.osgi.export>
+ org.keycloak.adapters.jetty.*
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ org.eclipse.jetty.*;version="[9.1,9.2)";resolution:=optional,
+ javax.servlet.*;version="[3.0,4)";resolution:=optional,
+ org.keycloak.*;version="${project.version}",
+ *;resolution:=optional
+ </keycloak.osgi.import>
</properties>
<description />
@@ -113,6 +122,39 @@
<target>1.6</target>
</configuration>
</plugin>
+
+ <!-- Adding OSGI metadata to the JAR without changing the packaging type. -->
+ <plugin>
+ <artifactId>maven-jar-plugin</artifactId>
+ <configuration>
+ <archive>
+ <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
+ </archive>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <executions>
+ <execution>
+ <id>bundle-manifest</id>
+ <phase>process-classes</phase>
+ <goals>
+ <goal>manifest</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <instructions>
+ <Bundle-ClassPath>.</Bundle-ClassPath>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
</plugins>
</build>
diff --git a/integration/jetty/jetty9.1/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java b/integration/jetty/jetty9.1/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java
index 24fc9b2..6d4cb92 100755
--- a/integration/jetty/jetty9.1/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java
+++ b/integration/jetty/jetty9.1/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java
@@ -5,6 +5,7 @@ import org.eclipse.jetty.security.authentication.FormAuthenticator;
import org.eclipse.jetty.server.Request;
import org.eclipse.jetty.util.MultiMap;
import org.keycloak.adapters.KeycloakDeployment;
+import org.keycloak.adapters.jetty.core.AbstractJettySessionTokenStore;
import org.keycloak.util.MultivaluedHashMap;
import javax.servlet.http.HttpSession;
diff --git a/integration/jetty/jetty9.1/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java b/integration/jetty/jetty9.1/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java
index db15f33..d1ab5f3 100755
--- a/integration/jetty/jetty9.1/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java
+++ b/integration/jetty/jetty9.1/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java
@@ -6,6 +6,7 @@ import org.eclipse.jetty.server.Request;
import org.eclipse.jetty.server.UserIdentity;
import org.keycloak.adapters.AdapterTokenStore;
import org.keycloak.adapters.KeycloakDeployment;
+import org.keycloak.adapters.jetty.core.AbstractKeycloakJettyAuthenticator;
import javax.servlet.ServletRequest;
integration/jetty/jetty9.2/pom.xml 42(+42 -0)
diff --git a/integration/jetty/jetty9.2/pom.xml b/integration/jetty/jetty9.2/pom.xml
index c1b3729..8be7751 100755
--- a/integration/jetty/jetty9.2/pom.xml
+++ b/integration/jetty/jetty9.2/pom.xml
@@ -13,6 +13,15 @@
<name>Keycloak Jetty 9.2.x Integration</name>
<properties>
<jetty9.version>9.2.4.v20141103</jetty9.version>
+ <keycloak.osgi.export>
+ org.keycloak.adapters.jetty.*
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ org.eclipse.jetty.*;resolution:=optional,
+ javax.servlet.*;version="[3.0,4)";resolution:=optional,
+ org.keycloak.*;version="${project.version}",
+ *;resolution:=optional
+ </keycloak.osgi.import>
</properties>
<description />
@@ -99,6 +108,39 @@
<target>1.6</target>
</configuration>
</plugin>
+
+ <!-- Adding OSGI metadata to the JAR without changing the packaging type. -->
+ <plugin>
+ <artifactId>maven-jar-plugin</artifactId>
+ <configuration>
+ <archive>
+ <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
+ </archive>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <executions>
+ <execution>
+ <id>bundle-manifest</id>
+ <phase>process-classes</phase>
+ <goals>
+ <goal>manifest</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <instructions>
+ <Bundle-ClassPath>.</Bundle-ClassPath>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
</plugins>
</build>
diff --git a/integration/jetty/jetty9.2/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java b/integration/jetty/jetty9.2/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java
index 4ff9af9..f48a0d8 100755
--- a/integration/jetty/jetty9.2/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java
+++ b/integration/jetty/jetty9.2/src/main/java/org/keycloak/adapters/jetty/JettySessionTokenStore.java
@@ -5,10 +5,10 @@ import org.eclipse.jetty.security.authentication.FormAuthenticator;
import org.eclipse.jetty.server.Request;
import org.eclipse.jetty.util.MultiMap;
import org.keycloak.adapters.KeycloakDeployment;
+import org.keycloak.adapters.jetty.core.AbstractJettySessionTokenStore;
import org.keycloak.util.MultivaluedHashMap;
import javax.servlet.http.HttpSession;
-import java.lang.reflect.Field;
/**
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
diff --git a/integration/jetty/jetty9.2/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java b/integration/jetty/jetty9.2/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java
index b43e27c..6cd1e07 100755
--- a/integration/jetty/jetty9.2/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java
+++ b/integration/jetty/jetty9.2/src/main/java/org/keycloak/adapters/jetty/KeycloakJettyAuthenticator.java
@@ -6,6 +6,7 @@ import org.eclipse.jetty.server.Request;
import org.eclipse.jetty.server.UserIdentity;
import org.keycloak.adapters.AdapterTokenStore;
import org.keycloak.adapters.KeycloakDeployment;
+import org.keycloak.adapters.jetty.core.AbstractKeycloakJettyAuthenticator;
import javax.servlet.ServletRequest;
integration/jetty/jetty-core/pom.xml 42(+42 -0)
diff --git a/integration/jetty/jetty-core/pom.xml b/integration/jetty/jetty-core/pom.xml
index 3de4bed..c37bc66 100755
--- a/integration/jetty/jetty-core/pom.xml
+++ b/integration/jetty/jetty-core/pom.xml
@@ -13,6 +13,15 @@
<name>Keycloak Jetty Core Integration</name>
<properties>
<jetty9.version>8.1.16.v20140903</jetty9.version>
+ <keycloak.osgi.export>
+ org.keycloak.adapters.jetty.core.*
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ org.eclipse.jetty.*;version="[8.1,10)";resolution:=optional,
+ javax.servlet.*;version="[2.5,4)";resolution:=optional,
+ org.keycloak.*;version="${project.version}",
+ *;resolution:=optional
+ </keycloak.osgi.import>
</properties>
<description />
@@ -94,6 +103,39 @@
<target>1.6</target>
</configuration>
</plugin>
+
+ <!-- Adding OSGI metadata to the JAR without changing the packaging type. -->
+ <plugin>
+ <artifactId>maven-jar-plugin</artifactId>
+ <configuration>
+ <archive>
+ <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
+ </archive>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <executions>
+ <execution>
+ <id>bundle-manifest</id>
+ <phase>process-classes</phase>
+ <goals>
+ <goal>manifest</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <instructions>
+ <Bundle-ClassPath>.</Bundle-ClassPath>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
</plugins>
</build>
diff --git a/integration/jetty/jetty-core/src/main/java/org/keycloak/adapters/jetty/core/WrappingSessionHandler.java b/integration/jetty/jetty-core/src/main/java/org/keycloak/adapters/jetty/core/WrappingSessionHandler.java
new file mode 100644
index 0000000..529b6f0
--- /dev/null
+++ b/integration/jetty/jetty-core/src/main/java/org/keycloak/adapters/jetty/core/WrappingSessionHandler.java
@@ -0,0 +1,30 @@
+package org.keycloak.adapters.jetty.core;
+
+import org.eclipse.jetty.server.Handler;
+import org.eclipse.jetty.server.SessionManager;
+import org.eclipse.jetty.server.handler.HandlerWrapper;
+import org.eclipse.jetty.server.session.SessionHandler;
+
+/**
+ * @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
+ */
+public class WrappingSessionHandler extends SessionHandler {
+
+ public WrappingSessionHandler() {
+ super();
+ }
+
+ public WrappingSessionHandler(SessionManager mgr) {
+ super(mgr);
+ }
+
+ @Override
+ public void setHandler(Handler handler) {
+ if (getHandler() != null && getHandler() instanceof HandlerWrapper) {
+ HandlerWrapper wrappedHandler = (HandlerWrapper) getHandler();
+ wrappedHandler.setHandler(handler);
+ } else {
+ super.setHandler(handler);
+ }
+ }
+}
integration/osgi-adapter/pom.xml 104(+104 -0)
diff --git a/integration/osgi-adapter/pom.xml b/integration/osgi-adapter/pom.xml
new file mode 100644
index 0000000..9d462f2
--- /dev/null
+++ b/integration/osgi-adapter/pom.xml
@@ -0,0 +1,104 @@
+<?xml version="1.0"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+ <parent>
+ <artifactId>keycloak-parent</artifactId>
+ <groupId>org.keycloak</groupId>
+ <version>1.1.0.Final-SNAPSHOT</version>
+ <relativePath>../../pom.xml</relativePath>
+ </parent>
+ <modelVersion>4.0.0</modelVersion>
+
+ <artifactId>keycloak-osgi-adapter</artifactId>
+ <name>Keycloak OSGI Adapter</name>
+ <packaging>jar</packaging>
+
+ <properties>
+ <jetty9.version>8.1.16.v20140903</jetty9.version>
+ <keycloak.osgi.export>
+ org.keycloak.adapters.osgi.*
+ </keycloak.osgi.export>
+ <keycloak.osgi.import>
+ org.ops4j.pax.web.*;version="[3.0,4)",
+ javax.servlet.*;version="[2.5,4)";resolution:=optional,
+ org.eclipse.jetty.*;version="[8.1,10)";resolution:=optional,
+ org.keycloak.*;version="${project.version}",
+ *;resolution:=optional
+ </keycloak.osgi.import>
+ </properties>
+
+ <dependencies>
+ <dependency>
+ <groupId>org.jboss.logging</groupId>
+ <artifactId>jboss-logging</artifactId>
+ <scope>provided</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.osgi</groupId>
+ <artifactId>org.osgi.core</artifactId>
+ <scope>provided</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.osgi</groupId>
+ <artifactId>org.osgi.enterprise</artifactId>
+ <scope>provided</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.ops4j.pax.web</groupId>
+ <artifactId>pax-web-runtime</artifactId>
+ <scope>provided</scope>
+ </dependency>
+ <dependency>
+ <groupId>org.eclipse.jetty</groupId>
+ <artifactId>jetty-security</artifactId>
+ <version>${jetty9.version}</version>
+ <scope>provided</scope>
+ </dependency>
+ </dependencies>
+
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <configuration>
+ <source>${maven.compiler.source}</source>
+ <target>${maven.compiler.target}</target>
+ </configuration>
+ </plugin>
+
+ <!-- Adding OSGI metadata to the JAR without changing the packaging type. -->
+ <plugin>
+ <artifactId>maven-jar-plugin</artifactId>
+ <configuration>
+ <archive>
+ <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile>
+ </archive>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <extensions>true</extensions>
+ <executions>
+ <execution>
+ <id>bundle-manifest</id>
+ <phase>process-classes</phase>
+ <goals>
+ <goal>manifest</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <instructions>
+ <Bundle-ClassPath>.</Bundle-ClassPath>
+ <Bundle-Name>${project.name}</Bundle-Name>
+ <Bundle-SymbolicName>${project.groupId}.${project.artifactId}</Bundle-SymbolicName>
+ <Import-Package>${keycloak.osgi.import}</Import-Package>
+ <Export-Package>${keycloak.osgi.export}</Export-Package>
+ </instructions>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+</project>
diff --git a/integration/osgi-adapter/src/main/java/org/keycloak/adapters/osgi/PaxWebIntegrationService.java b/integration/osgi-adapter/src/main/java/org/keycloak/adapters/osgi/PaxWebIntegrationService.java
new file mode 100644
index 0000000..1aa67f0
--- /dev/null
+++ b/integration/osgi-adapter/src/main/java/org/keycloak/adapters/osgi/PaxWebIntegrationService.java
@@ -0,0 +1,163 @@
+package org.keycloak.adapters.osgi;
+
+import java.net.URL;
+import java.util.Arrays;
+import java.util.List;
+import java.util.Random;
+
+import org.eclipse.jetty.security.ConstraintMapping;
+import org.eclipse.jetty.util.security.Constraint;
+import org.jboss.logging.Logger;
+import org.ops4j.pax.web.service.WebContainer;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.ServiceReference;
+import org.osgi.service.http.HttpContext;
+import org.osgi.util.tracker.ServiceTracker;
+import org.osgi.util.tracker.ServiceTrackerCustomizer;
+
+/**
+ * Integration with pax-web, which allows to inject custom jetty-web.xml configuration from current bundle classpath into {@link WebContainer}
+ * and allows to inject custom security constraint for securing resources by Keycloak.
+ *
+ * <p>It assumes that pax-web {@link WebContainer} is used as implementation of OSGI {@link org.osgi.service.http.HttpService}, which
+ * is true in karaf/fuse environment</p>
+ *
+ * @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
+ */
+public class PaxWebIntegrationService {
+
+ protected static final Logger log = Logger.getLogger(PaxWebIntegrationService.class);
+
+ private BundleContext bundleContext;
+ private String jettyWebXmlLocation;
+ private List<ConstraintMapping> constraintMappings; // Using jetty constraint mapping just because of compatibility with other fuse services
+
+ private ServiceTracker webContainerTracker;
+ private HttpContext httpContext;
+
+ public BundleContext getBundleContext() {
+ return bundleContext;
+ }
+
+ public void setBundleContext(BundleContext bundleContext) {
+ this.bundleContext = bundleContext;
+ }
+
+ public String getJettyWebXmlLocation() {
+ return jettyWebXmlLocation;
+ }
+
+ public void setJettyWebXmlLocation(String jettyWebXmlLocation) {
+ this.jettyWebXmlLocation = jettyWebXmlLocation;
+ }
+
+ public List<ConstraintMapping> getConstraintMappings() {
+ return constraintMappings;
+ }
+
+ public void setConstraintMappings(List<ConstraintMapping> constraintMappings) {
+ this.constraintMappings = constraintMappings;
+ }
+
+ protected ServiceTracker getWebContainerTracker() {
+ return webContainerTracker;
+ }
+
+ protected HttpContext getHttpContext() {
+ return httpContext;
+ }
+
+
+ public void start() {
+ ServiceTrackerCustomizer trackerCustomizer = new ServiceTrackerCustomizer() {
+
+ @Override
+ public Object addingService(ServiceReference reference) {
+ return addingWebContainerCallback(reference);
+ }
+
+ @Override
+ public void modifiedService(ServiceReference reference, Object service) {
+ }
+
+ @Override
+ public void removedService(ServiceReference reference, Object service) {
+ removingWebContainerCallback(reference);
+ }
+ };
+
+ webContainerTracker = new ServiceTracker(bundleContext, WebContainer.class.getName(), trackerCustomizer);
+ webContainerTracker.open();
+ }
+
+ public void stop() {
+ webContainerTracker.remove(webContainerTracker.getServiceReference());
+ }
+
+ protected WebContainer addingWebContainerCallback(ServiceReference webContainerServiceReference) {
+ WebContainer service = (WebContainer) bundleContext.getService(webContainerServiceReference);
+ httpContext = service.createDefaultHttpContext();
+
+ addJettyWebXml(service);
+
+ if (constraintMappings == null) {
+ throw new IllegalStateException("constraintMappings was null!");
+ }
+ for (ConstraintMapping constraintMapping : constraintMappings) {
+ addConstraintMapping(service, constraintMapping);
+ }
+
+ service.registerLoginConfig("BASIC", "does-not-matter", null, null, httpContext);
+
+ return service;
+ }
+
+ protected void addJettyWebXml(WebContainer service) {
+ String jettyWebXmlLoc;
+ if (this.jettyWebXmlLocation == null) {
+ jettyWebXmlLoc = "/WEB-INF/jetty-web.xml";
+ } else {
+ jettyWebXmlLoc = this.jettyWebXmlLocation;
+ }
+
+ URL jettyWebXml = bundleContext.getBundle().getResource(jettyWebXmlLoc);
+ if (jettyWebXml != null) {
+ log.debug("Found jetty-web XML configuration on bundle classpath on " + jettyWebXmlLoc);
+ service.registerJettyWebXml(jettyWebXml, httpContext);
+ } else {
+ log.debug("Not found jetty-web XML configuration on bundle classpath on " + jettyWebXmlLoc);
+ }
+ }
+
+ protected void addConstraintMapping(WebContainer service, ConstraintMapping constraintMapping) {
+ Constraint constraint = constraintMapping.getConstraint();
+ String[] roles = constraint.getRoles();
+ // name property is unavailable on constraint object :/
+ String name = "Constraint-" + new Random().nextInt();
+
+ int dataConstraint = constraint.getDataConstraint();
+ String dataConstraintStr;
+ switch (dataConstraint) {
+ case Constraint.DC_UNSET: dataConstraintStr = null; break;
+ case Constraint.DC_NONE: dataConstraintStr = "NONE"; break;
+ case Constraint.DC_CONFIDENTIAL: dataConstraintStr = "CONFIDENTIAL"; break;
+ case Constraint.DC_INTEGRAL: dataConstraintStr = "INTEGRAL"; break;
+ default:
+ log.warnv("Unknown data constraint: " + dataConstraint);
+ dataConstraintStr = "CONFIDENTIAL";
+ }
+ List<String> rolesList = Arrays.asList(roles);
+
+ log.debug("Adding security constraint name=" + name + ", url=" + constraintMapping.getPathSpec() + ", dataConstraint=" + dataConstraintStr + ", canAuthenticate="
+ + constraint.getAuthenticate() + ", roles=" + rolesList);
+ service.registerConstraintMapping(name, constraintMapping.getPathSpec(), null, dataConstraintStr, constraint.getAuthenticate(), rolesList, httpContext);
+ }
+
+ protected void removingWebContainerCallback(ServiceReference serviceReference) {
+ WebContainer service = (WebContainer)bundleContext.getService(serviceReference);
+ if (service != null) {
+ service.unregisterLoginConfig(httpContext);
+ service.unregisterConstraintMapping(httpContext);
+ }
+ }
+}
diff --git a/integration/osgi-adapter/src/main/java/org/keycloak/adapters/osgi/ServletUnregistrationService.java b/integration/osgi-adapter/src/main/java/org/keycloak/adapters/osgi/ServletUnregistrationService.java
new file mode 100644
index 0000000..236c49e
--- /dev/null
+++ b/integration/osgi-adapter/src/main/java/org/keycloak/adapters/osgi/ServletUnregistrationService.java
@@ -0,0 +1,100 @@
+package org.keycloak.adapters.osgi;
+
+import java.util.Hashtable;
+
+import javax.servlet.Servlet;
+
+import org.jboss.logging.Logger;
+import org.ops4j.pax.web.service.WebContainer;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.ServiceReference;
+import org.osgi.service.http.HttpContext;
+
+/**
+ * Service, which allows to remove previously registered servlets in karaf/fuse environment. It assumes that particular servlet was previously
+ * registered as service in OSGI container under {@link javax.servlet.Servlet} interface.
+ *
+ * <p>The point is to register automatically registered builtin servlet endpoints (like "/cxf" for instance) to allow secure them
+ * by Keycloak and re-register them again</p>
+ *
+ * @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
+ */
+public class ServletUnregistrationService {
+
+ protected static final Logger log = Logger.getLogger(ServletUnregistrationService.class);
+
+ private BundleContext bundleContext;
+ private ServiceReference servletReference;
+
+ public BundleContext getBundleContext() {
+ return bundleContext;
+ }
+
+ public void setBundleContext(BundleContext bundleContext) {
+ this.bundleContext = bundleContext;
+ }
+
+ public ServiceReference getServletReference() {
+ return servletReference;
+ }
+
+ public void setServletReference(ServiceReference servletReference) {
+ this.servletReference = servletReference;
+ }
+
+ // TODO: Re-register original servlet back during stop?
+ public void start() {
+ if (servletReference == null) {
+ throw new IllegalStateException("No servlet reference provided");
+ }
+
+ Servlet servlet = (Servlet) bundleContext.getService(servletReference);
+ WebContainer webContainer = findWebContainer(servletReference);
+ if (webContainer == null) {
+ return;
+ }
+
+ // Unregister servlet now
+ try {
+ webContainer.unregisterServlet(servlet);
+ log.debugv("Original servlet with alias " + servletReference.getProperty("alias") + " unregistered successfully.");
+ } catch (IllegalStateException e) {
+ log.warnv("Can't unregister servlet due to: " + e.getMessage());
+ }
+ }
+
+ public void stop() {
+ try {
+ Servlet servlet = (Servlet) bundleContext.getService(servletReference);
+ WebContainer webContainer = findWebContainer(servletReference);
+ if (webContainer == null) {
+ return;
+ }
+
+ Hashtable<String, Object> servletInitParams = new Hashtable<String, Object>();
+ String[] propNames = servletReference.getPropertyKeys();
+ for (String propName : propNames) {
+ servletInitParams.put(propName, servletReference.getProperty(propName));
+ }
+
+ // Try to register original servlet back
+ HttpContext httpContext = webContainer.createDefaultHttpContext();
+ String alias = (String) servletReference.getProperty("alias");
+ webContainer.registerServlet(alias, servlet, servletInitParams, httpContext);
+ } catch (Exception e) {
+ log.warn("Can't register original servlet back", e);
+ }
+ }
+
+ protected WebContainer findWebContainer(ServiceReference servletRef) {
+ BundleContext servletBundleContext = servletRef.getBundle().getBundleContext();
+ ServiceReference webContainerReference = servletBundleContext.getServiceReference(WebContainer.class.getName());
+ if (webContainerReference == null) {
+ log.warn("Not found webContainer reference for bundle " + servletBundleContext);
+ return null;
+ } else {
+ return (WebContainer) servletBundleContext.getService(webContainerReference);
+ }
+ }
+
+}
integration/pom.xml 1(+1 -0)
diff --git a/integration/pom.xml b/integration/pom.xml
index 7311775..42d21b3 100755
--- a/integration/pom.xml
+++ b/integration/pom.xml
@@ -28,5 +28,6 @@
<module>js</module>
<module>installed</module>
<module>admin-client</module>
+ <module>osgi-adapter</module>
</modules>
</project>
pom.xml 20(+19 -1)
diff --git a/pom.xml b/pom.xml
index 97b5f6d..e814323 100755
--- a/pom.xml
+++ b/pom.xml
@@ -13,6 +13,7 @@
<properties>
<aesh.version>0.33.12</aesh.version>
+ <base64.version>2.3.8</base64.version>
<bouncycastle.version>1.46</bouncycastle.version>
<jackson.version>1.9.9</jackson.version>
<keycloak.apache.httpcomponents.version>4.2.1</keycloak.apache.httpcomponents.version>
@@ -48,6 +49,8 @@
<infinispan.version>6.0.2.Final</infinispan.version>
<liquibase.version>3.2.2</liquibase.version>
<jetty9.version>9.1.0.v20131115</jetty9.version>
+ <osgi.version>4.2.0</osgi.version>
+ <pax.web.version>3.1.2</pax.web.version>
<!-- maven-compiler-plugin -->
<maven.compiler.target>1.6</maven.compiler.target>
@@ -138,7 +141,7 @@
<dependency>
<groupId>net.iharder</groupId>
<artifactId>base64</artifactId>
- <version>2.3.8</version>
+ <version>${base64.version}</version>
</dependency>
<dependency>
<groupId>javax.mail</groupId>
@@ -507,6 +510,21 @@
<artifactId>liquibase-core</artifactId>
<version>${liquibase.version}</version>
</dependency>
+ <dependency>
+ <groupId>org.osgi</groupId>
+ <artifactId>org.osgi.core</artifactId>
+ <version>${osgi.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.osgi</groupId>
+ <artifactId>org.osgi.enterprise</artifactId>
+ <version>${osgi.version}</version>
+ </dependency>
+ <dependency>
+ <groupId>org.ops4j.pax.web</groupId>
+ <artifactId>pax-web-runtime</artifactId>
+ <version>${pax.web.version}</version>
+ </dependency>
</dependencies>
</dependencyManagement>
diff --git a/testsuite/integration/src/test/java/org/keycloak/testsuite/jaxrs/JaxrsFilterTest.java b/testsuite/integration/src/test/java/org/keycloak/testsuite/jaxrs/JaxrsFilterTest.java
index 16f00f5..2ff046c 100644
--- a/testsuite/integration/src/test/java/org/keycloak/testsuite/jaxrs/JaxrsFilterTest.java
+++ b/testsuite/integration/src/test/java/org/keycloak/testsuite/jaxrs/JaxrsFilterTest.java
@@ -316,8 +316,8 @@ public class JaxrsFilterTest {
// @Test
public void testCxfExample() {
- String uri = "http://localhost:9000/customerservice/customers/123";
- //String uri = "http://localhost:8080/jax_rs_basic_servlet/services/service1/customerservice/customers/123";
+ //String uri = "http://localhost:9000/customerservice/customers/123";
+ String uri = "http://localhost:8080/jax_rs_basic_servlet/services/service1/customerservice/customers/123";
Response resp = client.target(uri).request()
.get();
Assert.assertEquals(resp.getStatus(), 401);
diff --git a/testsuite/jetty/jetty91/src/test/java/org/keycloak/testsuite/Jetty9Test.java b/testsuite/jetty/jetty91/src/test/java/org/keycloak/testsuite/Jetty9Test.java
index 22170ee..4b87597 100755
--- a/testsuite/jetty/jetty91/src/test/java/org/keycloak/testsuite/Jetty9Test.java
+++ b/testsuite/jetty/jetty91/src/test/java/org/keycloak/testsuite/Jetty9Test.java
@@ -21,49 +21,23 @@
*/
package org.keycloak.testsuite;
-import org.eclipse.jetty.security.ConstraintMapping;
-import org.eclipse.jetty.security.ConstraintSecurityHandler;
-import org.eclipse.jetty.security.HashLoginService;
import org.eclipse.jetty.server.Handler;
import org.eclipse.jetty.server.Server;
import org.eclipse.jetty.server.handler.HandlerCollection;
-import org.eclipse.jetty.servlet.ServletHolder;
-import org.eclipse.jetty.util.security.Constraint;
import org.eclipse.jetty.webapp.WebAppContext;
import org.junit.AfterClass;
-import org.junit.Assert;
import org.junit.BeforeClass;
import org.junit.ClassRule;
-import org.junit.Ignore;
import org.junit.Rule;
import org.junit.Test;
-import org.keycloak.KeycloakSecurityContext;
-import org.keycloak.OAuth2Constants;
-import org.keycloak.adapters.jetty.AbstractKeycloakJettyAuthenticator;
-import org.keycloak.adapters.jetty.KeycloakJettyAuthenticator;
import org.keycloak.models.KeycloakSession;
import org.keycloak.models.RealmModel;
-import org.keycloak.protocol.oidc.OpenIDConnectService;
-import org.keycloak.representations.idm.RealmRepresentation;
import org.keycloak.services.managers.RealmManager;
import org.keycloak.testsuite.adapter.AdapterTestStrategy;
-import org.keycloak.testsuite.pages.LoginPage;
import org.keycloak.testsuite.rule.AbstractKeycloakRule;
-import org.keycloak.testsuite.rule.WebResource;
-import org.keycloak.testsuite.rule.WebRule;
-import org.keycloak.testutils.KeycloakServer;
-import org.openqa.selenium.WebDriver;
-
-import javax.servlet.ServletException;
-import javax.servlet.http.HttpServlet;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-import javax.ws.rs.core.UriBuilder;
+
import java.io.File;
-import java.io.IOException;
-import java.io.OutputStream;
import java.net.URL;
-import java.security.Principal;
import java.util.ArrayList;
import java.util.List;
diff --git a/testsuite/jetty/jetty92/src/test/java/org/keycloak/testsuite/Jetty9Test.java b/testsuite/jetty/jetty92/src/test/java/org/keycloak/testsuite/Jetty9Test.java
index e965ea6..ceab804 100755
--- a/testsuite/jetty/jetty92/src/test/java/org/keycloak/testsuite/Jetty9Test.java
+++ b/testsuite/jetty/jetty92/src/test/java/org/keycloak/testsuite/Jetty9Test.java
@@ -21,49 +21,23 @@
*/
package org.keycloak.testsuite;
-import org.eclipse.jetty.security.ConstraintMapping;
-import org.eclipse.jetty.security.ConstraintSecurityHandler;
-import org.eclipse.jetty.security.HashLoginService;
import org.eclipse.jetty.server.Handler;
import org.eclipse.jetty.server.Server;
import org.eclipse.jetty.server.handler.HandlerCollection;
-import org.eclipse.jetty.servlet.ServletHolder;
-import org.eclipse.jetty.util.security.Constraint;
import org.eclipse.jetty.webapp.WebAppContext;
import org.junit.AfterClass;
-import org.junit.Assert;
import org.junit.BeforeClass;
import org.junit.ClassRule;
-import org.junit.Ignore;
import org.junit.Rule;
import org.junit.Test;
-import org.keycloak.KeycloakSecurityContext;
-import org.keycloak.OAuth2Constants;
-import org.keycloak.adapters.jetty.AbstractKeycloakJettyAuthenticator;
-import org.keycloak.adapters.jetty.KeycloakJettyAuthenticator;
import org.keycloak.models.KeycloakSession;
import org.keycloak.models.RealmModel;
-import org.keycloak.protocol.oidc.OpenIDConnectService;
-import org.keycloak.representations.idm.RealmRepresentation;
import org.keycloak.services.managers.RealmManager;
import org.keycloak.testsuite.adapter.AdapterTestStrategy;
-import org.keycloak.testsuite.pages.LoginPage;
import org.keycloak.testsuite.rule.AbstractKeycloakRule;
-import org.keycloak.testsuite.rule.WebResource;
-import org.keycloak.testsuite.rule.WebRule;
-import org.keycloak.testutils.KeycloakServer;
-import org.openqa.selenium.WebDriver;
-
-import javax.servlet.ServletException;
-import javax.servlet.http.HttpServlet;
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-import javax.ws.rs.core.UriBuilder;
+
import java.io.File;
-import java.io.IOException;
-import java.io.OutputStream;
import java.net.URL;
-import java.security.Principal;
import java.util.ArrayList;
import java.util.List;