0% found this document useful (0 votes)
167 views

Secure REST Service With OAuth2 Tokens - Java Code Geeks - 2018 PDF

The document discusses securing REST APIs with OAuth2 tokens in Spring Security. It provides an overview of using the resource owner password credentials grant type, where a client receives an access token after authenticating a user's credentials. The implementation section outlines configuring Spring Security dependencies, adding OAuth2 support to web.xml for authentication filtering, and configuring OAuth in the spring-security.xml file to secure URLs under /api and define the /oauth/token endpoint for generating tokens.
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
167 views

Secure REST Service With OAuth2 Tokens - Java Code Geeks - 2018 PDF

The document discusses securing REST APIs with OAuth2 tokens in Spring Security. It provides an overview of using the resource owner password credentials grant type, where a client receives an access token after authenticating a user's credentials. The implementation section outlines configuring Spring Security dependencies, adding OAuth2 support to web.xml for authentication filtering, and configuring OAuth in the spring-security.xml file to secure URLs under /api and define the /oauth/token endpoint for generating tokens.
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 9

11/5/2018 Secure REST Service with OAuth2 Tokens | Java Code Geeks - 2018

1. Introduction
In this tutorial, we will check out how we can use Spring Security with OAuth to secure REST Service. In the demo
application, the secured REST resources on the server are accessible with the path pattern ( /api/**
), such that the request
URLs based on this path are mapped to different controller methods. This means that –

Any REST request URL without ‘ /api‘ in the path will stay invalid, as these won’t match to any of the controller
mappings.
After the required OAuth2 configurations are done, any REST request URL without a token as parameter will
be unauthorized
.

Another path pattern ( /oauth/token


) we have configured which will help configured authorization server generate the
access token. Note that we will be using Password Grant Type in this demo application.

Before we move on with the implementation, let’s recap on the events involved with this grant type.

2. Resource Owner Password Credentials Grant Type


Used between trusted applications.
The user (Resource Owner) shares the credentials directly with the client application, which requests the Authorization
Server to return the access token after successfully authenticating the user credentials and further authorizing the user
to access limited resources on the server.

Useful Links
Learn more about other Authorization Grant Types
Understanding OAuth2 token authentication

3. Implementation
Make sure the required pom entries are properly added to the pom.xml file.

pom.xml
01 <projectxmlns="http://maven.apache.org/POM/4.0.0"xmlns:xsi="http://www.w3.org/2001/XMLSchema-
instance"
02 xsi:schemaLocation="http://maven.apache.org/POM/4.0.0http://maven.apache.org/xsd/maven-
4.0.0.xsd">
03 <modelVersion>4.0.0</modelVersion>
04 <groupId>org.springframework.samples.service.service</groupId>
05 <artifactId>SecureRESTWithOAuth</artifactId>
06 <version>0.0.1-SNAPSHOT</version>
07 <packaging>war</packaging>
08
09 <dependencies>
10 <dependency>
11 <groupId>junit</groupId>
12 <artifactId>junit</artifactId>
13 <version>3.8.1</version>
14 <scope>test</scope>
15 </dependency>
16
17 <!-- Spring dependencies -->
18 <dependency>
19 <groupId>org.springframework</groupId>
20 <artifactId>spring-
core</artifactId>
https://www.javacodegeeks.com/2017/09/secure-rest-service-oauth2-tokens.html# 1/9
11/5/2018 Secure REST Service with OAuth2 Tokens | Java Code Geeks - 2018
core</artifactId>
21 <version>4.2.1.RELEASE</version>
22 </dependency>
23
24 <dependency>
25 <groupId>org.springframework</groupId>
26 <artifactId>spring-
web</artifactId>
27 <version>4.2.1.RELEASE</version>
28 </dependency>
29
30 <dependency>
31 <groupId>org.springframework</groupId>
32 <artifactId>spring-
webmvc</artifactId>
33 <version>4.2.1.RELEASE</version>
34 </dependency>
35
36 <!-- Jackson JSON Processor -->
37 <dependency>
38 <groupId>com.fasterxml.jackson.core</groupId>
39 <artifactId>jackson-
databind</artifactId>
40 <version>2.4.1</version>
41 </dependency>
42
43 <!-- Spring Security Dependencies
-->
44 <dependency>
45 <groupId>org.springframework.security</groupId>
46 <artifactId>spring-security-
core</artifactId>
47 <version>3.2.3.RELEASE</version>
48 </dependency>
49 <dependency>
50 <groupId>org.springframework.security</groupId>
51 <artifactId>spring-security-
web</artifactId>
52 <version>3.2.3.RELEASE</version>
53 </dependency>
54 <dependency>
55 <groupId>org.springframework.security</groupId>
56 <artifactId>spring-security-
config</artifactId>
57 <version>3.2.3.RELEASE</version>
58 </dependency>
59 <dependency>
60 <groupId>org.springframework.security.oauth</groupId>
61 <artifactId>spring-security-
oauth2</artifactId>
62 <version>1.0.0.RELEASE</version>
63 </dependency>
64 </dependencies>
65 </project>

web.xml
Update the web.xml file to load the context files and configure the Spring Security filter, which will redirect the request for
authentication and authorization before processing it.

https://www.javacodegeeks.com/2017/09/secure-rest-service-oauth2-tokens.html# 2/9
11/5/2018 Secure REST Service with OAuth2 Tokens | Java Code Geeks - 2018

01 <?xml version="1.0" encoding="ISO-8859-1"?


>
02 <web-
appxmlns:xsi="http://www.w3.org/2001/XMLSchema-
instance"
03 xmlns="http://java.sun.com/xml/ns/javaee"
04 xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
05 http://java.sun.com/xml/ns/javaee/web-
app_2_5.xsd"
06 id="WebApp_ID" version="2.5">
07
08 <display-
name>SecureRESTWithOAuth</display-name>
09
10 <servlet>
11 <servlet-name>mvc-
dispatcher</servlet-name>
12 <servlet-
class>org.springframework.web.servlet.DispatcherServlet</servlet-
class>
13 <load-on-startup>1</load-on-
startup>
14 </servlet>
15
16 <servlet-mapping>
17 <servlet-name>mvc-
dispatcher</servlet-name>
18 <url-pattern>/*</url-pattern>
19 </servlet-mapping>
20
21 <listener>
22 <listener-
class>org.springframework.web.context.ContextLoaderListener</listener-
class>
23 </listener>
24
25 <!-- Loads context files -->
26 <context-param>
27 <param-
name>contextConfigLocation</param-name>
28 <param-value>
29 /WEB-INF/mvc-dispatcher-
servlet.xml,
30 /WEB-INF/spring-security.xml
31 </param-value>
32 </context-param>
33
34 <!-- Spring Security -->
35 <filter>
36 <filter-
name>springSecurityFilterChain</filter-
name>
37 <filter-
class>org.springframework.web.filter.DelegatingFilterProxy
38 </filter-class>
39 </filter>
40
41 <filter-mapping>
42 <filter-
name>springSecurityFilterChain</filter-
name>
43 <url-pattern>/*</url-pattern>
44 </filter-mapping>
45
46 </web-app>

mvc-dispatcher-servlet.xml
https://www.javacodegeeks.com/2017/09/secure-rest-service-oauth2-tokens.html# 3/9
11/5/2018 Secure REST Service with OAuth2 Tokens | Java Code Geeks - 2018

01 <?xml version="1.0" encoding="UTF-8"?>


02 <beans xmlns="http://www.springframework.or
03 xmlns:xsi="http://www.w3.org/2001/XMLSc
04 xmlns:util="http://www.springframework.
05 xsi:schemaLocation="http://www.springfr
06 http://www.springframework.org/schema/bea
07 http://www.springframework.org/schema/uti
08 http://www.springframework.org/schema/con
09
10 <context:component-scan base-package="c
11 <mvc:annotation-driven />
12
13 </beans>

Since we will are using admin JSP files, we have configured the corresponding view resolver for it.

Now let’s configure the Spring Security OAuth in its context file.

spring-security.xml
001 <?xml version="1.0" encoding="UTF-8" ?>
002 <beans xmlns="http://www.springframework.or
003 xmlns:xsi="http://www.w3.org/2001/XMLSc
004 xmlns:context="http://www.springframewo
005 xmlns:sec="http://www.springframework.o
006 xsi:schemaLocation="http://www.springfr
007 http://www.springframework.org/schema/mvc
008 http://www.springframework.org/schema/sec
009 http://www.springframework.org/schema/bea
010 http://www.springframework.org/schema/con
011
012 <!-- Default url to get a token from OA
013 <http pattern="/oauth/token" create-ses
014 authentication-manager-ref="clientA
015 xmlns="http://www.springframework.o
016 <intercept-url pattern="/oauth/toke
017 <anonymous enabled="false" />
018 <http-basic entry-point-ref="client
019 <custom-filter ref="clientCredentia
020 after="BASIC_AUTH_FILTER" />
021 <access-denied-handler ref="oauthAc
022 </http>
023
024 <!-- URLs should be protected and what
025 <!-- Can define more patterns based on
026 the server -->
027 <http pattern="/api/**" create-session=
028 entry-point-ref="oauthAuthenticatio
029 access-decision-manager-ref="access
030 xmlns="http://www.springframework.o
031 <anonymous enabled="false" />
032 <intercept-url pattern="/api/**" ac
033 <!-- Protect oauth clients with res
034 <custom-filter ref="resourceServerF
035 <access-denied-handler ref="oauthAc
036 </http>
037
038 <bean id="oauthAuthenticationEntryPoint
039 class="org.springframework.security
040 <property name="realmName" value="d
041 </bean>
042
043 <bean id="clientAuthenticationEntryPoin
044 class="org.springframework.security
045 <property name="realmName" value="d
046 < t "t N " l "B
https://www.javacodegeeks.com/2017/09/secure-rest-service-oauth2-tokens.html# 4/9
11/5/2018 Secure REST Service with OAuth2 Tokens | Java Code Geeks - 2018
046 <property name="typeName" value="Ba
047 </bean>
048
049 <bean id="oauthAccessDeniedHandler"
050 class="org.springframework.security
051
052 <bean id="clientCredentialsTokenEndpoin
053 class="org.springframework.security
054 <property name="authenticationManag
055 </bean>
056
057 <bean id="accessDecisionManager" class=
058 xmlns="http://www.springframework.o
059 <constructor-arg>
060 <list>
061 <bean class="org.springfram
062 <bean class="org.springfram
063 <bean class="org.springfram
064 </list>
065 </constructor-arg>
066 </bean>
067
068 <authentication-manager id="clientAuthe
069 xmlns="http://www.springframework.o
070 <authentication-provider user-servi
071 </authentication-manager>
072
073 <!-- This is simple authentication mana
074 combination. We can replace this wi
075 credentials from DB instead -->
076 <authentication-manager alias="authenti
077 xmlns="http://www.springframework.o
078 <authentication-provider>
079 <user-service>
080 <user name="admin" password
081 </user-service>
082 </authentication-provider>
083 </authentication-manager>
084
085 <bean id="clientDetailsUserService"
086 class="org.springframework.security
087 <constructor-arg ref="clientDetails
088 </bean>
089
090 <!-- This defines the token store. We h
091 store but we can instead use a user
092 <bean id="tokenStore"
093 class="org.springframework.security
094 <!-- If need to store tokens in DB
095 <bean id="tokenStore"
096 class="org.springframework.security
097 <constructor-arg ref="jdbcTemplate"
098 </bean> -->
099
100 <!-- This is where we defined token bas
101 and other things -->
102 <bean id="tokenServices"
103 class="org.springframework.security
104 <property name="tokenStore" ref="to
105 <property name="supportRefreshToken
106 <property name="accessTokenValidity
107 <property name="clientDetailsServic
108 </bean>
109
110 <bean id="userApprovalHandler"
111 class="org.springframework.security
112 <property name="tokenServices" ref=
113 </bean>
114
https://www.javacodegeeks.com/2017/09/secure-rest-service-oauth2-tokens.html# 5/9
11/5/2018 Secure REST Service with OAuth2 Tokens | Java Code Geeks - 2018
115 <!-- The server issuing access tokens t
116 the resource owner and obtaining au
117 <oauth:authorization-server
118 client-details-service-ref="clientD
119 user-approval-handler-ref="userAppr
120 <oauth:authorization-code />
121 <oauth:implicit />
122 <oauth:refresh-token />
123 <oauth:client-credentials />
124 <oauth:password />
125 </oauth:authorization-server>
126
127 <!-- Define protected resources hosted
128 <oauth:resource-server id="resourceServ
129 resource-id="adminProfile" token-se
130
131 <!-- OAuth clients allowed to access th
132 like facebook, google if we are sha
133 <oauth:client-details-service id="clien
134 <oauth:client client-id="fbApp"
135 authorized-grant-types="passwor
136 secret="fbApp" authorities="ROL
137 </oauth:client-details-service>
138
139 <sec:global-method-security
140 pre-post-annotations="enabled" prox
141 <sec:expression-handler ref="oauthE
142 </sec:global-method-security>
143
144 <oauth:expression-handler id="oauthExpr
145 <oauth:web-expression-handler id="oauth
146
147 </beans>

We have configured /oauth/token URL for issuing access and refresh tokens and /api/** maps to the actual protected
resources on the server. Hence to access any URL matching the pattern /api/**, a valid token needs to be passed along
with the request.

Authentication Manager is the container where the authentication happens. In our case, the authentication manager
checks –

If the user is authenticated.


If the user has requested for the correct client-id.
If the client-id is fine, is the user authorized to use it to access the admin profile on the server.

Refer to the below snippet –

https://www.javacodegeeks.com/2017/09/secure-rest-service-oauth2-tokens.html# 6/9
11/5/2018 Secure REST Service with OAuth2 Tokens | Java Code Geeks - 2018

01 <authentication-manager id="clientAuthentic
02 xmlns="http://www.springframework.o
03 <authentication-provider user-service-r
04 </authentication-manager>
05
06 <bean id="clientDetailsUserService"
07 class="org.springframework.security
08 <constructor-arg ref="clientDetails" />
09 </bean>
10
11 <!-- OAuth clients allowed to access the pr
12 like facebook, google if we are sha
13 <oauth:client-details-service id="clientDet
14 <oauth:client client-id="fbApp"
15 authorized-grant-types="password,re
16 secret="fbApp" authorities="ROLE_AP
17 </oauth:client-details-service>

Once the user is authenticated, the authorization servercalls the tokenServices and issues the access token.

01 <oauth:authorization-server
02 client-details-service-ref="clientDetai
03 user-approval-handler-ref="userApproval
04 <oauth:authorization-code />
05 <oauth:implicit />
06 <oauth:refresh-token />
07 <oauth:client-credentials />
08 <oauth:password />
09 </oauth:authorization-server>
10
11 <bean id="tokenServices"
12 class="org.springframework.security
13 <property name="tokenStore" ref="tokenS
14 <property name="supportRefreshToken" va
15 <property name="accessTokenValiditySeco
16 <property name="clientDetailsService" r
17 </bean>
18
19 <bean id="tokenStore"
20 class="org.springframework.security
21
22 <bean id="userApprovalHandler"
23 class="org.springframework.security
24 <property name="tokenServices" ref="tok
25 </bean>

While specifying the clients, note the grant type we have specified, which is password.
1 <oauth:client-details-service id="clientDet
2 <oauth:client client-id="fbApp"
3 authorized-grant-types="password,re
4 secret="fbApp" authorities="ROLE_AP
5 </oauth:client-details-service&gt

Once the access token has been issued, we can access the protected resources on the server passing it along with every
request. Let’s finally take a look at the Spring Controller we have written –

EmployeeController.java

https://www.javacodegeeks.com/2017/09/secure-rest-service-oauth2-tokens.html# 7/9
11/5/2018 Secure REST Service with OAuth2 Tokens | Java Code Geeks - 2018

01 package com.jcombat.controller;
02
03 importorg.springframework.web.bind.annotation.PathVariable;
04 importorg.springframework.web.bind.annotation.RequestMapping;
05 importorg.springframework.web.bind.annotation.RequestMethod;
06 importorg.springframework.web.bind.annotation.RequestParam;
07 importorg.springframework.web.bind.annotation.RestController;
08
09 import com.jcombat.bean.Employee;
10
11 @RestController
12 @RequestMapping(value = "/api/Employee")
13 public class EmployeeController {
14
15 @RequestMapping(value = "/{name}",
method = RequestMethod.GET)
16 public Employee process(
17 @PathVariable("name") String
name,
18 @RequestParam(value = "empId",
required = false, defaultValue
= "00000") final String id) {
19 Employee employee = newEmployee();
20 employee.setEmpId(id);
21 employee.setName(name);
22 return employee;
23 }
24 };

4. Running the application


To run the application, let’s start with requesting the access token from the authorization server –

http://localhost:8080/SecureRESTWithOAuth/oauth/token?
grant_type=password&client_id=fbApp&client_secret=fbApp&username=admin&password=123

01 {
02 "value":"a7718567-6e38-4be3-aa41-
382c90e042e0",
03 "expiration":1505631027817,
04 "tokenType":"bearer",
05 "refreshToken":{
06 "value":"7792b077-7ae0-427e-8170-
8b1440e5fefd",
07 "expiration":1508222907814
08 },
09 "scope":[
10
11 ],
12 "additionalInformation":{
13
14 },
15 "expiresIn":109,
16 "expired":false
17 }

Once the access token is generated, we are ready to pass it along with every subsequent requests for the protected
resources on the server.

http://localhost:8080/SecureRESTWithOAuth/api/Employee/abhimanyu?access_token=7792b077-7ae0-427e-8170-
8b1440e5fefd

https://www.javacodegeeks.com/2017/09/secure-rest-service-oauth2-tokens.html# 8/9
11/5/2018 Secure REST Service with OAuth2 Tokens | Java Code Geeks - 2018

https://www.javacodegeeks.com/2017/09/secure-rest-service-oauth2-tokens.html# 9/9

You might also like