Đăng nhập biểu mẫu bảo mật mùa xuân

1. Giới thiệu

Bài viết này sẽ tập trung vào Đăng nhập với Spring Security . Chúng tôi sẽ xây dựng dựa trên ví dụ Spring MVC đơn giản trước đó, vì đó là một phần cần thiết của việc thiết lập ứng dụng web cùng với cơ chế đăng nhập.

2. Sự phụ thuộc của Maven

Khi làm việc với Spring Boot, trình khởi động spring-boot-starter-security sẽ tự động bao gồm tất cả các phần phụ thuộc như spring-security-core , spring-security-webspring-security-config trong số những phần khác:

 org.springframework.boot spring-boot-starter-security 2.3.3.RELEASE 

Trong trường hợp chúng tôi không sử dụng Spring Boot, vui lòng xem bài viết Spring Security with Maven, mô tả cách thêm tất cả các phụ thuộc bắt buộc. Cả hai tiêu chuẩn spring-security-webspring-security-config sẽ được yêu cầu.

3. Cấu hình Java bảo mật mùa xuân

Hãy bắt đầu bằng cách tạo một lớp cấu hình Spring Security mở rộng WebSecurityConfigurerAdapter.

Bằng cách thêm @EnableWebSecurity , chúng tôi nhận được hỗ trợ tích hợp Spring Security và MVC:

@Configuration @EnableWebSecurity public class SecSecurityConfig extends WebSecurityConfigurerAdapter { @Override protected void configure(final AuthenticationManagerBuilder auth) throws Exception { // authentication manager (see below) } @Override protected void configure(final HttpSecurity http) throws Exception { // http builder configurations for authorize requests and form login (see below) } }

Trong ví dụ này, chúng tôi đã sử dụng xác thực trong bộ nhớ và xác định 3 người dùng.

Tiếp theo, chúng tôi đi qua các phần tử chúng tôi đã sử dụng để tạo cấu hình đăng nhập biểu mẫu.

Trước tiên, hãy xây dựng Trình quản lý xác thực của chúng tôi.

3.1. Trình quản lý xác thực

Nhà cung cấp xác thực được hỗ trợ bởi một triển khai trong bộ nhớ đơn giản - đặc biệt là InMemoryUserDetailsManager . Điều này rất hữu ích cho việc tạo mẫu nhanh khi chưa cần thiết một cơ chế bền bỉ đầy đủ:

protected void configure(final AuthenticationManagerBuilder auth) throws Exception { auth.inMemoryAuthentication() .withUser("user1").password(passwordEncoder().encode("user1Pass")).roles("USER") .and() .withUser("user2").password(passwordEncoder().encode("user2Pass")).roles("USER") .and() .withUser("admin").password(passwordEncoder().encode("adminPass")).roles("ADMIN"); }

Ở đây, chúng tôi định cấu hình ba người dùng với tên người dùng, mật khẩu và vai trò được mã hóa cứng.

Bắt đầu với Spring 5, chúng ta cũng phải xác định một bộ mã hóa mật khẩu . Trong ví dụ của chúng tôi, chúng tôi đã sử dụng BCryptPasswordEncoder:

@Bean public PasswordEncoder passwordEncoder() { return new BCryptPasswordEncoder(); }

Tiếp theo, hãy cấu hình HttpSecurity.

3.2. Cấu hình để cho phép yêu cầu

Chúng tôi bắt đầu bằng cách thực hiện các cấu hình cần thiết để Ủy quyền Yêu cầu.

Ở đây, chúng tôi cho phép truy cập / đăng nhập ẩn danh để người dùng có thể xác thực. Hạn chế / quản trị viên đối với vai trò QUẢN TRỊ và đảm bảo mọi thứ khác:

@Override protected void configure(final HttpSecurity http) throws Exception { http .csrf().disable() .authorizeRequests() .antMatchers("/admin/**").hasRole("ADMIN") .antMatchers("/anonymous*").anonymous() .antMatchers("/login*").permitAll() .anyRequest().authenticated() .and() // ... }

Lưu ý rằng thứ tự của các phần tử antMatchers () là rất quan trọng - các quy tắc cụ thể hơn cần đến trước, sau đó là các quy tắc chung hơn .

3.3. Cấu hình cho Đăng nhập Biểu mẫu

Tiếp theo, chúng tôi mở rộng cấu hình ở trên để đăng nhập và đăng xuất biểu mẫu:

@Override protected void configure(final HttpSecurity http) throws Exception { http // ... .and() .formLogin() .loginPage("/login.html") .loginProcessingUrl("/perform_login") .defaultSuccessUrl("/homepage.html", true) .failureUrl("/login.html?error=true") .failureHandler(authenticationFailureHandler()) .and() .logout() .logoutUrl("/perform_logout") .deleteCookies("JSESSIONID") .logoutSuccessHandler(logoutSuccessHandler()); }
  • loginPage () - trang đăng nhập tùy chỉnh
  • loginProcessingUrl () - URL để gửi tên người dùng và mật khẩu đến
  • defaultSuccessUrl () - trang đích sau khi đăng nhập thành công
  • failUrl () - trang đích sau khi đăng nhập không thành công
  • logoutUrl () - đăng xuất tùy chỉnh

4. Thêm Spring Security vào Ứng dụng Web

Để sử dụng cấu hình Spring Security được xác định ở trên, chúng ta cần đính kèm nó vào ứng dụng web.

Chúng tôi sẽ sử dụng WebApplicationInitializer , vì vậy chúng tôi không cần cung cấp bất kỳ web.xml nào :

public class AppInitializer implements WebApplicationInitializer { @Override public void onStartup(ServletContext sc) { AnnotationConfigWebApplicationContext root = new AnnotationConfigWebApplicationContext(); root.register(SecSecurityConfig.class); sc.addListener(new ContextLoaderListener(root)); sc.addFilter("securityFilter", new DelegatingFilterProxy("springSecurityFilterChain")) .addMappingForUrlPatterns(null, false, "/*"); } }

Lưu ý rằng trình khởi tạo này không cần thiết nếu chúng ta đang sử dụng ứng dụng Spring Boot. Hãy xem bài viết của chúng tôi về cấu hình tự động bảo mật Spring Boot để biết thêm chi tiết về cách cấu hình bảo mật được tải trong Spring Boot.

5. Cấu hình XML bảo mật mùa xuân

Hãy cũng xem xét cấu hình XML tương ứng.

Dự án tổng thể đang sử dụng cấu hình Java, vì vậy chúng tôi cần nhập tệp cấu hình XML qua lớp Java @Configuration :

@Configuration @ImportResource({ "classpath:webSecurityConfig.xml" }) public class SecSecurityConfig { public SecSecurityConfig() { super(); } }

Và cấu hình XML bảo mật mùa xuân - webSecurityConfig.xml :

6. Web.xml

Trước khi giới thiệu Spring 4 , chúng tôi đã từng định cấu hình Spring Security trong web.xml - chỉ một bộ lọc bổ sung được thêm vào Spring MVC web.xml chuẩn :

Spring Secured Application     springSecurityFilterChain org.springframework.web.filter.DelegatingFilterProxy   springSecurityFilterChain /* 

Bộ lọc - DelegateFilterProxy - chỉ cần ủy quyền cho một bean do Spring quản lý - FilterChainProxy - mà bản thân nó có thể hưởng lợi từ việc quản lý toàn bộ vòng đời của Spring bean và như vậy.

7. Biểu mẫu đăng nhập

Trang biểu mẫu đăng nhập sẽ được đăng ký với Spring MVC bằng cách sử dụng cơ chế đơn giản để ánh xạ tên lượt xem với URL mà không cần bộ điều khiển rõ ràng ở giữa:

registry.addViewController("/login.html");

This, of course, corresponds to the login.jsp:


    
User:
Password:

The Spring Login form has the following relevant artifacts:

  • login – the URL where the form is POSTed to trigger the authentication process
  • username – the username
  • password – the password

8. Further Configuring Spring Login

We briefly discussed a few configurations of the login mechanism when we introduced the Spring Security Configuration above – let's go into some detail now.

One reason to override most of the defaults in Spring Security is to hide the fact that the application is secured with Spring Security and minimize the information a potential attacker knows about the application.

Fully configured, the login element looks like this:

@Override protected void configure(HttpSecurity http) throws Exception { http.formLogin() .loginPage("/login.html") .loginProcessingUrl("/perform_login") .defaultSuccessUrl("/homepage.html",true) .failureUrl("/login.html?error=true") }

Or the corresponding XML configuration:

8.1. The Login Page

Next, let's see how we can configure a custom login page using the loginPage() method:

http.formLogin() .loginPage("/login.html")

Or, via XML configuration:

login-page='/login.html'

If we don't specify this, Spring Security will generate a very basic Login Form at the /login URL.

8.2. The POST URL for Login

The default URL where the Spring Login will POST to trigger the authentication process is /login which used to be /j_spring_security_check before Spring Security 4.

We can use the loginProcessingUrl method to override this URL:

http.formLogin() .loginProcessingUrl("/perform_login")

Or, via XML configuration:

login-processing-url="/perform_login"

A good reason to override this default URL is to hide the fact that the application is actually secured with Spring Security – that information should not be available externally.

8.3. The Landing Page on Success

After a successful login process, the user is redirected to a page – which by default is the root of the web application.

We can override this via the defaultSuccessUrl() method:

http.formLogin() .defaultSuccessUrl("/homepage.html")

Or with XML configuration:

default-target-url="/homepage.html"

In case the always-use-default-target is set to true, then the user is always redirected to this page. If that attribute is set to false, then the user will be redirected to the previous page they wanted to visit before being prompted to authenticate.

8.4. The Landing Page on Failure

Same as with the Login Page, the Login Failure Page is autogenerated by Spring Security at /login?error by default.

To override this, we can use the failureUrl() method:

http.formLogin() .failureUrl("/login.html?error=true")

Or with XML:

authentication-failure-url="/login.html?error=true"

9. Conclusion

Trong Ví dụ đăng nhập mùa xuân này , chúng tôi đã định cấu hình một quy trình xác thực đơn giản - chúng tôi đã thảo luận về Biểu mẫu đăng nhập bảo mật mùa xuân, Cấu hình bảo mật và một số tùy chỉnh nâng cao hơn có sẵn.

Việc triển khai hướng dẫn Đăng nhập mùa xuân này có thể được tìm thấy trong dự án GitHub - đây là một dự án dựa trên Eclipse, vì vậy nó sẽ dễ dàng nhập và chạy như nó vốn có.

Khi dự án chạy cục bộ, HTML mẫu có thể được truy cập tại:

//localhost:8080/spring-security-mvc-login/login.html