Make default username and password configurable

Closes gh-10963
This commit is contained in:
Madhura Bhave 2017-12-11 13:02:33 -08:00
parent e68d8a3f98
commit 47ed096981
33 changed files with 170 additions and 135 deletions

View File

@ -16,7 +16,7 @@
package org.springframework.boot.autoconfigure.security;
import java.util.UUID;
import java.util.List;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
@ -57,15 +57,19 @@ public class AuthenticationManagerConfiguration {
.getLog(AuthenticationManagerConfiguration.class);
@Bean
public InMemoryUserDetailsManager inMemoryUserDetailsManager(
public InMemoryUserDetailsManager inMemoryUserDetailsManager(SecurityProperties properties,
ObjectProvider<PasswordEncoder> passwordEncoder) throws Exception {
String password = UUID.randomUUID().toString();
logger.info(String.format("%n%nUsing default security password: %s%n", password));
SecurityProperties.User user = properties.getUser();
if (user.isPasswordGenerated()) {
logger.info(String.format("%n%nUsing generated security password: %s%n", user.getPassword()));
}
String encodedPassword = passwordEncoder
.getIfAvailable(PasswordEncoderFactories::createDelegatingPasswordEncoder)
.encode(password);
.encode(user.getPassword());
List<String> roles = user.getRoles();
return new InMemoryUserDetailsManager(
User.withUsername("user").password(encodedPassword).roles().build());
User.withUsername(user.getName()).password(encodedPassword)
.roles(roles.toArray(new String[roles.size()])).build());
}
}

View File

@ -16,20 +16,25 @@
package org.springframework.boot.autoconfigure.security;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.UUID;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.web.servlet.DispatcherType;
import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.core.Ordered;
import org.springframework.util.StringUtils;
/**
* Configuration properties for Spring Security.
*
* @author Dave Syer
* @author Andy Wilkinson
* @author Madhura Bhave
*/
@ConfigurationProperties(prefix = "spring.security")
public class SecurityProperties implements SecurityPrerequisite {
@ -58,6 +63,12 @@ public class SecurityProperties implements SecurityPrerequisite {
private final Filter filter = new Filter();
private User user = new User();
public User getUser() {
return this.user;
}
public Filter getFilter() {
return this.filter;
}
@ -93,4 +104,56 @@ public class SecurityProperties implements SecurityPrerequisite {
}
public static class User {
/**
* Default user name.
*/
private String name = "user";
/**
* Password for the default user name.
*/
private String password = UUID.randomUUID().toString();
/**
* Granted roles for the default user name.
*/
private List<String> roles = new ArrayList<>();
private boolean passwordGenerated = true;
public String getName() {
return this.name;
}
public void setName(String name) {
this.name = name;
}
public String getPassword() {
return this.password;
}
public void setPassword(String password) {
if (!StringUtils.hasLength(password)) {
return;
}
this.passwordGenerated = false;
this.password = password;
}
public List<String> getRoles() {
return this.roles;
}
public void setRoles(List<String> roles) {
this.roles = new ArrayList<>(roles);
}
public boolean isPasswordGenerated() {
return this.passwordGenerated;
}
}
}

View File

@ -16,7 +16,7 @@
package org.springframework.boot.autoconfigure.security.reactive;
import java.util.UUID;
import java.util.List;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
@ -25,6 +25,7 @@ import org.springframework.beans.factory.ObjectProvider;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication;
import org.springframework.boot.autoconfigure.security.SecurityProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.ReactiveAuthenticationManager;
@ -54,20 +55,24 @@ class ReactiveAuthenticationManagerConfiguration {
.getLog(ReactiveAuthenticationManagerConfiguration.class);
@Bean
public MapReactiveUserDetailsService reactiveUserDetailsService(
public MapReactiveUserDetailsService reactiveUserDetailsService(SecurityProperties properties,
ObjectProvider<PasswordEncoder> passwordEncoder) {
String password = UUID.randomUUID().toString();
logger.info(String.format("%n%nUsing default security password: %s%n", password));
UserDetails userDetails = getUserDetails(password, passwordEncoder);
SecurityProperties.User user = properties.getUser();
if (user.isPasswordGenerated()) {
logger.info(String.format("%n%nUsing default security password: %s%n", user.getPassword()));
}
UserDetails userDetails = getUserDetails(user, passwordEncoder);
return new MapReactiveUserDetailsService(userDetails);
}
private UserDetails getUserDetails(String password,
private UserDetails getUserDetails(SecurityProperties.User user,
ObjectProvider<PasswordEncoder> passwordEncoder) {
String encodedPassword = passwordEncoder
.getIfAvailable(PasswordEncoderFactories::createDelegatingPasswordEncoder)
.encode(password);
return User.withUsername("user").password(encodedPassword).roles().build();
.encode(user.getPassword());
List<String> roles = user.getRoles();
return User.withUsername(user.getName()).password(encodedPassword)
.roles(roles.toArray(new String[roles.size()])).build();
}
}

View File

@ -18,6 +18,8 @@ package org.springframework.boot.autoconfigure.security.reactive;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.security.SecurityProperties;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;
import org.springframework.security.config.annotation.web.reactive.EnableWebFluxSecurity;
@ -35,6 +37,7 @@ import org.springframework.security.web.reactive.result.method.annotation.Authen
@Configuration
@ConditionalOnClass({ EnableWebFluxSecurity.class,
AuthenticationPrincipalArgumentResolver.class })
@EnableConfigurationProperties(SecurityProperties.class)
@Import({ WebFluxSecurityConfiguration.class,
ReactiveAuthenticationManagerConfiguration.class })
public class ReactiveSecurityAutoConfiguration {

View File

@ -150,7 +150,7 @@ public class SecurityAutoConfigurationTests {
this.context.refresh();
UserDetailsService manager = this.context.getBean(UserDetailsService.class);
assertThat(this.outputCapture.toString())
.contains("Using default security password:");
.contains("Using generated security password:");
assertThat(manager.loadUserByUsername("user")).isNotNull();
}
@ -167,7 +167,7 @@ public class SecurityAutoConfigurationTests {
assertThat(manager).isEqualTo(this.context.getBean(
TestAuthenticationManagerConfiguration.class).authenticationManager);
assertThat(this.outputCapture.toString())
.doesNotContain("Using default security password: ");
.doesNotContain("Using generated security password: ");
TestingAuthenticationToken token = new TestingAuthenticationToken("foo", "bar");
assertThat(manager.authenticate(token)).isNotNull();
}

View File

@ -66,7 +66,7 @@ public class SecurityFilterAutoConfigurationEarlyInitializationTests {
context.refresh();
int port = context.getWebServer().getPort();
String password = this.outputCapture.toString()
.split("Using default security password: ")[1].split("\n")[0].trim();
.split("Using generated security password: ")[1].split("\n")[0].trim();
new TestRestTemplate("user", password)
.getForEntity("http://localhost:" + port, Object.class);
// If early initialization occurred a ConverterNotFoundException is thrown

View File

@ -16,13 +16,11 @@
package org.springframework.boot.autoconfigure.security;
import java.util.Collections;
import org.junit.Before;
import org.junit.Test;
import org.springframework.boot.context.properties.bind.Bindable;
import org.springframework.boot.context.properties.bind.Binder;
import org.springframework.boot.context.properties.source.ConfigurationPropertySource;
import org.springframework.boot.context.properties.source.MapConfigurationPropertySource;
import static org.assertj.core.api.Assertions.assertThat;
@ -31,23 +29,55 @@ import static org.assertj.core.api.Assertions.assertThat;
* Tests for {@link SecurityProperties}.
*
* @author Dave Syer
* @author Madhura Bhave
*/
public class SecurityPropertiesTests {
private SecurityProperties security = new SecurityProperties();
private Binder binder;
private MapConfigurationPropertySource source = new MapConfigurationPropertySource();
@Before
public void setUp() throws Exception {
this.binder = new Binder(this.source);
}
@Test
public void testBinding() {
bind("spring.security.filter.order", "55");
public void filterOrderShouldBind() {
this.source.put("spring.security.filter.order", "55");
this.binder.bind("spring.security", Bindable.ofInstance(this.security));
assertThat(this.security.getFilter().getOrder()).isEqualTo(55);
}
private void bind(String name, String value) {
bind(new MapConfigurationPropertySource(Collections.singletonMap(name, value)));
@Test
public void userWhenNotConfiguredShouldUseDefaultNameAndGeneratedPassword() throws Exception {
SecurityProperties.User user = this.security.getUser();
assertThat(user.getName()).isEqualTo("user");
assertThat(user.getPassword()).isNotNull();
assertThat(user.isPasswordGenerated()).isTrue();
assertThat(user.getRoles()).isEmpty();
}
private void bind(ConfigurationPropertySource source) {
new Binder(source).bind("spring.security", Bindable.ofInstance(this.security));
@Test
public void userShouldBindProperly() throws Exception {
this.source.put("spring.security.user.name", "foo");
this.source.put("spring.security.user.password", "password");
this.source.put("spring.security.user.roles", "ADMIN,USER");
this.binder.bind("spring.security", Bindable.ofInstance(this.security));
SecurityProperties.User user = this.security.getUser();
assertThat(user.getName()).isEqualTo("foo");
assertThat(user.getPassword()).isEqualTo("password");
assertThat(user.isPasswordGenerated()).isFalse();
assertThat(user.getRoles()).containsExactly("ADMIN", "USER");
}
@Test
public void passwordAutogeneratedIfEmpty() {
this.source.put("spring.security.user.password", "");
this.binder.bind("spring.security", Bindable.ofInstance(this.security));
assertThat(this.security.getUser().isPasswordGenerated()).isTrue();
}
}

View File

@ -2852,13 +2852,16 @@ the following example:
[indent=0]
----
Using default security password: 78fa095d-3f4c-48b1-ad50-e24c31d5cf35
Using generated security password: 78fa095d-3f4c-48b1-ad50-e24c31d5cf35
----
NOTE: If you fine-tune your logging configuration, ensure that the
`org.springframework.boot.autoconfigure.security` category is set to log `INFO`-level
messages. Otherwise, the default password is not printed.
You can change the username and password by providing a `spring.security.user.name` and
`spring.security.user.password`.
The default security configuration is implemented in `SecurityAutoConfiguration` and in
the classes imported from there (`SpringBootWebSecurityConfiguration` for web security
and `AuthenticationManagerConfiguration` for authentication configuration, which is also
@ -2874,7 +2877,7 @@ Boot samples] to get you started with common use cases.
The basic features you get by default in a web application are:
* A `UserDetailsService` bean with in-memory store and a single user with a generated
password.
password (see `SecurityProperties.User` for the properties of the user).
* Form-based login or HTTP Basic security (depending on Content-Type) for the entire
application (including actuator endpoints if actuator is on the classpath).

View File

@ -18,10 +18,7 @@ package org.springframework.boot.test.autoconfigure.security;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.test.autoconfigure.web.servlet.MockMvcSecurityAutoConfiguration;
import org.springframework.context.annotation.Bean;
import org.springframework.security.access.annotation.Secured;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@ -33,12 +30,6 @@ import org.springframework.web.bind.annotation.RestController;
@SpringBootApplication
public class SecurityTestApplication {
@Bean
public InMemoryUserDetailsManager inMemoryUserDetailsManager() {
return new InMemoryUserDetailsManager(User.withDefaultPasswordEncoder()
.username("user").password("secret").roles("USER").build());
}
@RestController
static class MyController {

View File

@ -0,0 +1,3 @@
spring.security.user.name=user
spring.security.user.password=secret
spring.security.user.roles=USER

View File

@ -18,19 +18,10 @@ package sample.actuator.log4j2;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
@SpringBootApplication
public class SampleActuatorLog4J2Application {
@Bean
public InMemoryUserDetailsManager inMemoryUserDetailsManager() {
return new InMemoryUserDetailsManager(User.withDefaultPasswordEncoder()
.username("user").password("password").roles("USER").build());
}
public static void main(String[] args) throws Exception {
SpringApplication.run(SampleActuatorLog4J2Application.class, args);
}

View File

@ -1,2 +1,4 @@
spring.security.user.name=user
spring.security.user.password=password
management.endpoint.shutdown.enabled=true
management.endpoints.web.expose=*

View File

@ -21,9 +21,6 @@ import java.util.Map;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
@ -32,12 +29,6 @@ import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class SampleActuatorUiApplication {
@Bean
public InMemoryUserDetailsManager inMemoryUserDetailsManager() {
return new InMemoryUserDetailsManager(User.withDefaultPasswordEncoder()
.username("user").password("password").roles("USER").build());
}
@GetMapping("/")
public String home(Map<String, Object> model) {
model.put("message", "Hello World");

View File

@ -1,3 +1,5 @@
spring.security.user.name=user
spring.security.user.password=password
management.health.diskspace.enabled=false
management.endpoints.web.expose=*
management.jolokia.enabled=true

View File

@ -22,8 +22,6 @@ import org.springframework.boot.actuate.health.HealthIndicator;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
@SpringBootApplication
@EnableConfigurationProperties(ServiceProperties.class)
@ -33,12 +31,6 @@ public class SampleActuatorApplication {
SpringApplication.run(SampleActuatorApplication.class, args);
}
@Bean
public InMemoryUserDetailsManager inMemoryUserDetailsManager() {
return new InMemoryUserDetailsManager(User.withDefaultPasswordEncoder()
.username("user").password("password").roles("USER").build());
}
@Bean
public HealthIndicator helloHealthIndicator() {
return new HealthIndicator() {

View File

@ -1,5 +1,8 @@
service.name=Phil
spring.security.user.name=user
spring.security.user.password=password
# logging.file=/tmp/logs/app.log
# logging.level.org.springframework.security=DEBUG
management.server.address=127.0.0.1

View File

@ -19,9 +19,6 @@ package sample.secure.webflux;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.security.core.userdetails.MapReactiveUserDetailsService;
import org.springframework.security.core.userdetails.ReactiveUserDetailsService;
import org.springframework.security.core.userdetails.User;
import org.springframework.web.reactive.function.server.RouterFunction;
import org.springframework.web.reactive.function.server.ServerResponse;
@ -40,10 +37,4 @@ public class SampleSecureWebFluxApplication {
return route(POST("/echo"), echoHandler::echo);
}
@Bean
public ReactiveUserDetailsService userDetailsService() {
return new MapReactiveUserDetailsService(User.withDefaultPasswordEncoder()
.username("foo").password("password").roles("USER").build());
}
}

View File

@ -0,0 +1,2 @@
spring.security.user.name=user
spring.security.user.password=password

View File

@ -56,7 +56,7 @@ public class SampleSecureWebFluxApplicationTests {
public void userDefinedMappingsAccessibleOnLogin() {
this.webClient.get().uri("/").accept(MediaType.APPLICATION_JSON)
.header("Authorization", "basic " + getBasicAuth()).exchange()
.expectBody(String.class).isEqualTo("Hello foo");
.expectBody(String.class).isEqualTo("Hello user");
}
@Test
@ -67,7 +67,7 @@ public class SampleSecureWebFluxApplicationTests {
}
private String getBasicAuth() {
return new String(Base64.getEncoder().encode(("foo:password").getBytes()));
return new String(Base64.getEncoder().encode(("user:password").getBytes()));
}
}

View File

@ -20,14 +20,11 @@ import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.core.authority.AuthorityUtils;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
@EnableAutoConfiguration
@ComponentScan
@ -37,12 +34,6 @@ public class SampleSecureApplication implements CommandLineRunner {
@Autowired
private SampleService service;
@Bean
public InMemoryUserDetailsManager inMemoryUserDetailsManager() {
return new InMemoryUserDetailsManager(User.withDefaultPasswordEncoder()
.username("user").password("password").roles("USER").build());
}
@Override
public void run(String... args) throws Exception {
SecurityContextHolder.getContext()

View File

@ -1 +1,4 @@
# debug: true
# debug: true
spring.security.user.name=user
spring.security.user.password=password
spring.security.user.roles=USER

View File

@ -30,19 +30,11 @@ import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.boot.web.servlet.support.SpringBootServletInitializer;
import org.springframework.context.annotation.Bean;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
@SpringBootConfiguration
@EnableAutoConfiguration
public class SampleServletApplication extends SpringBootServletInitializer {
@Bean
public InMemoryUserDetailsManager inMemoryUserDetailsManager() {
return new InMemoryUserDetailsManager(User.withDefaultPasswordEncoder()
.username("user").password("password").roles("USER").build());
}
@SuppressWarnings("serial")
@Bean
public Servlet dispatcherServlet() {

View File

@ -0,0 +1,2 @@
spring.security.user.name=user
spring.security.user.password=password

View File

@ -20,9 +20,6 @@ import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.security.config.web.server.ServerHttpSecurity;
import org.springframework.security.core.userdetails.MapReactiveUserDetailsService;
import org.springframework.security.core.userdetails.ReactiveUserDetailsService;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.web.server.SecurityWebFilterChain;
import org.springframework.security.web.server.context.WebSessionServerSecurityContextRepository;
@ -33,12 +30,6 @@ public class SampleSessionWebFluxApplication {
SpringApplication.run(SampleSessionWebFluxApplication.class);
}
@Bean
public ReactiveUserDetailsService userDetailsRepository() {
return new MapReactiveUserDetailsService(User.withDefaultPasswordEncoder()
.username("user").password("password").roles("USER").build());
}
@Bean
public SecurityWebFilterChain springSecurityFilterChain(ServerHttpSecurity http) {
// @formatter:off

View File

@ -0,0 +1,2 @@
spring.security.user.name=user
spring.security.user.password=password

View File

@ -18,9 +18,6 @@ package sample.session;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
@SpringBootApplication
public class SampleSessionApplication {
@ -29,10 +26,4 @@ public class SampleSessionApplication {
SpringApplication.run(SampleSessionApplication.class);
}
@Bean
public InMemoryUserDetailsManager inMemoryUserDetailsManager() {
return new InMemoryUserDetailsManager(User.withDefaultPasswordEncoder()
.username("user").password("password").roles("USER").build());
}
}

View File

@ -1 +1,3 @@
spring.security.user.name=user
spring.security.user.password=password
management.endpoints.web.expose=*

View File

@ -21,12 +21,9 @@ import java.util.Map;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
@ -69,12 +66,6 @@ public class SampleWebSecureCustomApplication implements WebMvcConfigurer {
.failureUrl("/login?error").permitAll().and().logout().permitAll();
}
@Bean
public InMemoryUserDetailsManager InMemoryUserDetailsManager() {
return new InMemoryUserDetailsManager(User.withDefaultPasswordEncoder()
.username("user").password("user").roles("USER").build());
}
}
}

View File

@ -1,2 +1,5 @@
spring.thymeleaf.cache: false
logging.level.org.springframework.security: INFO
logging.level.org.springframework.security: INFO
spring.security.user.name=user
spring.security.user.password=password

View File

@ -83,7 +83,7 @@ public class SampleWebSecureCustomApplicationTests {
headers.setContentType(MediaType.APPLICATION_FORM_URLENCODED);
MultiValueMap<String, String> form = new LinkedMultiValueMap<>();
form.set("username", "user");
form.set("password", "user");
form.set("password", "password");
ResponseEntity<String> entity = this.restTemplate.exchange("/login",
HttpMethod.POST, new HttpEntity<>(form, headers), String.class);
assertThat(entity.getStatusCode()).isEqualTo(HttpStatus.FOUND);

View File

@ -22,12 +22,9 @@ import java.util.Map;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.security.StaticResourceRequest;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
@ -76,15 +73,6 @@ public class SampleWebSecureApplication implements WebMvcConfigurer {
// @formatter:on
}
@Bean
public InMemoryUserDetailsManager InMemoryUserDetailsManager() {
return new InMemoryUserDetailsManager(
User.withDefaultPasswordEncoder().username("admin").password("admin")
.roles("ADMIN", "USER").build(),
User.withDefaultPasswordEncoder().username("user").password("user")
.roles("USER").build());
}
}
}

View File

@ -1,4 +1,7 @@
spring.thymeleaf.cache: false
# demo only:
logging.level.org.springframework.security: INFO
logging.level.org.springframework.boot.actuate.audit.listener.AuditListener: DEBUG
logging.level.org.springframework.boot.actuate.audit.listener.AuditListener: DEBUG
spring.security.user.name=user
spring.security.user.password=password

View File

@ -83,7 +83,7 @@ public class SampleSecureApplicationTests {
headers.setContentType(MediaType.APPLICATION_FORM_URLENCODED);
MultiValueMap<String, String> form = new LinkedMultiValueMap<>();
form.set("username", "user");
form.set("password", "user");
form.set("password", "password");
ResponseEntity<String> entity = this.restTemplate.exchange("/login",
HttpMethod.POST, new HttpEntity<>(form, headers), String.class);
assertThat(entity.getStatusCode()).isEqualTo(HttpStatus.FOUND);