Skip to content

Commit 046a1fc

Browse files
abimaelrsergiosjohnr
authored andcommitted
Update description of securityMatcher and multiple filter chains
Closes gh-14419
1 parent 3002a82 commit 046a1fc

File tree

1 file changed

+94
-0
lines changed
  • docs/modules/ROOT/pages/servlet/configuration

1 file changed

+94
-0
lines changed

docs/modules/ROOT/pages/servlet/configuration/java.adoc

Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -250,6 +250,100 @@ public class MultiHttpSecurityConfig {
250250
If the URL does not start with `/api/`, this configuration is used.
251251
This configuration is considered after `apiFilterChain`, since it has an `@Order` value after `1` (no `@Order` defaults to last).
252252

253+
To effectively manage security in an application where certain areas and the entire app need protection, we can employ multiple filter chains alongside the securityMatcher. This approach allows us to define distinct security configurations tailored to specific parts while also ensuring overall application security. The provided example showcases distinct configurations for URLs starting with "/account/", "/balance", "/loans-approval/", "/credit-cards-approval/", "/loans", "/cards", "/notices", "/contact", "/login", "/logout" and "/register". This approach allows tailored security settings for specific endpoints, enhancing overall application security and control.
254+
255+
[source,java]
256+
----
257+
@Configuration
258+
@EnableWebSecurity
259+
public class CustomSecurityFilterChainConfig {
260+
261+
@Bean <1>
262+
public UserDetailsService userDetailsService() {
263+
// ensure the passwords are encoded properly
264+
InMemoryUserDetailsManager manager = new InMemoryUserDetailsManager();
265+
manager.createUser(User.withDefaultPasswordEncoder().username("user").password("password").roles("USER").build());
266+
manager.createUser(User.withDefaultPasswordEncoder().username("admin").password("password").roles("USER", "ADMIN").build());
267+
return manager;
268+
}
269+
270+
@Bean
271+
@Order(1) <2>
272+
public SecurityFilterChain dashBoardFilterChain(HttpSecurity http) throws Exception {
273+
http
274+
.securityMatcher("/account/**", "/loans/**", "/cards/**") <3>
275+
.authorizeHttpRequests(authorizeRequests -> authorizeRequests
276+
.anyRequest().hasRole("USER") <4>
277+
)
278+
.httpBasic(Customizer.withDefaults());
279+
return http.build();
280+
}
281+
282+
@Bean
283+
@Order(2) <5>
284+
public SecurityFilterChain balanceFilterChain(HttpSecurity http) throws Exception {
285+
http
286+
.securityMatcher("/balance/**") <6>
287+
.authorizeHttpRequests(authorizeRequests -> authorizeRequests
288+
.anyRequest().hasAnyRole("USER", "ADMIN") <7>
289+
)
290+
.httpBasic(Customizer.withDefaults());
291+
return http.build();
292+
}
293+
294+
@Bean
295+
@Order(3) <8>
296+
public SecurityFilterChain approvalsFilterChain(HttpSecurity http) throws Exception {
297+
http
298+
.securityMatcher("/loans-approval/**", "/credit-cards-approval/**")<9>
299+
.authorizeHttpRequests(authorizeRequests -> authorizeRequests
300+
.anyRequest().hasRole("ADMIN") <10>
301+
)
302+
.httpBasic(Customizer.withDefaults());
303+
return http.build();
304+
}
305+
306+
@Bean
307+
@Order(4) <11>
308+
public SecurityFilterChain allowedFilterChain(HttpSecurity http) throws Exception {
309+
http
310+
.authorizeHttpRequests(authorizeRequests -> authorizeRequests
311+
.requestMatchers("/login","/logout","/notices", "/contact", "/register") <12>
312+
.permitAll() <13>
313+
)
314+
.formLogin(Customizer.withDefaults())
315+
.httpBasic(Customizer.withDefaults());
316+
return http.build();
317+
}
318+
319+
@Bean <14>
320+
public SecurityFilterChain defaultFilterChain(HttpSecurity http) throws Exception {
321+
http
322+
.authorizeHttpRequests(authorizeRequests -> authorizeRequests
323+
.anyRequest().authenticated() <15>
324+
)
325+
.formLogin(Customizer.withDefaults());
326+
return http.build();
327+
}
328+
}
329+
----
330+
<1> Begin by configuring authentication settings.
331+
<2> Define a SecurityFilterChain instance with @Order(1), which means that this chain will have the highest priority.
332+
<3> Specify that the http.securityMatcher applies only to "/account", "/loans", and "/cards" URLs.
333+
<4> Requires the user to have the role "USER" to access the URLs "/account", "/loans", and "/cards".
334+
<5> Next, create another SecurityFilterChain instance with @Order(2), this chain will be considered second.
335+
<6> Indicate that the http.securityMatcher applies only to "/balance" URL.
336+
<7> Requires the user to have the role "USER" or the role "ADMIN" to access the URL "/balance"
337+
<8> Next, create another SecurityFilterChain instance with @Order(3), this particular security filter chain will be the third in the order of execution.
338+
<9> The http.securityMatcher applies only to "/loans-approval" and "/credit-cards-approval" URLs.
339+
<10> The user must have the role "ADMIN" to access the URLs "/loans-approval" and "/credit-cards-approval"
340+
<11> Define a SecurityFilterChain instance with @Order(4) this chain will be considered fourth.
341+
<12> The http.securityMatcher applies only to "/login", "/logout", "/notices", "/contact", "/register" URLs.
342+
<13> Allows access to these specific URLs without authentication.
343+
<14> Lastly, create an additional SecurityFilterChain instance without an @Order annotation. This configuration will handle requests not covered by the other filter chains and will be processed last (no @Order defaults to last).
344+
<15> Requires the user to be authenticated to access any URL not explicitly allowed or protected by other filter chains.
345+
346+
253347
[[jc-custom-dsls]]
254348
== Custom DSLs
255349

0 commit comments

Comments
 (0)