| Size: 3774 Comment:  | Size: 27120 Comment:  | 
| Deletions are marked like this. | Additions are marked like this. | 
| Line 19: | Line 19: | 
| The example in the tutorial doesn't run out of the box. It doesn't explain how to load the private key (PEM). Also it relies on Java 8. If we try to use the example with Java 11 it doesn't work due to issues with xml bind. | |
| Line 36: | Line 38: | 
| │ │ ├── AnonymousController.java | |
| Line 55: | Line 58: | 
| {{{ | {{{#!highlight bash docker run -d -p 8080:8080 --name test test_image | 
| Line 59: | Line 63: | 
| {{{ | {{{#!highlight bash FROM openjdk:8-alpine RUN apk add maven RUN mkdir -p /usr/src/tutpoint-jwt COPY . /usr/src/tutpoint-jwt WORKDIR /usr/src/tutpoint-jwt RUN mvn clean install CMD ["java","-jar","target/websecurityapp-0.0.1-SNAPSHOT.jar"] | 
| Line 63: | Line 74: | 
| {{{ | {{{#!highlight java package com.tutorialspoint.websecurityapp; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.security.authentication.AuthenticationManager; import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder; import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.builders.WebSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter; import org.springframework.security.config.http.SessionCreationPolicy; import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; import org.springframework.security.crypto.password.PasswordEncoder; @Configuration @EnableWebSecurity @EnableGlobalMethodSecurity(prePostEnabled = true) public class SecurityConfiguration extends WebSecurityConfigurerAdapter { @Autowired private CustomDetailsService customDetailsService; @Bean public PasswordEncoder encoder() { return new BCryptPasswordEncoder(); } @Override @Autowired protected void configure(AuthenticationManagerBuilder auth) throws Exception { auth.userDetailsService(customDetailsService).passwordEncoder(encoder()); } @Override protected void configure(HttpSecurity http) throws Exception { http.authorizeRequests().anyRequest().authenticated().and().sessionManagement() .sessionCreationPolicy(SessionCreationPolicy.NEVER); } @Override public void configure(WebSecurity web) throws Exception { web.ignoring().antMatchers("/anonymous/**", "/resources/**", "/static/**"); } @Override @Bean public AuthenticationManager authenticationManagerBean() throws Exception { return super.authenticationManagerBean(); } } | 
| Line 67: | Line 132: | 
| {{{ | {{{#!highlight java package com.tutorialspoint.websecurityapp; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.security.authentication.AuthenticationManager; import org.springframework.security.oauth2.config.annotation.configurers.ClientDetailsServiceConfigurer; import org.springframework.security.oauth2.config.annotation.web.configuration.AuthorizationServerConfigurerAdapter; import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerEndpointsConfigurer; import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerSecurityConfigurer; import org.springframework.security.oauth2.provider.token.store.JwtAccessTokenConverter; import org.springframework.security.oauth2.provider.token.store.JwtTokenStore; import java.io.FileReader; import java.io.BufferedReader; @Configuration public class OAuth2Config extends AuthorizationServerConfigurerAdapter { private String clientid = "tutorialspoint"; private String clientSecret = "my-secret-key"; @Autowired @Qualifier("authenticationManagerBean") private AuthenticationManager authenticationManager; private String getFileContent(String filename) { String ret = ""; BufferedReader bufReader = null; try { bufReader = new BufferedReader(new FileReader(filename)); String line = ""; while (line != null) { line = bufReader.readLine(); if (line != null) { ret += line; } } bufReader.close(); } catch (Exception ex) { } finally { } return ret; } @Bean public JwtAccessTokenConverter tokenEnhancer() { JwtAccessTokenConverter converter = new JwtAccessTokenConverter(); String pemData = getFileContent("jwt.pem"); converter.setSigningKey(pemData); converter.setVerifierKey(pemData); return converter; } @Bean public JwtTokenStore tokenStore() { return new JwtTokenStore(tokenEnhancer()); } @Override public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception { endpoints.authenticationManager(authenticationManager).tokenStore(tokenStore()) .accessTokenConverter(tokenEnhancer()); } @Override public void configure(AuthorizationServerSecurityConfigurer security) throws Exception { security.tokenKeyAccess("permitAll()").checkTokenAccess("isAuthenticated()"); } @Override public void configure(ClientDetailsServiceConfigurer clients) throws Exception { clients.inMemory().withClient(clientid).secret(clientSecret).scopes("read", "write") .authorizedGrantTypes("password", "refresh_token").accessTokenValiditySeconds(20000) .refreshTokenValiditySeconds(20000); } } | 
| Line 71: | Line 218: | 
| {{{ | {{{#!highlight java package com.tutorialspoint.websecurityapp; import org.springframework.security.core.userdetails.User; public class CustomUser extends User { private static final long serialVersionUID = 1L; public CustomUser(UserEntity user) { super(user.getUsername(), user.getPassword(), user.getGrantedAuthoritiesList()); } } | 
| Line 75: | Line 232: | 
| {{{ | {{{#!highlight java package com.tutorialspoint.websecurityapp; import java.util.ArrayList; import java.util.Collection; import org.springframework.security.core.GrantedAuthority; public class UserEntity { private String username; private String password; private String role; private Collection<GrantedAuthority> grantedAuthoritiesList = new ArrayList<>(); public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } public Collection<GrantedAuthority> getGrantedAuthoritiesList() { return grantedAuthoritiesList; } public void setGrantedAuthoritiesList(Collection<GrantedAuthority> grantedAuthoritiesList) { this.grantedAuthoritiesList = grantedAuthoritiesList; } public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public String getRole() { return role; } public void setRole(String role) { this.role = role; } } }}} === src/main/java/com/tutorialspoint/websecurityapp/AnonymousController.java === {{{ package com.tutorialspoint.websecurityapp; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.ResponseBody; @Controller @RequestMapping("/anonymous") public class AnonymousController { @ResponseBody @RequestMapping(value = "/dummy", produces = "application/json") // http://localhost:8080/anonymous/dummy public String getDummy() { return "dummy"; } } | 
| Line 79: | Line 303: | 
| {{{ | {{{#!highlight java package com.tutorialspoint.websecurityapp; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.security.access.prepost.PreAuthorize; import org.springframework.security.oauth2.config.annotation.web.configuration.EnableAuthorizationServer; import org.springframework.security.oauth2.config.annotation.web.configuration.EnableResourceServer; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; @SpringBootApplication @EnableAuthorizationServer @EnableResourceServer @RestController public class WebsecurityappApplication { public static void main(String[] args) { SpringApplication.run(WebsecurityappApplication.class, args); } @PreAuthorize("hasRole('ROLE_ADMIN')") @RequestMapping(value = "/products") public String getProductName() { return "Honey"; } @PreAuthorize("hasRole('ROLE_USER')") @RequestMapping(value = "/productsuser") public String getProductNameUsers() { return "HoneyUser"; } } | 
| Line 83: | Line 339: | 
| {{{ | {{{#!highlight java package com.tutorialspoint.websecurityapp; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.security.core.userdetails.UserDetailsService; import org.springframework.security.core.userdetails.UsernameNotFoundException; import org.springframework.stereotype.Service; @Service public class CustomDetailsService implements UserDetailsService { @Autowired OAuthDao oauthDao; @Override public CustomUser loadUserByUsername(final String username) throws UsernameNotFoundException { UserEntity userEntity = null; try { userEntity = oauthDao.getUserDetails(username); CustomUser customUser = new CustomUser(userEntity); return customUser; } catch (Exception e) { e.printStackTrace(); throw new UsernameNotFoundException("User " + username + " was not found in the database"); } } } | 
| Line 87: | Line 368: | 
| {{{ | {{{#!highlight java package com.tutorialspoint.websecurityapp; import java.sql.ResultSet; import java.util.ArrayList; import java.util.Collection; import java.util.List; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.jdbc.core.JdbcTemplate; import org.springframework.security.core.GrantedAuthority; import org.springframework.security.core.authority.SimpleGrantedAuthority; import org.springframework.stereotype.Repository; @Repository public class OAuthDao { @Autowired private JdbcTemplate jdbcTemplate; public UserEntity getUserDetails(String username) { String userSQLQuery = "SELECT * FROM USERS WHERE USERNAME=?"; List<UserEntity> list = jdbcTemplate.query(userSQLQuery, new String[] { username }, (ResultSet resultSet, int rowNum) -> { UserEntity user = new UserEntity(); user.setUsername(username); user.setPassword(resultSet.getString("PASSWORD")); user.setRole(resultSet.getString("ROLE")); return user; }); if (list.size() > 0) { Collection<GrantedAuthority> grantedAuthoritiesList = new ArrayList<>(); UserEntity user = list.get(0); GrantedAuthority grantedAuthority = new SimpleGrantedAuthority(user.getRole()); grantedAuthoritiesList.add(grantedAuthority); user.setGrantedAuthoritiesList(grantedAuthoritiesList); return user; } return null; } } | 
| Line 91: | Line 415: | 
| {{{ | {{{#!highlight sql CREATE TABLE USERS (ID INT PRIMARY KEY, USERNAME VARCHAR(45), PASSWORD VARCHAR(60), ROLE VARCHAR(60) ); | 
| Line 96: | Line 421: | 
| security.oauth2.resource.filter-order=3 logging.file=/tmp/testout.log | |
| Line 99: | Line 426: | 
| {{{ | {{{#!highlight sql INSERT INTO USERS (ID, USERNAME,PASSWORD, ROLE) VALUES ( 1, 'tutorialspoint@gmail.com','$2a$08$fL7u5xcvsZl78su29x1ti.dxI.9rYO8t0q5wk2ROJ.1cdR53bmaVG','ROLE_ADMIN'); INSERT INTO USERS (ID, USERNAME,PASSWORD, ROLE) VALUES ( 2, 'myemail@gmail.com','$2a$08$fL7u5xcvsZl78su29x1ti.dxI.9rYO8t0q5wk2ROJ.1cdR53bmaVG','ROLE_USER'); | 
| Line 103: | Line 435: | 
| {{{ | {{{#!highlight bash docker build -t test_image . | 
| Line 107: | Line 440: | 
| {{{ | {{{#!highlight xml <?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/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.tutorialspoint</groupId> <artifactId>websecurityapp</artifactId> <version>0.0.1-SNAPSHOT</version> <packaging>jar</packaging> <name>websecurityapp</name> <description>Demo project for Spring Boot</description> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>1.5.9.RELEASE</version> <relativePath /> <!-- lookup parent from repository --> </parent> <properties> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding> <java.version>1.8</java.version> </properties> <dependencies> <!-- Caused by: java.lang.ClassNotFoundException: javax.xml.bind.JAXBException --> <!-- API, java.xml.bind module --> <dependency> <groupId>jakarta.xml.bind</groupId> <artifactId>jakarta.xml.bind-api</artifactId> <version>2.3.2</version> </dependency> <!-- Runtime, com.sun.xml.bind module --> <dependency> <groupId>org.glassfish.jaxb</groupId> <artifactId>jaxb-runtime</artifactId> <version>2.3.2</version> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-jdbc</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-security</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.security.oauth</groupId> <artifactId>spring-security-oauth2</artifactId> </dependency> <dependency> <groupId>org.springframework.security</groupId> <artifactId>spring-security-jwt</artifactId> </dependency> <dependency> <groupId>com.h2database</groupId> <artifactId>h2</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.springframework.security</groupId> <artifactId>spring-security-test</artifactId> <scope>test</scope> </dependency> </dependencies> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build> </project> | 
| Line 111: | Line 539: | 
| {{{ | {{{#!highlight bash ACCESS_TOKEN=$(curl -X POST --url http://localhost:8080/oauth/token --user tutorialspoint:my-secret-key --data 'grant_type=password&username=myemail@gmail.com&password=password' | jq -r '.access_token') ACCESS_TOKEN_ADMIN=$(curl -X POST --url http://localhost:8080/oauth/token --user tutorialspoint:my-secret-key --data 'grant_type=password&username=tutorialspoint@gmail.com&password=password' | jq -r '.access_token') #echo $ACCESS_TOKEN curl -X GET http://localhost:8080/productsuser --header "Authorization: Bearer $ACCESS_TOKEN" curl -X GET http://localhost:8080/products --header "Authorization: Bearer $ACCESS_TOKEN_ADMIN" curl -X GET http://localhost:8080/anonymous/dummy curl -X GET http://localhost:8080/products --header "Authorization: Bearer $ACCESS_TOKEN" curl -X GET http://localhost:8080/productsuser --header "Authorization: Bearer $ACCESS_TOKEN_ADMIN" | 
| Line 115: | Line 552: | 
| {{{ | {{{#!highlight bash docker exec -it test /bin/sh | 
| Line 119: | Line 557: | 
| {{{ }}} | {{{#!highlight bash docker stop test docker rm test }}} == SpringBoot 2.2.8 (resource server) + keycloak 10.0.2 (authentication server) + Java 11 == {{{ wget https://downloads.jboss.org/keycloak/10.0.2/keycloak-10.0.2.zip unzip -t keycloak-10.0.2.zip cd ~/keycloak-10.0.2/bin sh standalone.sh http://localhost:8080/auth admin admin admin create http://localhost:8080/auth/admin/master/console/#/realms/master Master, add realm, MyRealm , create Users, add user, myuser select user, credentials, mypwd mypwd, temporary off Add role USER to MyRealm Make user myuser have role USER signout http://localhost:8080/auth/realms/MyRealm/account/ realm: MyRealm user pwd: myuser mypwd client id: curl_confidential protocol: openid-connect Curl_confidential settings: access-type confidential valid redirect url http://localhost:8080 tab credentials: regenerate secret 6dfe5f84-d115-4d3e-8a56-a0fcf5b2f13e curl -d 'client_id=curl_confidential' -d 'client_secret=6dfe5f84-d115-4d3e-8a56-a0fcf5b2f13e' -d 'username=myuser' -d 'password=mypwd' -d 'grant_type=password' 'http://localhost:8080/auth/realms/MyRealm/protocol/openid-connect/token' }}} {{{ . ├── pom.xml └── src └── main ├── java │ └── com │ └── example │ └── demo │ └── DemoApplication.java └── resources └── application.properties }}} === pom.xml === {{{ <?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 https://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>2.2.8.RELEASE</version> <relativePath/> <!-- lookup parent from repository --> </parent> <groupId>com.example</groupId> <artifactId>demo</artifactId> <version>0.0.1-SNAPSHOT</version> <name>demo</name> <description>Demo project for Spring Boot</description> <properties> <java.version>11</java.version> </properties> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-oauth2-resource-server</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-security</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> </dependencies> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build> </project> }}} === src/main/resources/application.properties === {{{ server.port=8181 spring.security.oauth2.resourceserver.jwt.issuer-uri=http://localhost:8080/auth/realms/MyRealm #logging.level.root=DEBUG logging.level.root=INFO logging.file=/tmp/testout.log }}} === src/main/java/com/example/demo/DemoApplication.java === {{{#!highlight java package com.example.demo; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RestController; import org.springframework.security.core.Authentication; import org.springframework.security.core.GrantedAuthority; import org.springframework.security.oauth2.jwt.Jwt; @RestController @SpringBootApplication public class DemoApplication { public static void main(String[] args) { SpringApplication.run(DemoApplication.class, args); } @GetMapping("/otherhello") public String otherHello(){ return "other hello"; } @GetMapping("/hello") public String hello(Authentication authentication) { String s=""; for(int i=0; i<authentication.getAuthorities().size();i++){ GrantedAuthority ga = (GrantedAuthority) authentication.getAuthorities().toArray()[i]; s += ga.getAuthority() + " "; } Jwt jwt = (Jwt) authentication.getCredentials(); Object[] keys = jwt.getClaims().keySet().toArray(); String allkeys = ""; for(int j=0; j< keys.length ;j++){ allkeys = allkeys + " " + (String)keys[j] + ":" + jwt.getClaims().get( keys[j] ).toString()+ " "; } return "I am authenticated with user " + authentication.getName() + " " + s + " " + authentication.getDetails().toString() + " " + allkeys; } } }}} === src/main/java/com/example/demo/SecurityConfiguration.java === {{{#!highlight java package com.example.demo; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.security.authentication.AuthenticationManager; import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder; import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.builders.WebSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter; import org.springframework.security.config.http.SessionCreationPolicy; import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; import org.springframework.security.crypto.password.PasswordEncoder; @Configuration @EnableWebSecurity public class SecurityConfiguration extends WebSecurityConfigurerAdapter { @Override protected void configure(HttpSecurity http) throws Exception { http.oauth2ResourceServer().jwt(); } @Override public void configure(WebSecurity web) throws Exception { web.ignoring().antMatchers("/otherhello**").antMatchers("/static**"); } } }}} === src/main/webapp/static/test2.txt === {{{ test2 }}} === Invoke endpoint on resource server with access token from keycloak === {{{ curl http://localhost:8181/hello -vvv TOKEN=$(curl -d 'client_id=curl_confidential' -d 'client_secret=6dfe5f84-d115-4d3e-8a56-a0fcf5b2f13e' -d 'username=myuser' -d 'password=mypwd' -d 'grant_type=password' 'http://localhost:8080/auth/realms/MyRealm/protocol/openid-connect/token' | jq -r '.access_token') curl -X GET http://localhost:8181/hello --header "Authorization: Bearer $TOKEN" I am authenticated with user d7192f29-ee2f-4079-95f9-a75df61f3973 SCOPE_profile SCOPE_email org.springframework.security.web.authentication.WebAuthenticationDetails@b364: RemoteIpAddress: 0:0:0:0:0:0:0:1; SessionId: null sub:d7192f29-ee2f-4079-95f9-a75df61f3973 resource_access:{"account":{"roles":["manage-account","manage-account-links","view-profile"]}} email_verified:false iss:http://localhost:8080/auth/realms/MyRealm typ:Bearer preferred_username:myuser aud:[account] acr:1 realm_access:{"roles":["offline_access","uma_authorization","USER"]} azp:curl_confidential scope:profile email exp:2020-06-18T23:01:09Z session_state:a3cc9c25-ae55-492f-be5a-28aafd3a6d3f iat:2020-06-18T22:56:09Z jti:bc4a4a6e-5da5-434b-9a77-cb0a88c64c4c curl -X GET http://localhost:8181/otherhello # other hello curl -X GET http://localhost:8181/static/test2.txt -v # test2 }}} | 
jwt (JSON Web Token)
JSON Web Token
- https://www.devglan.com/spring-security/spring-boot-jwt-auth 
- https://www.tutorialspoint.com/spring_boot/spring_boot_oauth2_with_jwt.htm 
Overview
In authentication, when the user successfully logs in using their credentials, a JSON Web Token will be returned and must be saved locally (typically in local or session storage, but cookies can also be used), instead of the traditional approach of creating a session in the server and returning a cookie.
The tokens are designed to be compact,[2] URL-safe,[3] and usable especially in a web-browser single-sign-on (SSO) context. JWT claims can be typically used to pass identity of authenticated users between an identity provider and a service provider, or any other type of claims as required by business processes.
This is a stateless authentication mechanism as the user state is never saved in server memory. The server's protected routes will check for a valid JWT in the Authorization header, and if it is present, the user will be allowed to access protected resources. As JWTs are self-contained, all the necessary information is there, reducing the need to query the database multiple times.
Adapted tutorials point Spring boot + JWT example
The example in the tutorial doesn't run out of the box. It doesn't explain how to load the private key (PEM). Also it relies on Java 8. If we try to use the example with Java 11 it doesn't work due to issues with xml bind.
Structure
. ├── build_image.sh ├── connect_container.sh ├── Dockerfile ├── get_token.sh ├── jwt.pem ├── pom.xml ├── run_container.sh ├── src │ └── main │ ├── java │ │ └── com │ │ └── tutorialspoint │ │ └── websecurityapp │ │ ├── AnonymousController.java │ │ ├── CustomDetailsService.java │ │ ├── CustomUser.java │ │ ├── OAuth2Config.java │ │ ├── OAuthDao.java │ │ ├── SecurityConfiguration.java │ │ ├── UserEntity.java │ │ └── WebsecurityappApplication.java │ └── resources │ ├── application.properties │ ├── data.sql │ └── schema.sql └── stop_container.sh
- mkdir -p src/main/java/com/tutorialspoint/websecurityapp/
- mkdir src/main/resources/
- openssl genrsa -out jwt.pem 2048 # generate private key
run_container.sh
   1 docker run -d -p 8080:8080 --name test test_image
Dockerfile
src/main/java/com/tutorialspoint/websecurityapp/SecurityConfiguration.java
   1 package com.tutorialspoint.websecurityapp;
   2 
   3 import org.springframework.beans.factory.annotation.Autowired;
   4 import org.springframework.context.annotation.Bean;
   5 import org.springframework.context.annotation.Configuration;
   6 
   7 import org.springframework.security.authentication.AuthenticationManager;
   8 import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
   9 import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
  10 import org.springframework.security.config.annotation.web.builders.HttpSecurity;
  11 import org.springframework.security.config.annotation.web.builders.WebSecurity;
  12 import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
  13 import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
  14 import org.springframework.security.config.http.SessionCreationPolicy;
  15 import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
  16 import org.springframework.security.crypto.password.PasswordEncoder;
  17 
  18 @Configuration
  19 @EnableWebSecurity
  20 @EnableGlobalMethodSecurity(prePostEnabled = true)
  21 public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
  22         @Autowired
  23         private CustomDetailsService customDetailsService;
  24 
  25         @Bean
  26         public PasswordEncoder encoder() {
  27                 return new BCryptPasswordEncoder();
  28         }
  29 
  30         @Override
  31         @Autowired
  32         protected void configure(AuthenticationManagerBuilder auth) throws Exception {
  33                 auth.userDetailsService(customDetailsService).passwordEncoder(encoder());
  34         }
  35 
  36         @Override
  37         protected void configure(HttpSecurity http) throws Exception {
  38                 http.authorizeRequests().anyRequest().authenticated().and().sessionManagement()
  39                                 .sessionCreationPolicy(SessionCreationPolicy.NEVER);
  40 
  41         }
  42 
  43         @Override
  44         public void configure(WebSecurity web) throws Exception {
  45                 web.ignoring().antMatchers("/anonymous/**", "/resources/**", "/static/**");
  46         }
  47 
  48         @Override
  49         @Bean
  50         public AuthenticationManager authenticationManagerBean() throws Exception {
  51                 return super.authenticationManagerBean();
  52         }
  53 }
src/main/java/com/tutorialspoint/websecurityapp/OAuth2Config.java
   1 package com.tutorialspoint.websecurityapp;
   2 
   3 import org.springframework.beans.factory.annotation.Autowired;
   4 import org.springframework.beans.factory.annotation.Qualifier;
   5 import org.springframework.context.annotation.Bean;
   6 import org.springframework.context.annotation.Configuration;
   7 
   8 import org.springframework.security.authentication.AuthenticationManager;
   9 import org.springframework.security.oauth2.config.annotation.configurers.ClientDetailsServiceConfigurer;
  10 import org.springframework.security.oauth2.config.annotation.web.configuration.AuthorizationServerConfigurerAdapter;
  11 import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerEndpointsConfigurer;
  12 import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerSecurityConfigurer;
  13 import org.springframework.security.oauth2.provider.token.store.JwtAccessTokenConverter;
  14 import org.springframework.security.oauth2.provider.token.store.JwtTokenStore;
  15 
  16 import java.io.FileReader;
  17 import java.io.BufferedReader;
  18 
  19 @Configuration
  20 public class OAuth2Config extends AuthorizationServerConfigurerAdapter {
  21         private String clientid = "tutorialspoint";
  22         private String clientSecret = "my-secret-key";
  23 
  24         @Autowired
  25         @Qualifier("authenticationManagerBean")
  26         private AuthenticationManager authenticationManager;
  27 
  28         private String getFileContent(String filename) {
  29                 String ret = "";
  30                 BufferedReader bufReader = null;
  31                 try {
  32                         bufReader = new BufferedReader(new FileReader(filename));
  33                         String line = "";
  34                         while (line != null) {
  35                                 line = bufReader.readLine();
  36                                 if (line != null) {
  37                                         ret += line;
  38                                 }
  39                         }
  40                         bufReader.close();
  41                 } catch (Exception ex) {
  42                 } finally {
  43                 }
  44 
  45                 return ret;
  46         }
  47 
  48         @Bean
  49         public JwtAccessTokenConverter tokenEnhancer() {
  50 
  51                 JwtAccessTokenConverter converter = new JwtAccessTokenConverter();
  52                 String pemData = getFileContent("jwt.pem");
  53                 converter.setSigningKey(pemData);
  54                 converter.setVerifierKey(pemData);
  55                 return converter;
  56         }
  57 
  58         @Bean
  59         public JwtTokenStore tokenStore() {
  60                 return new JwtTokenStore(tokenEnhancer());
  61         }
  62 
  63         @Override
  64         public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
  65                 endpoints.authenticationManager(authenticationManager).tokenStore(tokenStore())
  66                                 .accessTokenConverter(tokenEnhancer());
  67         }
  68 
  69         @Override
  70         public void configure(AuthorizationServerSecurityConfigurer security) throws Exception {
  71                 security.tokenKeyAccess("permitAll()").checkTokenAccess("isAuthenticated()");
  72         }
  73 
  74         @Override
  75         public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
  76                 clients.inMemory().withClient(clientid).secret(clientSecret).scopes("read", "write")
  77                                 .authorizedGrantTypes("password", "refresh_token").accessTokenValiditySeconds(20000)
  78                                 .refreshTokenValiditySeconds(20000);
  79 
  80         }
  81 }
src/main/java/com/tutorialspoint/websecurityapp/CustomUser.java
   1 package com.tutorialspoint.websecurityapp;
   2 
   3 import org.springframework.security.core.userdetails.User;
   4 
   5 public class CustomUser extends User {
   6    private static final long serialVersionUID = 1L;
   7    public CustomUser(UserEntity user) {
   8       super(user.getUsername(), user.getPassword(), user.getGrantedAuthoritiesList());
   9    }
  10 } 
src/main/java/com/tutorialspoint/websecurityapp/UserEntity.java
   1 package com.tutorialspoint.websecurityapp;
   2 
   3 import java.util.ArrayList;
   4 import java.util.Collection;
   5 import org.springframework.security.core.GrantedAuthority;
   6 
   7 public class UserEntity {
   8         private String username;
   9         private String password;
  10         private String role;
  11         private Collection<GrantedAuthority> grantedAuthoritiesList = new ArrayList<>();
  12 
  13         public String getPassword() {
  14                 return password;
  15         }
  16 
  17         public void setPassword(String password) {
  18                 this.password = password;
  19         }
  20 
  21         public Collection<GrantedAuthority> getGrantedAuthoritiesList() {
  22                 return grantedAuthoritiesList;
  23         }
  24 
  25         public void setGrantedAuthoritiesList(Collection<GrantedAuthority> grantedAuthoritiesList) {
  26                 this.grantedAuthoritiesList = grantedAuthoritiesList;
  27         }
  28 
  29         public String getUsername() {
  30                 return username;
  31         }
  32 
  33         public void setUsername(String username) {
  34                 this.username = username;
  35         }
  36 
  37         public String getRole() {
  38                 return role;
  39         }
  40 
  41         public void setRole(String role) {
  42                 this.role = role;
  43         }
  44 
  45 }
src/main/java/com/tutorialspoint/websecurityapp/AnonymousController.java
package com.tutorialspoint.websecurityapp;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
@Controller
@RequestMapping("/anonymous")
public class AnonymousController {
        @ResponseBody
        @RequestMapping(value = "/dummy", produces = "application/json")
        // http://localhost:8080/anonymous/dummy
        public String getDummy() {
                return "dummy";
        }
}
src/main/java/com/tutorialspoint/websecurityapp/WebsecurityappApplication.java
   1 package com.tutorialspoint.websecurityapp;
   2 
   3 import org.springframework.boot.SpringApplication;
   4 import org.springframework.boot.autoconfigure.SpringBootApplication;
   5 import org.springframework.security.access.prepost.PreAuthorize;
   6 import org.springframework.security.oauth2.config.annotation.web.configuration.EnableAuthorizationServer;
   7 import org.springframework.security.oauth2.config.annotation.web.configuration.EnableResourceServer;
   8 import org.springframework.web.bind.annotation.RequestMapping;
   9 import org.springframework.web.bind.annotation.RestController;
  10 
  11 @SpringBootApplication
  12 @EnableAuthorizationServer
  13 @EnableResourceServer
  14 @RestController
  15 public class WebsecurityappApplication {
  16         public static void main(String[] args) {
  17                 SpringApplication.run(WebsecurityappApplication.class, args);
  18         }
  19 
  20         @PreAuthorize("hasRole('ROLE_ADMIN')")
  21         @RequestMapping(value = "/products")
  22         public String getProductName() {
  23                 return "Honey";
  24         }
  25 
  26         @PreAuthorize("hasRole('ROLE_USER')")
  27         @RequestMapping(value = "/productsuser")
  28         public String getProductNameUsers() {
  29                 return "HoneyUser";
  30         }
  31 
  32 }
src/main/java/com/tutorialspoint/websecurityapp/CustomDetailsService.java
   1 package com.tutorialspoint.websecurityapp;
   2 
   3 import org.springframework.beans.factory.annotation.Autowired;
   4 import org.springframework.security.core.userdetails.UserDetailsService;
   5 import org.springframework.security.core.userdetails.UsernameNotFoundException;
   6 import org.springframework.stereotype.Service;
   7 
   8 @Service
   9 public class CustomDetailsService implements UserDetailsService {
  10    @Autowired
  11    OAuthDao oauthDao;
  12 
  13    @Override
  14    public CustomUser loadUserByUsername(final String username) throws UsernameNotFoundException {
  15       UserEntity userEntity = null;
  16       try {
  17          userEntity = oauthDao.getUserDetails(username);
  18          CustomUser customUser = new CustomUser(userEntity);
  19          return customUser;
  20       } catch (Exception e) {
  21          e.printStackTrace();
  22          throw new UsernameNotFoundException("User " + username + " was not found in the database");
  23       }
  24    }
  25 } 
src/main/java/com/tutorialspoint/websecurityapp/OAuthDao.java
   1 package com.tutorialspoint.websecurityapp;
   2 
   3 import java.sql.ResultSet;
   4 import java.util.ArrayList;
   5 import java.util.Collection;
   6 import java.util.List;
   7 
   8 import org.springframework.beans.factory.annotation.Autowired;
   9 import org.springframework.jdbc.core.JdbcTemplate;
  10 import org.springframework.security.core.GrantedAuthority;
  11 import org.springframework.security.core.authority.SimpleGrantedAuthority;
  12 import org.springframework.stereotype.Repository;
  13 
  14 @Repository
  15 public class OAuthDao {
  16         @Autowired
  17         private JdbcTemplate jdbcTemplate;
  18 
  19         public UserEntity getUserDetails(String username) {
  20 
  21                 String userSQLQuery = "SELECT * FROM USERS WHERE USERNAME=?";
  22                 List<UserEntity> list = jdbcTemplate.query(userSQLQuery, new String[] { username },
  23                                 (ResultSet resultSet, int rowNum) -> {
  24 
  25                                         UserEntity user = new UserEntity();
  26                                         user.setUsername(username);
  27                                         user.setPassword(resultSet.getString("PASSWORD"));
  28                                         user.setRole(resultSet.getString("ROLE"));
  29                                         return user;
  30                                 });
  31                 
  32                 if (list.size() > 0) {
  33                         Collection<GrantedAuthority> grantedAuthoritiesList = new ArrayList<>();
  34                         UserEntity user = list.get(0);
  35                         GrantedAuthority grantedAuthority = new SimpleGrantedAuthority(user.getRole());
  36                         grantedAuthoritiesList.add(grantedAuthority);
  37                         user.setGrantedAuthoritiesList(grantedAuthoritiesList);
  38                         return user;
  39                 }
  40                 
  41                 return null;
  42         }
  43 }
src/main/resources/schema.sql
   1 CREATE TABLE USERS (ID INT PRIMARY KEY, USERNAME VARCHAR(45), PASSWORD VARCHAR(60), ROLE VARCHAR(60) );
src/main/resources/application.properties
security.oauth2.resource.filter-order=3 logging.file=/tmp/testout.log
src/main/resources/data.sql
   1 INSERT INTO USERS (ID, USERNAME,PASSWORD, ROLE) VALUES (
   2    1, 'tutorialspoint@gmail.com','$2a$08$fL7u5xcvsZl78su29x1ti.dxI.9rYO8t0q5wk2ROJ.1cdR53bmaVG','ROLE_ADMIN');
   3 
   4 INSERT INTO USERS (ID, USERNAME,PASSWORD, ROLE) VALUES (
   5    2, 'myemail@gmail.com','$2a$08$fL7u5xcvsZl78su29x1ti.dxI.9rYO8t0q5wk2ROJ.1cdR53bmaVG','ROLE_USER'); 
build_image.sh
   1 docker build -t test_image .
pom.xml
   1 <?xml version = "1.0" encoding = "UTF-8"?>
   2 <project xmlns="http://maven.apache.org/POM/4.0.0"
   3         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   4         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 
   5    http://maven.apache.org/xsd/maven-4.0.0.xsd">
   6 
   7         <modelVersion>4.0.0</modelVersion>
   8         <groupId>com.tutorialspoint</groupId>
   9         <artifactId>websecurityapp</artifactId>
  10         <version>0.0.1-SNAPSHOT</version>
  11         <packaging>jar</packaging>
  12         <name>websecurityapp</name>
  13         <description>Demo project for Spring Boot</description>
  14 
  15         <parent>
  16                 <groupId>org.springframework.boot</groupId>
  17                 <artifactId>spring-boot-starter-parent</artifactId>
  18                 <version>1.5.9.RELEASE</version>
  19                 <relativePath /> <!-- lookup parent from repository -->
  20         </parent>
  21 
  22         <properties>
  23                 <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
  24                 <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
  25                 <java.version>1.8</java.version>
  26         </properties>
  27 
  28         <dependencies>
  29                 <!--  Caused by: java.lang.ClassNotFoundException: javax.xml.bind.JAXBException  -->
  30                 <!-- API, java.xml.bind module -->
  31                 <dependency>
  32                         <groupId>jakarta.xml.bind</groupId>
  33                         <artifactId>jakarta.xml.bind-api</artifactId>
  34                         <version>2.3.2</version>
  35                 </dependency>
  36 
  37                 <!-- Runtime, com.sun.xml.bind module -->
  38                 <dependency>
  39                         <groupId>org.glassfish.jaxb</groupId>
  40                         <artifactId>jaxb-runtime</artifactId>
  41                         <version>2.3.2</version>
  42                 </dependency>
  43                 <dependency>
  44                         <groupId>org.springframework.boot</groupId>
  45                         <artifactId>spring-boot-starter-jdbc</artifactId>
  46                 </dependency>
  47 
  48                 <dependency>
  49                         <groupId>org.springframework.boot</groupId>
  50                         <artifactId>spring-boot-starter-security</artifactId>
  51                 </dependency>
  52 
  53                 <dependency>
  54                         <groupId>org.springframework.boot</groupId>
  55                         <artifactId>spring-boot-starter-web</artifactId>
  56                 </dependency>
  57 
  58                 <dependency>
  59                         <groupId>org.springframework.security.oauth</groupId>
  60                         <artifactId>spring-security-oauth2</artifactId>
  61                 </dependency>
  62 
  63                 <dependency>
  64                         <groupId>org.springframework.security</groupId>
  65                         <artifactId>spring-security-jwt</artifactId>
  66                 </dependency>
  67 
  68                 <dependency>
  69                         <groupId>com.h2database</groupId>
  70                         <artifactId>h2</artifactId>
  71                 </dependency>
  72 
  73                 <dependency>
  74                         <groupId>org.springframework.boot</groupId>
  75                         <artifactId>spring-boot-starter-test</artifactId>
  76                         <scope>test</scope>
  77                 </dependency>
  78 
  79                 <dependency>
  80                         <groupId>org.springframework.security</groupId>
  81                         <artifactId>spring-security-test</artifactId>
  82                         <scope>test</scope>
  83                 </dependency>
  84         </dependencies>
  85 
  86         <build>
  87                 <plugins>
  88                         <plugin>
  89                                 <groupId>org.springframework.boot</groupId>
  90                                 <artifactId>spring-boot-maven-plugin</artifactId>
  91                         </plugin>
  92                 </plugins>
  93         </build>
  94 
  95 </project>
get_token.sh
   1 ACCESS_TOKEN=$(curl -X POST --url http://localhost:8080/oauth/token --user tutorialspoint:my-secret-key --data 'grant_type=password&username=myemail@gmail.com&password=password' | jq -r '.access_token')
   2 ACCESS_TOKEN_ADMIN=$(curl -X POST --url http://localhost:8080/oauth/token --user tutorialspoint:my-secret-key --data 'grant_type=password&username=tutorialspoint@gmail.com&password=password' | jq -r '.access_token')
   3 #echo $ACCESS_TOKEN
   4 curl -X GET http://localhost:8080/productsuser  --header "Authorization: Bearer $ACCESS_TOKEN"
   5 curl -X GET http://localhost:8080/products  --header "Authorization: Bearer $ACCESS_TOKEN_ADMIN"
   6 curl -X GET http://localhost:8080/anonymous/dummy
   7 
   8 curl -X GET http://localhost:8080/products  --header "Authorization: Bearer $ACCESS_TOKEN"
   9 curl -X GET http://localhost:8080/productsuser  --header "Authorization: Bearer $ACCESS_TOKEN_ADMIN"
connect_container.sh
   1 docker exec -it test /bin/sh
stop_container.sh
SpringBoot 2.2.8 (resource server) + keycloak 10.0.2 (authentication server) + Java 11
wget https://downloads.jboss.org/keycloak/10.0.2/keycloak-10.0.2.zip unzip -t keycloak-10.0.2.zip cd ~/keycloak-10.0.2/bin sh standalone.sh http://localhost:8080/auth admin admin admin create http://localhost:8080/auth/admin/master/console/#/realms/master Master, add realm, MyRealm , create Users, add user, myuser select user, credentials, mypwd mypwd, temporary off Add role USER to MyRealm Make user myuser have role USER signout http://localhost:8080/auth/realms/MyRealm/account/ realm: MyRealm user pwd: myuser mypwd client id: curl_confidential protocol: openid-connect Curl_confidential settings: access-type confidential valid redirect url http://localhost:8080 tab credentials: regenerate secret 6dfe5f84-d115-4d3e-8a56-a0fcf5b2f13e curl -d 'client_id=curl_confidential' -d 'client_secret=6dfe5f84-d115-4d3e-8a56-a0fcf5b2f13e' -d 'username=myuser' -d 'password=mypwd' -d 'grant_type=password' 'http://localhost:8080/auth/realms/MyRealm/protocol/openid-connect/token'
.
├── pom.xml
└── src
    └── main
        ├── java
        │   └── com
        │       └── example
        │           └── demo
        │               └── DemoApplication.java
        └── resources
            └── application.properties
pom.xml
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
        <modelVersion>4.0.0</modelVersion>
        <parent>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-parent</artifactId>
                <version>2.2.8.RELEASE</version>
                <relativePath/> <!-- lookup parent from repository -->
        </parent>
        <groupId>com.example</groupId>
        <artifactId>demo</artifactId>
        <version>0.0.1-SNAPSHOT</version>
        <name>demo</name>
        <description>Demo project for Spring Boot</description>
        <properties>
                <java.version>11</java.version>
        </properties>
        <dependencies>
                <dependency>
                        <groupId>org.springframework.boot</groupId>
                        <artifactId>spring-boot-starter-oauth2-resource-server</artifactId>
                </dependency>
                <dependency>
                        <groupId>org.springframework.boot</groupId>
                        <artifactId>spring-boot-starter-security</artifactId>
                </dependency>
                <dependency>
                        <groupId>org.springframework.boot</groupId>
                        <artifactId>spring-boot-starter-web</artifactId>
                </dependency>
        </dependencies>
        <build>
                <plugins>
                        <plugin>
                                <groupId>org.springframework.boot</groupId>
                                <artifactId>spring-boot-maven-plugin</artifactId>
                        </plugin>
                </plugins>
        </build>
</project>
src/main/resources/application.properties
server.port=8181 spring.security.oauth2.resourceserver.jwt.issuer-uri=http://localhost:8080/auth/realms/MyRealm #logging.level.root=DEBUG logging.level.root=INFO logging.file=/tmp/testout.log
src/main/java/com/example/demo/DemoApplication.java
   1 package com.example.demo;
   2 
   3 import org.springframework.boot.SpringApplication;
   4 import org.springframework.boot.autoconfigure.SpringBootApplication;
   5 import org.springframework.web.bind.annotation.GetMapping;
   6 import org.springframework.web.bind.annotation.RestController;
   7 import org.springframework.security.core.Authentication;
   8 import org.springframework.security.core.GrantedAuthority;
   9 import org.springframework.security.oauth2.jwt.Jwt;
  10 
  11 @RestController
  12 @SpringBootApplication
  13 public class DemoApplication {
  14 
  15         public static void main(String[] args) {
  16                 SpringApplication.run(DemoApplication.class, args);
  17         }
  18 
  19 
  20     @GetMapping("/otherhello")
  21     public String otherHello(){
  22       return "other hello";
  23     }
  24 
  25     @GetMapping("/hello")
  26     public String hello(Authentication authentication) {
  27         String s=""; 
  28         for(int i=0; i<authentication.getAuthorities().size();i++){
  29           GrantedAuthority ga = (GrantedAuthority)  authentication.getAuthorities().toArray()[i];
  30           s +=  ga.getAuthority()  + " ";
  31         }
  32         Jwt jwt = (Jwt) authentication.getCredentials();
  33         
  34         Object[] keys = jwt.getClaims().keySet().toArray();
  35         String allkeys = "";
  36 
  37         for(int j=0; j< keys.length  ;j++){
  38           allkeys = allkeys + " " +  (String)keys[j]  + ":" + jwt.getClaims().get( keys[j] ).toString()+ " ";
  39         }
  40 
  41         return "I am authenticated with user " + authentication.getName() + " " + s + " " + authentication.getDetails().toString() + " " + allkeys;
  42     }
  43 
  44 }
src/main/java/com/example/demo/SecurityConfiguration.java
   1 package com.example.demo;
   2 
   3 import org.springframework.beans.factory.annotation.Autowired;
   4 import org.springframework.context.annotation.Bean;
   5 import org.springframework.context.annotation.Configuration;
   6 import org.springframework.security.authentication.AuthenticationManager;
   7 import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
   8 import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
   9 import org.springframework.security.config.annotation.web.builders.HttpSecurity;
  10 import org.springframework.security.config.annotation.web.builders.WebSecurity;
  11 import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
  12 import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
  13 import org.springframework.security.config.http.SessionCreationPolicy;
  14 import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
  15 import org.springframework.security.crypto.password.PasswordEncoder;
  16 
  17 @Configuration
  18 @EnableWebSecurity
  19 public class SecurityConfiguration extends WebSecurityConfigurerAdapter {
  20 
  21         @Override
  22         protected void configure(HttpSecurity http) throws Exception {
  23                 http.oauth2ResourceServer().jwt();
  24         }
  25 
  26         @Override
  27         public void configure(WebSecurity web) throws Exception {
  28                 web.ignoring().antMatchers("/otherhello**").antMatchers("/static**");
  29         }
  30 
  31 }
src/main/webapp/static/test2.txt
test2
Invoke endpoint on resource server with access token from keycloak
curl http://localhost:8181/hello -vvv
TOKEN=$(curl -d 'client_id=curl_confidential' -d 'client_secret=6dfe5f84-d115-4d3e-8a56-a0fcf5b2f13e' -d 'username=myuser' -d 'password=mypwd' -d 'grant_type=password' 'http://localhost:8080/auth/realms/MyRealm/protocol/openid-connect/token' | jq -r '.access_token')
curl -X GET http://localhost:8181/hello  --header "Authorization: Bearer $TOKEN"
I am authenticated with user d7192f29-ee2f-4079-95f9-a75df61f3973 SCOPE_profile SCOPE_email  org.springframework.security.web.authentication.WebAuthenticationDetails@b364: RemoteIpAddress: 0:0:0:0:0:0:0:1; SessionId: null  sub:d7192f29-ee2f-4079-95f9-a75df61f3973  resource_access:{"account":{"roles":["manage-account","manage-account-links","view-profile"]}}  email_verified:false  iss:http://localhost:8080/auth/realms/MyRealm  typ:Bearer  preferred_username:myuser  aud:[account]  acr:1  realm_access:{"roles":["offline_access","uma_authorization","USER"]}  azp:curl_confidential  scope:profile email  exp:2020-06-18T23:01:09Z  session_state:a3cc9c25-ae55-492f-be5a-28aafd3a6d3f  iat:2020-06-18T22:56:09Z  jti:bc4a4a6e-5da5-434b-9a77-cb0a88c64c4c
curl -X GET http://localhost:8181/otherhello
# other hello
curl -X GET http://localhost:8181/static/test2.txt -v
# test2