Spring Security with JDBC Annotation only - spring

I am trying to create a Spring Boot Application using the Spring Security. I took the following example from http://spring.io/guides/gs/securing-web/. They use an "In Memory Authentification". I want to do the same but use a JDBC-Authentification.
Here is my WebSecurityConfig class:
package hello;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.jdbc.datasource.DriverManagerDataSource;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.config.annotation.web.servlet.configuration.EnableWebMvcSecurity;
#Configuration
#EnableWebMvcSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
#Override
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.antMatchers("/", "/home").permitAll()
.anyRequest().authenticated()
.and()
.formLogin()
.loginPage("/login")
.permitAll()
.and()
.logout()
.permitAll();
}
#Autowired
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
DriverManagerDataSource dataSource = new DriverManagerDataSource();
dataSource.setDriverClassName("com.mysql.jdbc.Driver");
dataSource.setUrl("jdbc:mysql://localhost:3306/test");
dataSource.setUsername("root");
dataSource.setPassword("root");
auth
.jdbcAuthentication().dataSource(dataSource)
.usersByUsernameQuery("select * from users where username=?")
.authoritiesByUsernameQuery("select * from user_roles where username=?");
}
}
I also set up a MySQL Database "test" and two tables "users" and "user_roles".
When I run the application and try to sign in I dont't get any Exceptions, but the application somehow can't find the user.
Can someone help me? What am I doing wrong?
Login page:
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:th="http://www.thymeleaf.org"
xmlns:sec="http://www.thymeleaf.org/thymeleaf-extras-springsecurity3">
<head>
<title>Spring Security Example </title>
</head>
<body>
<div th:if="${param.error}">
Invalid username and password.
</div>
<div th:if="${param.logout}">
You have been logged out.
</div>
<form th:action="#{/login}" method="post">
<div><label> User Name : <input type="text" name="username"/> </label></div>
<div><label> Password: <input type="password" name="password"/> </label></div>
<div><input type="submit" value="Sign In"/></div>
</form>
</body>
</html>
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 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>org.springframework</groupId>
<artifactId>gs-securing-web</artifactId>
<version>0.1.0</version>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>1.2.2.RELEASE</version>
</parent>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
<!-- tag::security[] -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<!-- end::security[] -->
<!-- JDBC -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>3.2.8.RELEASE</version>
</dependency>
<!-- MySQL -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>

Your user has to have at least one role assigned. If the user has no role, then the authentication fails (even if you want to be able to login without any specific roles). Also make sure, that the enabled flag of the user is true.

It is recommended that your Datasource is solved as a separated Bean instead of instantiate it in your configureGlobal Method:
#Bean
public DataSource dataSource() {
// create and return a new JDBC DataSource ...
}
You can make use the Bean as you made in your configureGlobal Method:
auth.jdbcAuthentication().dataSource(dataSource)

Related

Passing tokens through microservices using oauth2 authentication through GitHub

For this assignment we are to implement oauth2 using OAuth Apps in GitHub. We have two microservices UMS (UserManagmentService) and Messaging service. I am following the tutorial https://spring.io/guides/tutorials/spring-boot-oauth2/, as recommended - and it is working fine. I now have to extract the token and save it to a database with an expiry of 15 minutes in order to pass it to the other microservice (? I believe there is better ways to implement this). I would rather use JWT but do not understand the process to do so after using oauth2 through GitHub. My main questions are:
How to extract the token and store it to a database
How to set an expiry to the token
If possible, how to use a JWT instead and do the above.
I have limited knowledge of this as it is a new concept, any help would be appreciated.
INDEX.HTML
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8"/>
<meta http-equiv="X-UA-Compatible" content="IE=edge"/>
<title>Tweeter</title>
<meta name="description" content=""/>
<meta name="viewport" content="width=device-width"/>
<base href="/"/>
<link rel="stylesheet" type="text/css" href="/webjars/bootstrap/css/bootstrap.min.css"/>
<script type="text/javascript" src="/webjars/jquery/jquery.min.js"></script>
<script type="text/javascript" src="/webjars/bootstrap/js/bootstrap.min.js"></script>
<script type="text/javascript" src="/webjars/js-cookie/js.cookie.js"></script>
</head>
<body>
<h1>Welcome to Tweeter!</h1>
<div class="container unauthenticated">
Log In With GitHub
</div>
<div class="container authenticated" style="display:none">
Logged in as: <span id="user"></span>
</div>
<div>
<button onClick="logout()" class="btn btn-primary">Logout</button>
</div>
</div>
<script type="text/javascript">
$.get("/user", function(data) {
$("#user").html(data.name);
$(".unauthenticated").hide()
$(".authenticated").show()
});
var logout = function() {
$.post("/logout", function() {
$("#user").html('');
$(".unauthenticated").show();
$(".authenticated").hide();
})
return true;
}
$.ajaxSetup({
beforeSend : function(xhr, settings) {
if (settings.type == 'POST' || settings.type == 'PUT'
|| settings.type == 'DELETE') {
if (!(/^http:.*/.test(settings.url) || /^https:.*/
.test(settings.url))) {
// Only send the token to relative URLs i.e. locally.
xhr.setRequestHeader("X-XSRF-TOKEN",
Cookies.get('XSRF-TOKEN'));
}
}
}
});
</script>
</body>
</html>
WEBSECURITY
import org.springframework.context.annotation.Configuration;
import org.springframework.http.HttpStatus;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.web.authentication.HttpStatusEntryPoint;
import org.springframework.security.web.csrf.CookieCsrfTokenRepository;
#Configuration
#EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
#Override
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests(auth -> auth
.antMatchers("/", "/error", "/webjars/**").permitAll()
.anyRequest().authenticated()
)
.exceptionHandling(exc -> exc
.authenticationEntryPoint(new HttpStatusEntryPoint(HttpStatus.UNAUTHORIZED))
)
.csrf(c -> c
.csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse())
)
.logout(l -> l
.logoutSuccessUrl("/").permitAll()
)
.oauth2Login()
;
}
}
OAUTH2 CONTROLLER
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpEntity;
import org.springframework.http.ResponseEntity;
import org.springframework.security.core.annotation.AuthenticationPrincipal;
import org.springframework.security.oauth2.client.OAuth2AuthorizedClient;
import org.springframework.security.oauth2.client.OAuth2AuthorizedClientService;
import org.springframework.security.oauth2.client.authentication.OAuth2AuthenticationToken;
import org.springframework.security.oauth2.core.user.OAuth2User;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;
import java.net.http.HttpHeaders;
import java.util.Collections;
import java.util.Map;
#RestController
public class oauth2Controller {
#Autowired
private OAuth2AuthorizedClientService authorizedClientService;
#GetMapping(value="/user")
public Map<String, Object> username(#AuthenticationPrincipal OAuth2User principal) {
return Collections.singletonMap("name", principal.getAttribute("name"));
}
#GetMapping(value="/getAuthentication", produces="application/json")
public String getAuthentication(OAuth2AuthenticationToken auth) {
return auth.toString();
}
#GetMapping(value = "/getToken", produces = "application/json")
public String getEmails(OAuth2AuthenticationToken authentication) {
OAuth2AuthorizedClient client = authorizedClientService.loadAuthorizedClient(
authentication.getAuthorizedClientRegistrationId(),
authentication.getPrincipal().getName());
String token = client.getAccessToken().getTokenValue();
return token;
}
}
APPLICATION.YAML
## Server
server:
port: 8080
## MySQL
spring:
datasource:
driverClassName: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://0.0.0.0:3306/ums?serverTimezone=UTC&useLegacyDatetimeCode=false
username: root
password: passw
#GitHub
security:
oauth2:
client:
registration:
github:
clientId: ***********
clientSecret: ************
scope: read:user, user:name
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.7.6</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>org.cst8277.gibbons.caitlyn</groupId>
<artifactId>ums</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>ums</name>
<description>ums</description>
<properties>
<java.version>17</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-oauth2-client</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-webflux</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>com.mysql</groupId>
<artifactId>mysql-connector-j</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>io.projectreactor</groupId>
<artifactId>reactor-test</artifactId>
<scope>test</scope>
</dependency>
<!-- Added after creation-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
<version>3.0.0</version>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>jquery</artifactId>
<version>3.4.1</version>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>bootstrap</artifactId>
<version>4.3.1</version>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>webjars-locator-core</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>io.jsonwebtoken</groupId>
<artifactId>jjwt-api</artifactId>
<version>0.11.5</version>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>js-cookie</artifactId>
<version>2.1.0</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<excludes>
<exclude>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</exclude>
</excludes>
</configuration>
</plugin>
</plugins>
</build>
</project>

Spring boot WAR file Runs successfully on Eclipse IDE and by terminal but not running on external Tomcat 9.0

I have created a SpringBoot application with thymeleaf template, This application running successfully on Eclipse IDE and Running War file by MAC terminal command:
java -jar ./SpringBootTestMe.war
But problem is that it is not running on external tomcat-9.0, Giving below ERROR:
Sun Jan 26 09:01:37 IST 2020 There was an unexpected error
(type=Internal Server Error, status=500). Error during execution of
processor
'org.thymeleaf.spring5.processor.SpringInputGeneralFieldTagProcessor'
(template: "index" - line 13, col 28)
My source code are
File pom.xml
<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.spboot</groupId>
<artifactId>SpringBootTestMe</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>SpringBootTest</name>
<packaging>war</packaging>
<!-- lookup parent from repository -->
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.1.RELEASE</version>
<relativePath />
</parent>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
<start-class>com.spboot.web.TestApp</start-class>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
<scope>provided</scope>
</dependency>
</dependencies>
<build>
<finalName>SpringBootTestMe</finalName>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
SpringBootMainClass
package com.spboot.web;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.boot.web.servlet.support.SpringBootServletInitializer;
#SpringBootApplication
public class TestApp extends SpringBootServletInitializer {
public static void main(String[] args) {
SpringApplication.run(TestApp.class, args);
System.out.println("--------AppStarted--------");
}
#Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder builder) {
return builder.sources(TestApp.class);
}
}
HomeController
#Controller
#RequestMapping("SpringBootTestMe")
public class HomeController {
#RequestMapping(value={"", "login"})
public String login(UserRecord userRecord) {
System.out.println("HomeController Called...");
return "index";
}
}
ModalClass
public class UserRecord implements Serializable {
private Long id;
private String username;
private String email;
//Setters and getters
}
index.html
<!DOCTYPE html>
<html xmlns:th="https://thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>Login Page</title>
</head>
<body>
<div>
<form action="#" th:action="#{/login}" th:object="${userRecord}" method="post">
<table>
<tr>
<td><label for="username">User Name</label></td>
<td><input type="text" th:field="*{username}" /></td>
<td th:if="${#fields.hasErrors('username')}" th:errors="*{username}">Username Error</td>
</tr>
<tr>
<td><label for="email">Email</label></td>
<td><input type="text" th:field="*{email}"></input></td>
<td th:if="${#fields.hasErrors('email')}" th:errors="*{email}">Name Error</td>
</tr>
<tr>
<td></td>
<td><input type="submit" value="Submit"></input></td>
</tr>
</table>
</form>
</div>
</body>
</html>
It's giving error on username text field, tomcat not recognising the th:field
Can anybody help me please.
Thanks

The redirect URI included is not valid

I am trying to use GitLab OAuth2 with Spring Boot, but I am continuously getting:
redirected uri is invalid
I already registered the app in GitLab.
Here is my application.yml
security:
oauth2:
client:
clientId: CLIENT_ID
clientSecret: CLIENT_SECRET
userAuthorizationUri: https://gitlab.your-domain.com/oauth/authorize
accessTokenUri: https://gitlab.your-domain.com/oauth/token
registered-redirect-uri:
#- http://localhost:8080/login/oauth2/code/gitlab
- http://localhost:8080
tokenName: oauth_token
authenticationScheme: query
clientAuthenticationScheme: form
resource:
userInfoUri: https://gitlab.your-domain.com/api/v4/user
and a simple Spring REST class:
#SpringBootApplication
#EnableOAuth2Sso
#RestController
public class DemoApplication extends WebSecurityConfigurerAdapter {
public static void main(String[] args) {
SpringApplication.run(DemoApplication.class, args);
}
#RequestMapping("/user")
public Principal user(Principal principal) {
return principal;
}
#Override
protected void configure(HttpSecurity http) throws Exception {
http
.antMatcher("/**")
.authorizeRequests()
.antMatchers("/", "/login**", "/webjars/**", "/error**").permitAll()
.anyRequest().authenticated()
.and()
.logout()
.logoutSuccessUrl("/")
.permitAll();
}
}
Finally the index.html file:
<body>
<h1>Demo</h1>
<div class="container unauthenticated">
With GitLab: click here
</div>
<div class="container authenticated" style="display: none">
Logged in as: <span id="user"></span>
<div>
<button onClick="logout()" class="btn btn-primary">Logout</button>
</div>
</div>
<script type="text/javascript">
$.get("/user", function(data) {
$("#user").html(data.userAuthentication.details.name);
$(".unauthenticated").hide()
$(".authenticated").show()
});
var logout = function() {
$.post("/logout", function() {
$("#user").html('');
$(".unauthenticated").show();
$(".authenticated").hide();
})
return true;
}
</script>
</body>
I am able to login to GitLab, and authorization is also done successfully, finally when it came to redirecting to the base URL:
http://localhost:8080
its saying the redirect URL is not valid.
Here is my 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 http://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.1.4.RELEASE</version>
<relativePath /> <!-- lookup parent from repository -->
</parent>
<groupId>com.learning</groupId>
<artifactId>spring-oauth-gitlab-demo-app</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>demo</name>
<description>Demo project for Spring Boot</description>
<properties>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>jquery</artifactId>
<!-- <version>2.1.1</version> -->
<version>3.4.1</version>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>bootstrap</artifactId>
<!-- <version>3.2.0</version> -->
<version>4.3.1</version>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>webjars-locator-core</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.security.oauth.boot</groupId>
<artifactId>spring-security-oauth2-autoconfigure</artifactId>
<version>2.1.4.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-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>
I was getting the same error in Gitlab and I fixed it by changing http://localhost:5000 to http://localhost:5000/!!

Spring Security OAuth2 SSO Unauthorized 401 Error

I am quite new to Spring Security and OAuth2 SSO in particular.
I am currently trying to test and learn with this sample Spring Boot OAuth2 tutorial:
https://spring.io/guides/tutorials/spring-boot-oauth2/
I can sign in using similar application.yml settings like this:
security:
oauth2:
client:
clientId: 233668646673605
clientSecret: 33b17e044ee6a4fa383f46ec6e28ea1d
accessTokenUri: https://graph.facebook.com/oauth/access_token
userAuthorizationUri: https://www.facebook.com/dialog/oauth
tokenName: oauth_token
authenticationScheme: query
clientAuthenticationScheme: form
resource:
userInfoUri: https://graph.facebook.com/me
Here is my 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 http://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.1.3.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.sao.social.apps</groupId>
<artifactId>SocialApplication</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>SocialApplication</name>
<description>OAuth2 Login With Spring Boot</description>
<properties>
<java.version>1.8</java.version>
</properties>
<dependencies>
<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.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>
<dependency>
<groupId>org.springframework.security.oauth.boot</groupId>
<artifactId>spring-security-oauth2-autoconfigure</artifactId>
<version>2.1.1.RELEASE</version>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>jquery</artifactId>
<version>2.1.1</version>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>bootstrap</artifactId>
<version>3.2.0</version>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>webjars-locator-core</artifactId>
</dependency>
<dependency>
<groupId>org.webjars</groupId>
<artifactId>js-cookie</artifactId>
<version>2.1.0</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
Here is the main class that also has OAuth2SSO enabled as as well as security and rest controller:
#SpringBootApplication
#EnableOAuth2Sso
#RestController
public class SocialApplication extends WebSecurityConfigurerAdapter {
#RequestMapping("/user")
public Principal user(Principal principal) {
return principal;
}
#Override
protected void configure(HttpSecurity httpSec) throws Exception{
httpSec
.antMatcher("/**")
.authorizeRequests()
.antMatchers("/", "/login**", "/webjars/**", "/error**")
.permitAll()
.anyRequest()
.authenticated()
.and().logout().logoutSuccessUrl("/").permitAll()
.and().csrf().csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse());
}
public static void main(String[] args) {
SpringApplication.run(SocialApplication.class, args);
}
}
And finally here is the view: index.html:
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8"/>
<meta http-equiv="X-UA-Compatible" content="IE=edge"/>
<title>Demo</title>
<meta name="description" content=""/>
<meta name="viewport" content="width=device-width"/>
<base href="/"/>
<link rel="stylesheet" type="text/css" href="/webjars/bootstrap/css/bootstrap.min.css"/>
<script type="text/javascript" src="/webjars/jquery/jquery.min.js"></script>
<script type="text/javascript" src="/webjars/bootstrap/js/bootstrap.min.js"></script>
</head>
<body>
<div class="container">
<h1>Login</h1>
<div class="container unauthenticated">
With Facebook: click here
</div>
<div class="container authenticated" style="display:none">
Logged in as: <span id="user"></span>
</div>
</div>
<script type="text/javascript">
$.get("/user", function(data) {
$("#user").html(data.userAuthentication.details.name);
$(".unauthenticated").hide();
$(".authenticated").show();
});
</script>
</body>
</html>
My main challenge is that I can login with Facebook(The Authorization Server in this case) but then when I am redirected to localhost:8080/login I always receive 401 unauthorized error from spring instead of showing me the name of the user successfully authenticated and logged in as expected in the view-index.html. Is there something else I need to set up on Facebook or am I missing something on Spring?
Thank you!
Make sure that the package of the SocialApplication class is at the same level as the other packages, it is possible that the #SpringBootApplication annotation of your main class is not scanning its components.
This was a solution for me.
I am following this tutorial too and am having the same issue. After updating to java 11 the problem disappeared and the "loggend in as" div showed.

Setting up a custom login page with spring security woes

Currently trying to create a simple login with spring Security but am getting an error that I am assume is because of something I am doing wrong with resolver view or controller. Just can't seem to figure out what. I get the following error
"There was an unexpected error (type=Internal Server Error, status=500).
Circular view path [home]: would dispatch back to the current handler URL [/home] again. Check your ViewResolver setup! (Hint: This may be the result of an unspecified view, due to default view name generation.)"
My Config:
#EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter{
public void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.inMemoryAuthentication()
.withUser("user")
.password("password")
.roles("USER");
}
public void configureGlobal(HttpSecurity http) throws Exception {
http.authorizeRequests()
.antMatchers("/resources/**").permitAll()
.anyRequest().authenticated()
.and()
.formLogin()
.loginPage("/loginpage")
.permitAll().and()
.logout();
}
#Bean
public ViewResolver viewResolver(){
InternalResourceViewResolver resolver = new InternalResourceViewResolver();
resolver.setViewClass(JstlView.class);
resolver.setPrefix("/resources/templates");
resolver.setSuffix(".html");
return resolver;
}
public void addViewController(ViewControllerRegistry registry){
registry.addViewController("/home").setViewName("home");
registry.addViewController("/loginpage").setViewName("loginpage");
}
}
Controller:
#Controller
public class loginController {
#RequestMapping("/home")
public String homePage(Model model){
return "home";
}
#GetMapping("/loginpage")
public String loginGetter(Model model){
return "loginpage";
}
}
Login page:
<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org">
<head>
<title>Title</title>
</head>
<body>
<div th:if="${param.error}">
Something is wrong
</div>
<div th:if="${param.logout}">
You have logged out
</div>
<div>
<form action="#{loginpage}" method="post">
<div><label>Username: <input type="text" name="username"/></in></label></div>
<div><label>Password: <input type="text" name="password"/></label></div>
<div><input type="submit" value="Sign in"/></in></div>
</form>
</div>
</body>
</html>
My Pom:
<?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.ronone</groupId>
<artifactId>SecurityTutorial</artifactId>
<version>1.0-SNAPSHOT</version>
<dependencies>
<!-- https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-web -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<version>1.5.2.RELEASE</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.springframework.security/spring-security-core -->
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-core</artifactId>
<version>4.2.2.RELEASE</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.springframework.security/spring-security-web -->
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-web</artifactId>
<version>4.2.1.RELEASE</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.springframework.security/spring-security-config -->
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-config</artifactId>
<version>3.2.0.RELEASE</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.thymeleaf/thymeleaf-spring3 -->
<dependency>
<groupId>org.thymeleaf</groupId>
<artifactId>thymeleaf-spring3</artifactId>
<version>3.0.3.RELEASE</version>
</dependency>
</dependencies>
</project>
Try this :
#EnableWebSecurity
#Configuration
public class SecurityConfig extends WebSecurityConfigurerAdapter{ ...}
Annotating a class with the #Configuration indicates that the class can be used by the Spring IoC container as a source of bean definitions.

Resources