KEYCLOAK-9836 Deprecate keycloak-servlet-oauth-clien
This commit is contained in:
parent
2fa2437555
commit
a516a795a2
30 changed files with 16 additions and 1254 deletions
|
@ -25,6 +25,9 @@ import java.util.Map;
|
|||
|
||||
/**
|
||||
* @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
|
||||
* @deprecated Class is deprecated and may be removed in the future. If you want to maintain this class for Keycloak community, please
|
||||
* contact Keycloak team on keycloak-dev mailing list. You can fork it into your github repository and
|
||||
* Keycloak team will reference it from "Keycloak Extensions" page.
|
||||
*/
|
||||
public class KeycloakDeploymentDelegateOAuthClient extends AbstractOAuthClient {
|
||||
|
||||
|
|
|
@ -51,7 +51,11 @@ import java.security.SecureRandom;
|
|||
/**
|
||||
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
|
||||
* @version $Revision: 1 $
|
||||
* @deprecated Class is deprecated and may be removed in the future. If you want to maintain this class for Keycloak community, please
|
||||
* contact Keycloak team on keycloak-dev mailing list. You can fork it into your github repository and
|
||||
* Keycloak team will reference it from "Keycloak Extensions" page.
|
||||
*/
|
||||
@Deprecated
|
||||
public class ServletOAuthClient extends KeycloakDeploymentDelegateOAuthClient {
|
||||
|
||||
// https://tools.ietf.org/html/rfc7636#section-4
|
||||
|
|
|
@ -26,6 +26,9 @@ import java.io.InputStream;
|
|||
/**
|
||||
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
|
||||
* @version $Revision: 1 $
|
||||
* @deprecated Class is deprecated and may be removed in the future. If you want to maintain this class for Keycloak community, please
|
||||
* contact Keycloak team on keycloak-dev mailing list. You can fork it into your github repository and
|
||||
* Keycloak team will reference it from "Keycloak Extensions" page.
|
||||
*/
|
||||
public class ServletOAuthClientBuilder {
|
||||
|
||||
|
|
|
@ -18,8 +18,6 @@ machine on the network or Internet.
|
|||
* **admin-access-app** A WAR application that does remote REST login to admin console to obtain a list of realm roles from Admin REST API
|
||||
* **angular-product-app** An Angular JS pure HTML5/Javascript application.
|
||||
* **database-service** JAX-RS services authenticated by bearer tokens only. The customer and product app invoke on it to get data
|
||||
* **third-party** Simple WAR that obtain a bearer token using OAuth2 using browser redirects to the auth-server.
|
||||
* **third-party-cdi** Simple CDI/JSF WAR that obtain a bearer token using OAuth2 using browser redirects to the auth-server.
|
||||
|
||||
The UI of each of these applications is very crude and exists just to show our OAuth2 implementation in action.
|
||||
|
||||
|
@ -160,17 +158,7 @@ If you click on the logout link of either of the product or customer app, you'll
|
|||
The example also shows different methods of client authentication. The customer-portal example is using traditional authentication with client_id and client_secret,
|
||||
but the product-portal example is using client authentication with JWT signed by client private key, which is retrieved from the keystore file inside the product-portal WAR.
|
||||
|
||||
Step 6: Traditional OAuth2 Example
|
||||
----------------------------------
|
||||
The customer and product apps are logins. The third-party app is the traditional OAuth2 usecase of a client wanting
|
||||
to get permission to access a user's data. To run this example open
|
||||
|
||||
[http://localhost:8080/oauth-client](http://localhost:8080/oauth-client)
|
||||
|
||||
If you are already logged in, you will not be asked for a username and password, but you will be redirected to
|
||||
an oauth grant page. This page asks you if you want to grant certain permissions to the third-part app.
|
||||
|
||||
Step 7: Try the CLI Example
|
||||
Step 6: Try the CLI Example
|
||||
---------------------------
|
||||
To try the CLI example run the following commands:
|
||||
|
||||
|
@ -183,7 +171,7 @@ The CLI example has two alternative methods for login. When a browser is availab
|
|||
temporary web server on a free port. If a browser is not available the URL to login is displayed on the CLI. The user can copy this URL to another computer that has a browser available. The code
|
||||
is displayed to the user after login and the user has to copy this code back to the application.
|
||||
|
||||
Step 8: Admin REST API
|
||||
Step 7: Admin REST API
|
||||
----------------------------------
|
||||
Keycloak has a Admin REST API. This example shows an application making a remote direct login to Keycloak to obtain a token
|
||||
then using that token to access the Admin REST API.
|
||||
|
@ -193,7 +181,7 @@ then using that token to access the Admin REST API.
|
|||
If you are already logged in, you will not be asked for a username and password, but you will be redirected to
|
||||
an oauth grant page. This page asks you if you want to grant certain permissions to the third-part app.
|
||||
|
||||
Step 9: Angular JS Example
|
||||
Step 8: Angular JS Example
|
||||
----------------------------------
|
||||
An Angular JS example using Keycloak to secure it.
|
||||
|
||||
|
@ -202,7 +190,7 @@ An Angular JS example using Keycloak to secure it.
|
|||
If you are already logged in, you will not be asked for a username and password, but you will be redirected to
|
||||
an oauth grant page. This page asks you if you want to grant certain permissions to the third-part app.
|
||||
|
||||
Step 10: Pure HTML5/Javascript Example
|
||||
Step 9: Pure HTML5/Javascript Example
|
||||
----------------------------------
|
||||
An pure HTML5/Javascript example using Keycloak to secure it.
|
||||
|
||||
|
@ -211,7 +199,7 @@ An pure HTML5/Javascript example using Keycloak to secure it.
|
|||
If you are already logged in, you will not be asked for a username and password, but you will be redirected to
|
||||
an oauth grant page. This page asks you if you want to grant certain permissions to the third-part app.
|
||||
|
||||
Step 11: Service Account Example
|
||||
Step 10: Service Account Example
|
||||
================================
|
||||
An example for retrieve service account dedicated to the Client Application itself (not to any user).
|
||||
|
||||
|
@ -219,7 +207,7 @@ An example for retrieve service account dedicated to the Client Application itse
|
|||
|
||||
Client authentication is done with OAuth2 Client Credentials Grant in out-of-bound request (Not Keycloak login screen displayed) .
|
||||
|
||||
Step 12: Offline Access Example
|
||||
Step 11: Offline Access Example
|
||||
===============================
|
||||
An example for retrieve offline token, which is then saved to the database and can be used by application anytime later. Offline token
|
||||
is valid even if user is already logged out from SSO. Server restart also won't invalidate offline token. Offline token can be revoked by the user in
|
||||
|
|
|
@ -41,8 +41,6 @@
|
|||
<module>admin-access-app</module>
|
||||
<module>angular-product-app</module>
|
||||
<module>database-service</module>
|
||||
<module>third-party</module>
|
||||
<module>third-party-cdi</module>
|
||||
<module>service-account</module>
|
||||
<module>offline-access-app</module>
|
||||
</modules>
|
||||
|
|
|
@ -1,98 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<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-examples-demo-parent</artifactId>
|
||||
<groupId>org.keycloak</groupId>
|
||||
<version>5.0.0-SNAPSHOT</version>
|
||||
</parent>
|
||||
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
<groupId>org.keycloak.example.demo</groupId>
|
||||
<artifactId>oauth-client-cdi-example</artifactId>
|
||||
<packaging>war</packaging>
|
||||
<name>Simple OAuth Client Using CDI and JSF</name>
|
||||
<description/>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.jboss.spec.javax.servlet</groupId>
|
||||
<artifactId>jboss-servlet-api_3.0_spec</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>javax.enterprise</groupId>
|
||||
<artifactId>cdi-api</artifactId>
|
||||
<version>2.0.SP1</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.jboss.spec.javax.faces</groupId>
|
||||
<artifactId>jboss-jsf-api_2.3_spec</artifactId>
|
||||
<version>2.3.9.SP01</version>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.jboss.logging</groupId>
|
||||
<artifactId>jboss-logging</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.keycloak</groupId>
|
||||
<artifactId>keycloak-core</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.keycloak</groupId>
|
||||
<artifactId>keycloak-adapter-core</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.keycloak</groupId>
|
||||
<artifactId>keycloak-servlet-oauth-client</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.httpcomponents</groupId>
|
||||
<artifactId>httpclient</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<build>
|
||||
<finalName>oauth-client-cdi</finalName>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.jboss.as.plugins</groupId>
|
||||
<artifactId>jboss-as-maven-plugin</artifactId>
|
||||
<configuration>
|
||||
<skip>false</skip>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.wildfly.plugins</groupId>
|
||||
<artifactId>wildfly-maven-plugin</artifactId>
|
||||
<configuration>
|
||||
<skip>false</skip>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</project>
|
|
@ -1,68 +0,0 @@
|
|||
/*
|
||||
* Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.example.oauth;
|
||||
|
||||
import org.jboss.logging.Logger;
|
||||
import org.keycloak.servlet.ServletOAuthClient;
|
||||
import org.keycloak.servlet.ServletOAuthClientBuilder;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.servlet.ServletContext;
|
||||
import javax.servlet.ServletContextEvent;
|
||||
import javax.servlet.ServletContextListener;
|
||||
import javax.servlet.annotation.WebListener;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FileNotFoundException;
|
||||
import java.io.InputStream;
|
||||
|
||||
/**
|
||||
* @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
|
||||
*/
|
||||
@WebListener
|
||||
public class AppContextListener implements ServletContextListener {
|
||||
|
||||
private static final Logger logger = Logger.getLogger(AppContextListener.class);
|
||||
|
||||
@Inject
|
||||
private ServletOAuthClient oauthClient;
|
||||
|
||||
@Override
|
||||
public void contextInitialized(ServletContextEvent sce) {
|
||||
ServletContext context = sce.getServletContext();
|
||||
|
||||
InputStream is = null;
|
||||
String path = context.getInitParameter("keycloak.config.file");
|
||||
if (path == null) {
|
||||
is = context.getResourceAsStream("/WEB-INF/keycloak.json");
|
||||
} else {
|
||||
try {
|
||||
is = new FileInputStream(path);
|
||||
} catch (FileNotFoundException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
ServletOAuthClientBuilder.build(is, oauthClient);
|
||||
logger.info("OAuth client configured and started");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void contextDestroyed(ServletContextEvent sce) {
|
||||
oauthClient.stop();
|
||||
logger.info("OAuth client stopped");
|
||||
}
|
||||
}
|
|
@ -1,58 +0,0 @@
|
|||
/*
|
||||
* Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.example.oauth;
|
||||
|
||||
import org.keycloak.servlet.ServletOAuthClient;
|
||||
|
||||
import javax.enterprise.context.ApplicationScoped;
|
||||
import javax.enterprise.context.RequestScoped;
|
||||
import javax.enterprise.inject.Produces;
|
||||
import javax.faces.context.FacesContext;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
|
||||
/**
|
||||
* @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
|
||||
*/
|
||||
public class CDIResourcesProducer {
|
||||
|
||||
@Produces
|
||||
@RequestScoped
|
||||
public FacesContext produceFacesContext() {
|
||||
return FacesContext.getCurrentInstance();
|
||||
}
|
||||
|
||||
@Produces
|
||||
@RequestScoped
|
||||
@ServletRequestQualifier
|
||||
public HttpServletRequest produceServletRequest() {
|
||||
return (HttpServletRequest)FacesContext.getCurrentInstance().getExternalContext().getRequest();
|
||||
}
|
||||
|
||||
@Produces
|
||||
@RequestScoped
|
||||
public HttpServletResponse produceServletResponse() {
|
||||
return (HttpServletResponse)FacesContext.getCurrentInstance().getExternalContext().getResponse();
|
||||
}
|
||||
|
||||
@Produces
|
||||
@ApplicationScoped
|
||||
public ServletOAuthClient produceOAuthClient() {
|
||||
return new ServletOAuthClient();
|
||||
}
|
||||
}
|
|
@ -1,129 +0,0 @@
|
|||
/*
|
||||
* Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.example.oauth;
|
||||
|
||||
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.apache.http.impl.client.DefaultHttpClient;
|
||||
import org.jboss.logging.Logger;
|
||||
import org.keycloak.KeycloakSecurityContext;
|
||||
import org.keycloak.common.util.UriUtils;
|
||||
import org.keycloak.servlet.ServletOAuthClient;
|
||||
import org.keycloak.util.JsonSerialization;
|
||||
|
||||
import javax.enterprise.context.ApplicationScoped;
|
||||
import javax.faces.application.FacesMessage;
|
||||
import javax.faces.context.FacesContext;
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
|
||||
* @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
|
||||
* @version $Revision: 1 $
|
||||
*/
|
||||
@ApplicationScoped
|
||||
@Named("databaseClient")
|
||||
public class DatabaseClient {
|
||||
|
||||
@Inject
|
||||
@ServletRequestQualifier
|
||||
private HttpServletRequest request;
|
||||
|
||||
@Inject
|
||||
private HttpServletResponse response;
|
||||
|
||||
@Inject
|
||||
private FacesContext facesContext;
|
||||
|
||||
@Inject
|
||||
private ServletOAuthClient oauthClient;
|
||||
|
||||
@Inject
|
||||
private UserData userData;
|
||||
|
||||
private static final Logger logger = Logger.getLogger(DatabaseClient.class);
|
||||
|
||||
public void retrieveAccessToken() {
|
||||
try {
|
||||
oauthClient.redirectRelative("client.jsf", request, response);
|
||||
} catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
|
||||
static class TypedList extends ArrayList<String> {}
|
||||
|
||||
public void sendCustomersRequest() {
|
||||
List<String> customers = sendRequestToDBApplication(getBaseUrl() + "/database/customers");
|
||||
userData.setCustomers(customers);
|
||||
}
|
||||
|
||||
public void sendProductsRequest() {
|
||||
List<String> products = sendRequestToDBApplication(getBaseUrl() + "/database/products");
|
||||
userData.setProducts(products);
|
||||
}
|
||||
|
||||
protected List<String> sendRequestToDBApplication(String dbUri) {
|
||||
HttpClient client = new DefaultHttpClient();
|
||||
HttpGet get = new HttpGet(dbUri);
|
||||
try {
|
||||
|
||||
if (userData.isHasAccessToken()) {
|
||||
get.addHeader("Authorization", "Bearer " + userData.getAccessToken());
|
||||
}
|
||||
|
||||
HttpResponse response = client.execute(get);
|
||||
switch (response.getStatusLine().getStatusCode()) {
|
||||
case 200: HttpEntity entity = response.getEntity();
|
||||
InputStream is = entity.getContent();
|
||||
try {
|
||||
return JsonSerialization.readValue(is, TypedList.class);
|
||||
} finally {
|
||||
is.close();
|
||||
}
|
||||
case 401: facesContext.addMessage(null, new FacesMessage("Status: 401. Request not authenticated! You need to retrieve access token first."));
|
||||
break;
|
||||
case 403: facesContext.addMessage(null, new FacesMessage("Status: 403. Access token has insufficient privileges"));
|
||||
break;
|
||||
default: facesContext.addMessage(null, new FacesMessage("Status: " + response.getStatusLine() + ". Not able to retrieve data. See log for details"));
|
||||
logger.warn("Error occured. Status: " + response.getStatusLine());
|
||||
}
|
||||
|
||||
return null;
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
facesContext.addMessage(null, new FacesMessage("Unknown error. See log for details"));
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public String getBaseUrl() {
|
||||
KeycloakSecurityContext session = (KeycloakSecurityContext)request.getAttribute(KeycloakSecurityContext.class.getName());
|
||||
return UriUtils.getOrigin(request.getRequestURL().toString());
|
||||
}
|
||||
|
||||
}
|
|
@ -1,51 +0,0 @@
|
|||
/*
|
||||
* Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.example.oauth;
|
||||
|
||||
import javax.enterprise.context.RequestScoped;
|
||||
import javax.faces.application.FacesMessage;
|
||||
import javax.faces.context.FacesContext;
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
|
||||
/**
|
||||
* This is needed because Faces context is not available in HTTP filters
|
||||
*
|
||||
* @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
|
||||
*/
|
||||
@RequestScoped
|
||||
@Named("messagesChecker")
|
||||
public class MessagesChecker {
|
||||
|
||||
@Inject
|
||||
@ServletRequestQualifier
|
||||
private HttpServletRequest request;
|
||||
|
||||
@Inject
|
||||
private FacesContext facesContext;
|
||||
|
||||
public String getCheckMessage() {
|
||||
String oauthError = (String)request.getAttribute(RefreshTokenFilter.OAUTH_ERROR_ATTR);
|
||||
if (oauthError != null) {
|
||||
facesContext.addMessage(null, new FacesMessage("OAuth error occured: " + oauthError));
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
|
@ -1,79 +0,0 @@
|
|||
/*
|
||||
* Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.example.oauth;
|
||||
|
||||
import org.keycloak.OAuth2Constants;
|
||||
import org.keycloak.adapters.ServerRequest;
|
||||
import org.keycloak.servlet.ServletOAuthClient;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.servlet.Filter;
|
||||
import javax.servlet.FilterChain;
|
||||
import javax.servlet.FilterConfig;
|
||||
import javax.servlet.ServletException;
|
||||
import javax.servlet.ServletRequest;
|
||||
import javax.servlet.ServletResponse;
|
||||
import javax.servlet.annotation.WebFilter;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.IOException;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
|
||||
*/
|
||||
@WebFilter(value = "/client.jsf")
|
||||
public class RefreshTokenFilter implements Filter {
|
||||
|
||||
public static final String OAUTH_ERROR_ATTR = "oauthErrorAttr";
|
||||
|
||||
@Inject
|
||||
private ServletOAuthClient oauthClient;
|
||||
|
||||
@Inject
|
||||
private UserData userData;
|
||||
|
||||
@Override
|
||||
public void init(FilterConfig filterConfig) throws ServletException {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws IOException, ServletException {
|
||||
HttpServletRequest request = (HttpServletRequest)req;
|
||||
HttpServletResponse response = (HttpServletResponse)resp;
|
||||
Map<String, String[]> reqParams = request.getParameterMap();
|
||||
|
||||
if (reqParams.containsKey(OAuth2Constants.CODE)) {
|
||||
try {
|
||||
String accessToken = oauthClient.getBearerToken(request).getToken();
|
||||
userData.setAccessToken(accessToken);
|
||||
} catch (ServerRequest.HttpFailure e) {
|
||||
throw new ServletException(e);
|
||||
}
|
||||
} else if (reqParams.containsKey(OAuth2Constants.ERROR)) {
|
||||
String oauthError = reqParams.get(OAuth2Constants.ERROR)[0];
|
||||
request.setAttribute(OAUTH_ERROR_ATTR, oauthError);
|
||||
}
|
||||
|
||||
chain.doFilter(request, response);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void destroy() {
|
||||
}
|
||||
}
|
|
@ -1,35 +0,0 @@
|
|||
/*
|
||||
* Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.example.oauth;
|
||||
|
||||
import javax.inject.Qualifier;
|
||||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
|
||||
/**
|
||||
* This is needed to have same code working in AS7 and Wildfly. In Wildfly is HttpServletRequest injected automatically, in AS7 it's not
|
||||
*
|
||||
* @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
|
||||
*/
|
||||
@Qualifier
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Target({ElementType.FIELD, ElementType.METHOD, ElementType.PARAMETER })
|
||||
public @interface ServletRequestQualifier {
|
||||
}
|
|
@ -1,79 +0,0 @@
|
|||
/*
|
||||
* Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.example.oauth;
|
||||
|
||||
import javax.enterprise.context.SessionScoped;
|
||||
import javax.inject.Named;
|
||||
import java.io.Serializable;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author <a href="mailto:mposolda@redhat.com">Marek Posolda</a>
|
||||
*/
|
||||
@SessionScoped
|
||||
@Named("userData")
|
||||
public class UserData implements Serializable {
|
||||
|
||||
private String accessToken;
|
||||
private List<String> products;
|
||||
private List<String> customers;
|
||||
|
||||
public String getAccessToken() {
|
||||
return accessToken;
|
||||
}
|
||||
|
||||
public void setAccessToken(String accessToken) {
|
||||
this.accessToken = accessToken;
|
||||
}
|
||||
|
||||
public boolean isHasAccessToken() {
|
||||
return accessToken != null;
|
||||
}
|
||||
|
||||
public String getAccessTokenAvailabilityMessage() {
|
||||
StringBuilder builder = new StringBuilder("Access token ");
|
||||
if (!isHasAccessToken()) {
|
||||
builder.append("not ");
|
||||
}
|
||||
return builder.append("available!").toString();
|
||||
}
|
||||
|
||||
public List<String> getProducts() {
|
||||
return products;
|
||||
}
|
||||
|
||||
public void setProducts(List<String> products) {
|
||||
this.products = products;
|
||||
}
|
||||
|
||||
public boolean isHasProducts() {
|
||||
return products != null;
|
||||
}
|
||||
|
||||
public List<String> getCustomers() {
|
||||
return customers;
|
||||
}
|
||||
|
||||
public void setCustomers(List<String> customers) {
|
||||
this.customers = customers;
|
||||
}
|
||||
|
||||
public boolean isHasCustomers() {
|
||||
return customers != null;
|
||||
}
|
||||
}
|
|
@ -1,23 +0,0 @@
|
|||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
<!-- Marker file indicating CDI should be enabled -->
|
||||
<beans 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/beans_1_0.xsd">
|
||||
</beans>
|
|
@ -1,23 +0,0 @@
|
|||
<?xml version="1.0"?>
|
||||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
<!-- Marker file indicating JSF should be enabled -->
|
||||
<faces-config version="2.0" 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-facesconfig_2_0.xsd">
|
||||
|
||||
</faces-config>
|
|
@ -1,31 +0,0 @@
|
|||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<jboss-deployment-structure>
|
||||
<deployment>
|
||||
<dependencies>
|
||||
<!-- the Demo code uses classes in these modules. These are optional to import if you are not using
|
||||
Apache Http Client or the HttpClientBuilder that comes with the adapter core -->
|
||||
<module name="org.apache.httpcomponents"/>
|
||||
<module name="org.keycloak.keycloak-servlet-oauth-client"/>
|
||||
<module name="org.keycloak.keycloak-adapter-spi"/>
|
||||
<module name="org.keycloak.keycloak-adapter-core"/>
|
||||
<module name="org.keycloak.keycloak-common"/>
|
||||
<module name="org.keycloak.keycloak-core"/>
|
||||
</dependencies>
|
||||
</deployment>
|
||||
</jboss-deployment-structure>
|
|
@ -1,9 +0,0 @@
|
|||
{
|
||||
"realm" : "demo",
|
||||
"resource" : "third-party",
|
||||
"auth-server-url" : "/auth",
|
||||
"ssl-required" : "external",
|
||||
"credentials" : {
|
||||
"secret": "password"
|
||||
}
|
||||
}
|
|
@ -1,37 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<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>oauth-client-cdi</module-name>
|
||||
|
||||
<!--
|
||||
<security-constraint>
|
||||
<web-resource-collection>
|
||||
<url-pattern>/*</url-pattern>
|
||||
</web-resource-collection>
|
||||
<user-data-constraint>
|
||||
<transport-guarantee>CONFIDENTIAL</transport-guarantee>
|
||||
</user-data-constraint>
|
||||
</security-constraint>
|
||||
-->
|
||||
|
||||
</web-app>
|
|
@ -1,55 +0,0 @@
|
|||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<!DOCTYPE html
|
||||
PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
|
||||
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:ui="http://java.sun.com/jsf/facelets"
|
||||
xmlns:h="http://java.sun.com/jsf/html"
|
||||
>
|
||||
<body>
|
||||
<h1>Third Party App That Pulls Data Using OAuth</h1>
|
||||
<h:form>
|
||||
#{userData.accessTokenAvailabilityMessage}
|
||||
<br />
|
||||
<h:commandButton id="retrieve_token" value="Retrieve/refresh access token" action="#{databaseClient.retrieveAccessToken}"/>
|
||||
<h:commandButton id="products_request" value="Load products list" action="#{databaseClient.sendProductsRequest}"/>
|
||||
<h:commandButton id="customers_request" value="Load customers list" action="#{databaseClient.sendCustomersRequest}"/>
|
||||
</h:form>
|
||||
|
||||
<ui:fragment rendered="#{userData.hasProducts}">
|
||||
<hr />
|
||||
<h3>Products data available</h3>
|
||||
<ui:repeat value="#{userData.products}" var="product">
|
||||
#{product}<br/>
|
||||
</ui:repeat>
|
||||
</ui:fragment>
|
||||
|
||||
<ui:fragment rendered="#{userData.hasCustomers}">
|
||||
<hr />
|
||||
<h3>Customers data available</h3>
|
||||
<ui:repeat value="#{userData.customers}" var="customer">
|
||||
#{customer}<br/>
|
||||
</ui:repeat>
|
||||
</ui:fragment>
|
||||
|
||||
<div style="color: red">
|
||||
#{messagesChecker.checkMessage}
|
||||
<h:messages globalOnly="true"/>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
|
@ -1,22 +0,0 @@
|
|||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<html>
|
||||
<head>
|
||||
<meta http-equiv="Refresh" content="0; URL=client.jsf">
|
||||
</head>
|
||||
</html>
|
81
examples/demo-template/third-party/pom.xml
vendored
81
examples/demo-template/third-party/pom.xml
vendored
|
@ -1,81 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<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-examples-demo-parent</artifactId>
|
||||
<groupId>org.keycloak</groupId>
|
||||
<version>5.0.0-SNAPSHOT</version>
|
||||
</parent>
|
||||
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
<groupId>org.keycloak.example.demo</groupId>
|
||||
<artifactId>oauth-client-example</artifactId>
|
||||
<packaging>war</packaging>
|
||||
<name>Simple OAuth Client</name>
|
||||
<description/>
|
||||
|
||||
<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>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.keycloak</groupId>
|
||||
<artifactId>keycloak-adapter-core</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.keycloak</groupId>
|
||||
<artifactId>keycloak-servlet-oauth-client</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.apache.httpcomponents</groupId>
|
||||
<artifactId>httpclient</artifactId>
|
||||
<scope>provided</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<build>
|
||||
<finalName>oauth-client</finalName>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.jboss.as.plugins</groupId>
|
||||
<artifactId>jboss-as-maven-plugin</artifactId>
|
||||
<configuration>
|
||||
<skip>false</skip>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.wildfly.plugins</groupId>
|
||||
<artifactId>wildfly-maven-plugin</artifactId>
|
||||
<configuration>
|
||||
<skip>false</skip>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</project>
|
|
@ -1,70 +0,0 @@
|
|||
/*
|
||||
* Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.example.oauth;
|
||||
|
||||
import org.keycloak.servlet.ServletOAuthClient;
|
||||
import org.keycloak.servlet.ServletOAuthClientBuilder;
|
||||
|
||||
import javax.servlet.ServletContext;
|
||||
import javax.servlet.ServletContextEvent;
|
||||
import javax.servlet.ServletContextListener;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FileNotFoundException;
|
||||
import java.io.InputStream;
|
||||
|
||||
/**
|
||||
* Init code to load up the truststore so we can make appropriate SSL connections
|
||||
* You really should use a better way of initializing this stuff.
|
||||
*
|
||||
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
|
||||
* @version $Revision: 1 $
|
||||
*/
|
||||
public class Bootstrap implements ServletContextListener {
|
||||
|
||||
private ServletOAuthClient client;
|
||||
|
||||
@Override
|
||||
public void contextInitialized(ServletContextEvent sce) {
|
||||
client = new ServletOAuthClient();
|
||||
ServletContext context = sce.getServletContext();
|
||||
|
||||
configureClient(context);
|
||||
context.setAttribute(ServletOAuthClient.class.getName(), client);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void contextDestroyed(ServletContextEvent sce) {
|
||||
client.stop();
|
||||
}
|
||||
|
||||
private void configureClient(ServletContext context) {
|
||||
InputStream is = null;
|
||||
String path = context.getInitParameter("keycloak.config.file");
|
||||
if (path == null) {
|
||||
is = context.getResourceAsStream("/WEB-INF/keycloak.json");
|
||||
} else {
|
||||
try {
|
||||
is = new FileInputStream(path);
|
||||
} catch (FileNotFoundException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
|
||||
client = ServletOAuthClientBuilder.build(is);
|
||||
}
|
||||
}
|
|
@ -1,121 +0,0 @@
|
|||
/*
|
||||
* Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
* and other contributors as indicated by the @author tags.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.keycloak.example.oauth;
|
||||
|
||||
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.apache.http.impl.client.DefaultHttpClient;
|
||||
import org.keycloak.KeycloakSecurityContext;
|
||||
import org.keycloak.adapters.ServerRequest;
|
||||
import org.keycloak.common.util.UriUtils;
|
||||
import org.keycloak.representations.AccessTokenResponse;
|
||||
import org.keycloak.servlet.ServletOAuthClient;
|
||||
import org.keycloak.util.JsonSerialization;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author <a href="mailto:bill@burkecentral.com">Bill Burke</a>
|
||||
* @version $Revision: 1 $
|
||||
*/
|
||||
public class ProductDatabaseClient {
|
||||
|
||||
public static class Failure extends Exception {
|
||||
private int status;
|
||||
|
||||
public Failure(int status) {
|
||||
this.status = status;
|
||||
}
|
||||
|
||||
public int getStatus() {
|
||||
return status;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static void redirect(HttpServletRequest request, HttpServletResponse response) {
|
||||
// The ServletOAuthClient is obtained by getting a context attribute
|
||||
// that is set in the Bootstrap context listener in this project.
|
||||
// You really should come up with a better way to initialize
|
||||
// and obtain the ServletOAuthClient. I actually suggest downloading the ServletOAuthClient code
|
||||
// and take a look how it works. You can also take a look at third-party-cdi example
|
||||
ServletOAuthClient oAuthClient = (ServletOAuthClient) request.getServletContext().getAttribute(ServletOAuthClient.class.getName());
|
||||
try {
|
||||
oAuthClient.redirectRelative("pull_data.jsp", request, response);
|
||||
} catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
|
||||
static class TypedList extends ArrayList<String> {}
|
||||
|
||||
public static AccessTokenResponse getTokenResponse(HttpServletRequest request) {
|
||||
// The ServletOAuthClient is obtained by getting a context attribute
|
||||
// that is set in the Bootstrap context listener in this project.
|
||||
// You really should come up with a better way to initialize
|
||||
// and obtain the ServletOAuthClient. I actually suggest downloading the ServletOAuthClient code
|
||||
// and take a look how it works. You can also take a look at third-party-cdi example
|
||||
ServletOAuthClient oAuthClient = (ServletOAuthClient) request.getServletContext().getAttribute(ServletOAuthClient.class.getName());
|
||||
try {
|
||||
return oAuthClient.getBearerToken(request);
|
||||
} catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
} catch (ServerRequest.HttpFailure failure) {
|
||||
throw new RuntimeException(failure);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public static List<String> getProducts(HttpServletRequest request, String accessToken) throws Failure {
|
||||
KeycloakSecurityContext session = (KeycloakSecurityContext) request.getAttribute(KeycloakSecurityContext.class.getName());
|
||||
|
||||
// The ServletOAuthClient is obtained by getting a context attribute
|
||||
// that is set in the Bootstrap context listener in this project.
|
||||
// You really should come up with a better way to initialize
|
||||
// and obtain the ServletOAuthClient. I actually suggest downloading the ServletOAuthClient code
|
||||
// and take a look how it works. You can also take a look at third-party-cdi example
|
||||
ServletOAuthClient oAuthClient = (ServletOAuthClient) request.getServletContext().getAttribute(ServletOAuthClient.class.getName());
|
||||
HttpClient client = new DefaultHttpClient();
|
||||
|
||||
HttpGet get = new HttpGet(UriUtils.getOrigin(request.getRequestURL().toString()) + "/database/products");
|
||||
get.addHeader("Authorization", "Bearer " + accessToken);
|
||||
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);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -1,31 +0,0 @@
|
|||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<jboss-deployment-structure>
|
||||
<deployment>
|
||||
<dependencies>
|
||||
<!-- the Demo code uses classes in these modules. These are optional to import if you are not using
|
||||
Apache Http Client or the HttpClientBuilder that comes with the adapter core -->
|
||||
<module name="org.apache.httpcomponents"/>
|
||||
<module name="org.keycloak.keycloak-servlet-oauth-client"/>
|
||||
<module name="org.keycloak.keycloak-adapter-spi"/>
|
||||
<module name="org.keycloak.keycloak-adapter-core"/>
|
||||
<module name="org.keycloak.keycloak-common"/>
|
||||
<module name="org.keycloak.keycloak-core"/>
|
||||
</dependencies>
|
||||
</deployment>
|
||||
</jboss-deployment-structure>
|
|
@ -1,10 +0,0 @@
|
|||
{
|
||||
"realm" : "demo",
|
||||
"resource" : "third-party",
|
||||
"auth-server-url" : "/auth",
|
||||
"ssl-required" : "external",
|
||||
"credentials" : {
|
||||
"secret": "password"
|
||||
},
|
||||
"enable-pkce" : true
|
||||
}
|
|
@ -1,46 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<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>oauth-client</module-name>
|
||||
|
||||
<listener>
|
||||
<listener-class>org.keycloak.example.oauth.Bootstrap</listener-class>
|
||||
</listener>
|
||||
|
||||
<error-page>
|
||||
<exception-type>java.lang.RuntimeException</exception-type>
|
||||
<location>/error.jsp</location>
|
||||
</error-page>
|
||||
|
||||
<!--
|
||||
<security-constraint>
|
||||
<web-resource-collection>
|
||||
<url-pattern>/*</url-pattern>
|
||||
</web-resource-collection>
|
||||
<user-data-constraint>
|
||||
<transport-guarantee>CONFIDENTIAL</transport-guarantee>
|
||||
</user-data-constraint>
|
||||
</security-constraint>
|
||||
-->
|
||||
|
||||
</web-app>
|
|
@ -1 +0,0 @@
|
|||
An error occurred. Click <a href="index.html"> to try again.
|
|
@ -1,23 +0,0 @@
|
|||
<!--
|
||||
~ Copyright 2016 Red Hat, Inc. and/or its affiliates
|
||||
~ and other contributors as indicated by the @author tags.
|
||||
~
|
||||
~ Licensed under the Apache License, Version 2.0 (the "License");
|
||||
~ you may not use this file except in compliance with the License.
|
||||
~ You may obtain a copy of the License at
|
||||
~
|
||||
~ http://www.apache.org/licenses/LICENSE-2.0
|
||||
~
|
||||
~ Unless required by applicable law or agreed to in writing, software
|
||||
~ distributed under the License is distributed on an "AS IS" BASIS,
|
||||
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
~ See the License for the specific language governing permissions and
|
||||
~ limitations under the License.
|
||||
-->
|
||||
|
||||
<html>
|
||||
<body>
|
||||
<h1>Third Party App That Pulls Data Using OAuth</h1>
|
||||
<a href="redirect.jsp">Pull Data</a>
|
||||
</body>
|
||||
</html>
|
|
@ -1,49 +0,0 @@
|
|||
<%@ page import="org.keycloak.example.oauth.ProductDatabaseClient" %>
|
||||
<%@ page import="org.keycloak.representations.AccessTokenResponse" %>
|
||||
<%@ page import="org.keycloak.representations.IDToken" %>
|
||||
<%@ page import="org.keycloak.servlet.ServletOAuthClient" %>
|
||||
<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
|
||||
pageEncoding="ISO-8859-1"%>
|
||||
<%@ page session="false" %>
|
||||
<html>
|
||||
<head>
|
||||
<title>Pull Page</title>
|
||||
</head>
|
||||
<body>
|
||||
<%
|
||||
java.util.List<String> list = null;
|
||||
try {
|
||||
AccessTokenResponse tokenResponse = ProductDatabaseClient.getTokenResponse(request);
|
||||
if (tokenResponse.getIdToken() != null) {
|
||||
IDToken idToken = ServletOAuthClient.extractIdToken(tokenResponse.getIdToken());
|
||||
if (idToken.getPreferredUsername() != null) {
|
||||
out.println("<p>Username: " + idToken.getPreferredUsername() + "</p>");
|
||||
}
|
||||
if (idToken.getName() != null) {
|
||||
out.println("<p>Full Name: " + idToken.getName() + "</p>");
|
||||
}
|
||||
if (idToken.getEmail() != null) {
|
||||
out.println("<p>Email: " + idToken.getEmail() + "</p>");
|
||||
}
|
||||
}
|
||||
list = ProductDatabaseClient.getProducts(request, tokenResponse.getToken());
|
||||
} catch (ProductDatabaseClient.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 database service?");
|
||||
out.println("Status from database service invocation was: " + failure.getStatus());
|
||||
return;
|
||||
}
|
||||
%>
|
||||
<h2>Pulled Product Listing</h2>
|
||||
<%
|
||||
for (String prod : list)
|
||||
{
|
||||
out.print("<p>");
|
||||
out.print(prod);
|
||||
out.println("</p>");
|
||||
|
||||
}
|
||||
%>
|
||||
<br><br>
|
||||
</body>
|
||||
</html>
|
|
@ -1,5 +0,0 @@
|
|||
<%@ page import="org.keycloak.example.oauth.ProductDatabaseClient" %>
|
||||
<%@ page session="false" %>
|
||||
<%
|
||||
ProductDatabaseClient.redirect(request, response);
|
||||
%>
|
Loading…
Reference in a new issue