Issue
I have a Spring Boot application with this mappging:
@GetMapping(value = { "/", })
public String home(Model model) {
}
and
localhot:8080
,localhost:8080/
,localhost:8080/.
,localhost:8080/..
redirects to /
but not
localhost:8080/...
and in the WebSecurityConfig
the only public matcher I have is this one: /
.
I would like to restrict the access for localhost:8080/.
and localhost:8080/..
here:
@Configuration
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
private final UserSecurityService userSecurityService;
private final Environment env;
private static final String SALT = "fd&l23j§sfs23#$1*(_)nof";
public WebSecurityConfig(UserSecurityService userSecurityService, Environment env) {
this.userSecurityService = userSecurityService;
this.env = env;
}
@Bean
public BCryptPasswordEncoder passwordEncoder() {
return new BCryptPasswordEncoder(12, new SecureRandom(SALT.getBytes()));
}
@Override
protected void configure(HttpSecurity http) throws Exception {
CharacterEncodingFilter encodingFilter = new CharacterEncodingFilter();
encodingFilter.setEncoding("UTF-8");
encodingFilter.setForceEncoding(true);
http.addFilterBefore(encodingFilter, CsrfFilter.class);
http.csrf().disable();
http
.authorizeRequests()
.antMatchers(publicMatchers()).permitAll()
.anyRequest().authenticated()
.and()
.formLogin()
.loginPage("/login.html")
.defaultSuccessUrl("/advertise.html")
.failureUrl("/login.html?error").permitAll()
.and()
.logout()
.permitAll()
.and()
.rememberMe()
.key("uniqueAndSecret");
}
@Autowired
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
auth
.userDetailsService(userSecurityService)
.passwordEncoder(passwordEncoder());
}
private String[] publicMatchers() {
final String[] PUBLIC_MATCHERS = {
"/webjars/**",
"/css/**",
"/fonts/**",
"/images/**",
"/img/**",
"/js/**",
"/home.html",
"/links/**",
"/links.html",
"/favicon.ico",
"/forgotmypassword.html",
"/directory/**",
"/",
"/error/**/*",
"/h2-console/**",
ForgotMyPasswordController.FORGOT_PASSWORD_URL_MAPPING,
ForgotMyPasswordController.CHANGE_PASSWORD_PATH
};
return PUBLIC_MATCHERS;
}
}
Solution
I have made a simple example similar to yours. I am testing with curl (not a web browser) and this is the result:
localhost:8080/.
Internal server error.
This exception is thrown in the server: org.springframework.security.web.firewall.RequestRejectedException: The request was rejected because the URL was not normalized.
localhost:8080/..
Bad request
It seems that the embedded tomcat gives you that response. I tried adding a Global error controller and I could get the error in spring
localhost:8080/...
Endpoint not found
This is exepcted as I don't have any mapping for such endpoint "/..."
I think that your browser is actually requesting for localhost:8080/
when you type localhost:8080/.
or localhost:8080/..
Your spring boot app is not redirecting
Answered By - pepevalbe
Answer Checked By - Candace Johnson (JavaFixing Volunteer)