├── .gitignore
├── README.md
├── _config.yml
├── nbactions.xml
├── pom.xml
└── src
└── main
├── java
└── com
│ └── github
│ └── oauth2
│ └── server
│ ├── Application.java
│ ├── AuthorizationServerConfig.java
│ └── JsonToUrlEncodedAuthenticationFilter.java
└── resources
└── config
└── application.yml
/.gitignore:
--------------------------------------------------------------------------------
1 | target/
2 | !.mvn/wrapper/maven-wrapper.jar
3 |
4 | ### STS ###
5 | .apt_generated
6 | .classpath
7 | .factorypath
8 | .project
9 | .settings
10 | .springBeans
11 |
12 | ### IntelliJ IDEA ###
13 | .idea
14 | *.iws
15 | *.iml
16 | *.ipr
17 |
18 | ### NetBeans ###
19 | nbproject/private/
20 | build/
21 | nbbuild/
22 | dist/
23 | nbdist/
24 | .nb-gradle/
25 |
26 | ### VS Code ###
27 | .vscode
28 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | Sample standalone OAuth2 authorization server for Spring Boot (Uses in-memory token store)
2 |
3 | The requesting method for token supports both ```json format``` and ```url-encoded format```
4 |
5 |
6 | The token validity is currently 60secs.
7 |
8 |
9 | Update any of the ```clienId```/```clientPassword```/```tokenValidity``` to however you want.
10 | ## Other implementations
11 | * Using [JDBC](https://github.com/aldwindelgado/spring-boot-oauth2-server/tree/jdbc) with default token
12 | * Using [JDBC with JWT](https://github.com/aldwindelgado/spring-boot-oauth2-server/tree/jwt) as the token
13 |
14 | ## Running
15 | ```shell
16 | mvn clean package spring-boot:run
17 | ```
18 |
19 | ## Request for a token
20 | Use any of the curl commands to request an access token.
21 |
22 | #### Using URL-Encoded Format
23 | ```
24 | curl -X POST -H "Authorization: Basic YWNjb3VudDpwYXNzd29yZA==" -H "Content-Type: application/x-www-form-urlencoded" -v localhost:8080/oauth/token?grant_type=client_credentials
25 | ```
26 | #### Using JSON Format
27 | ```
28 | curl -X POST -H "Authorization: Basic YWNjb3VudDpwYXNzd29yZA==" -H "Content-Type: application/json" -d '{ "grant_type": "client_credentials" }' -v localhost:8080/oauth/token
29 | ```
30 |
31 | ## Resource Server
32 | See [spring-boot-oauth2-client](https://github.com/aldwindelgado/spring-boot-oauth2-client) for running the oauth-client (resource server)
33 |
--------------------------------------------------------------------------------
/_config.yml:
--------------------------------------------------------------------------------
1 | theme: jekyll-theme-minimal
--------------------------------------------------------------------------------
/nbactions.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | run
5 |
6 | jar
7 |
8 |
9 | process-classes
10 | org.codehaus.mojo:exec-maven-plugin:1.2.1:exec
11 |
12 |
13 | -classpath %classpath com.github.oauth2.server.Application
14 | java
15 |
16 |
17 |
18 |
--------------------------------------------------------------------------------
/pom.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 | 4.0.0
4 | com.github
5 | spring-boot-oauth2-server
6 | 1.0.0
7 |
8 | spring-boot-oauth2-server
9 | Sample OAuth2 authorization server using Spring Boot
10 |
11 |
12 | org.springframework.boot
13 | spring-boot-starter-parent
14 | 1.5.6.RELEASE
15 |
16 |
17 |
18 | UTF-8
19 | UTF-8
20 | 1.8
21 |
22 |
23 |
24 |
25 | org.springframework.boot
26 | spring-boot-starter-web
27 |
28 |
29 | org.springframework.boot
30 | spring-boot-starter
31 |
32 |
33 | org.springframework.boot
34 | spring-boot-starter-logging
35 |
36 |
37 |
38 |
39 | org.springframework.boot
40 | spring-boot-starter-log4j2
41 |
42 |
46 |
47 | org.springframework.security.oauth
48 | spring-security-oauth2
49 |
50 |
54 |
55 | org.springframework.boot
56 | spring-boot-starter-actuator
57 |
58 |
59 | org.springframework.boot
60 | spring-boot-starter-security
61 |
62 |
68 |
69 | org.apache.commons
70 | commons-lang3
71 | 3.1
72 | jar
73 |
74 |
75 | javax.ws.rs
76 | javax.ws.rs-api
77 | 2.0
78 | jar
79 |
80 |
81 | org.json
82 | json
83 | 20160810
84 | jar
85 |
86 |
87 | org.apache.commons
88 | commons-exec
89 | 1.3
90 | jar
91 |
92 |
93 | com.google.guava
94 | guava
95 | 23.0
96 | jar
97 |
98 |
99 |
100 |
101 |
102 |
103 | org.springframework.boot
104 | spring-boot-maven-plugin
105 |
106 |
107 |
108 |
--------------------------------------------------------------------------------
/src/main/java/com/github/oauth2/server/Application.java:
--------------------------------------------------------------------------------
1 | /*
2 | * To change this license header, choose License Headers in Project Properties.
3 | * To change this template file, choose Tools | Templates
4 | * and open the template in the editor.
5 | */
6 | package com.github.oauth2.server;
7 |
8 | import org.springframework.boot.SpringApplication;
9 | import org.springframework.boot.autoconfigure.SpringBootApplication;
10 | import org.springframework.http.HttpStatus;
11 | import org.springframework.http.MediaType;
12 | import org.springframework.http.ResponseEntity;
13 | import org.springframework.web.bind.annotation.RequestMapping;
14 |
15 | /**
16 | *
17 | * @author Aldwin Delgado
18 | */
19 | @SpringBootApplication
20 | public class Application {
21 |
22 | public static void main(String[] args) {
23 | SpringApplication.run(Application.class, args);
24 | }
25 |
26 | @RequestMapping(
27 | value = "/",
28 | produces = MediaType.APPLICATION_JSON_VALUE
29 | )
30 | public ResponseEntity index() {
31 | return new ResponseEntity<>("{\"message\":\"Home!\"}", HttpStatus.OK);
32 | }
33 | }
34 |
--------------------------------------------------------------------------------
/src/main/java/com/github/oauth2/server/AuthorizationServerConfig.java:
--------------------------------------------------------------------------------
1 | /*
2 | * To change this license header, choose License Headers in Project Properties.
3 | * To change this template file, choose Tools | Templates
4 | * and open the template in the editor.
5 | */
6 | package com.github.oauth2.server;
7 |
8 | import org.springframework.beans.factory.annotation.Autowired;
9 | import org.springframework.context.annotation.Configuration;
10 | import org.springframework.security.authentication.AuthenticationManager;
11 | import org.springframework.security.oauth2.config.annotation.configurers.ClientDetailsServiceConfigurer;
12 | import org.springframework.security.oauth2.config.annotation.web.configuration.AuthorizationServerConfigurerAdapter;
13 | import org.springframework.security.oauth2.config.annotation.web.configuration.EnableAuthorizationServer;
14 | import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerEndpointsConfigurer;
15 | import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerSecurityConfigurer;
16 | import org.springframework.security.oauth2.provider.token.TokenStore;
17 |
18 | /**
19 | *
20 | * @author Aldwin Delgado
21 | */
22 | @Configuration
23 | @EnableAuthorizationServer
24 | public class AuthorizationServerConfig extends AuthorizationServerConfigurerAdapter {
25 |
26 | private TokenStore tokenStore;
27 |
28 | @Autowired
29 | private AuthenticationManager authenticationManager;
30 |
31 | @Override
32 | public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
33 | endpoints
34 | .authenticationManager(authenticationManager)
35 | .approvalStoreDisabled()
36 | .tokenStore(tokenStore);
37 | }
38 |
39 | @Override
40 | public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
41 | clients
42 | .inMemory()
43 | .withClient("account")
44 | .secret("password")
45 | .authorizedGrantTypes("client_credentials", "password")
46 | .scopes("read", "write")
47 | .accessTokenValiditySeconds(60)
48 | .resourceIds("sample-oauth");
49 | }
50 |
51 | @Override
52 | public void configure(AuthorizationServerSecurityConfigurer security) throws Exception {
53 | security
54 | .checkTokenAccess("isAuthenticated()")
55 | .allowFormAuthenticationForClients();
56 | }
57 |
58 | }
59 |
--------------------------------------------------------------------------------
/src/main/java/com/github/oauth2/server/JsonToUrlEncodedAuthenticationFilter.java:
--------------------------------------------------------------------------------
1 | /*
2 | * To change this license header, choose License Headers in Project Properties.
3 | * To change this template file, choose Tools | Templates
4 | * and open the template in the editor.
5 | */
6 | package com.github.oauth2.server;
7 |
8 | import com.fasterxml.jackson.databind.ObjectMapper;
9 | import com.google.common.io.ByteStreams;
10 | import java.io.IOException;
11 | import java.util.Enumeration;
12 | import java.util.Map;
13 | import java.util.Objects;
14 | import java.util.stream.Collectors;
15 | import javax.servlet.FilterChain;
16 | import javax.servlet.ServletException;
17 | import javax.servlet.http.HttpServletRequest;
18 | import javax.servlet.http.HttpServletRequestWrapper;
19 | import javax.servlet.http.HttpServletResponse;
20 | import org.springframework.security.web.savedrequest.Enumerator;
21 | import org.springframework.stereotype.Component;
22 | import org.springframework.web.filter.OncePerRequestFilter;
23 |
24 | /**
25 | *
26 | * @author Aldwin Delgado
27 | */
28 | @Component
29 | public class JsonToUrlEncodedAuthenticationFilter extends OncePerRequestFilter {
30 |
31 | /**
32 | * @param request
33 | * @param response
34 | * @param filterChain
35 | * @throws javax.servlet.ServletException
36 | * @throws java.io.IOException
37 | *
38 | */
39 | @Override
40 | protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException {
41 |
42 | if (Objects.equals(request.getServletPath(), "/oauth/token") && Objects.equals(request.getContentType(), "application/json")) {
43 |
44 | byte[] json = ByteStreams.toByteArray(request.getInputStream());
45 |
46 | Map jsonMap = new ObjectMapper().readValue(json, Map.class);
47 | Map parameters
48 | = jsonMap.entrySet().stream()
49 | .collect(Collectors.toMap(
50 | Map.Entry::getKey,
51 | e -> new String[]{e.getValue()})
52 | );
53 |
54 | HttpServletRequest requestWrapper = new RequestWrapper(request, parameters);
55 | filterChain.doFilter(requestWrapper, response);
56 | } else {
57 | filterChain.doFilter(request, response);
58 | }
59 | }
60 |
61 | private class RequestWrapper extends HttpServletRequestWrapper {
62 |
63 | private final Map params;
64 |
65 | RequestWrapper(HttpServletRequest request, Map params) {
66 | super(request);
67 | this.params = params;
68 | }
69 |
70 | @Override
71 | public String getParameter(String name) {
72 | if (this.params.containsKey(name)) {
73 | return this.params.get(name)[0];
74 | }
75 | return "";
76 | }
77 |
78 | @Override
79 | public Map getParameterMap() {
80 | return this.params;
81 | }
82 |
83 | @Override
84 | public Enumeration getParameterNames() {
85 | return new Enumerator<>(params.keySet());
86 | }
87 |
88 | @Override
89 | public String[] getParameterValues(String name) {
90 | return params.get(name);
91 | }
92 | }
93 |
94 | }
95 |
--------------------------------------------------------------------------------
/src/main/resources/config/application.yml:
--------------------------------------------------------------------------------
1 | spring:
2 | application:
3 | name: spring-boot-oauth2-server
4 | mvc:
5 | favicon:
6 | enabled: false
7 | throw-exception-if-no-handler-found: true
8 | main:
9 | banner-mode: 'off'
10 | security:
11 | oauth2:
12 | resource:
13 | filter-order: 3
14 | client:
15 | authenticationScheme: header
16 | logging:
17 | level:
18 | # org.springframework.security: DEBUG
19 |
20 | server:
21 | port: 8080
22 | error:
23 | whitelabel:
24 | enabled: false
--------------------------------------------------------------------------------