成功登录后的Spring引导安全重定向-未定义



我遵循了春季启动安全教程,但最终结果有一个问题,包括在成功登录后,浏览器被重定向到/undefined

我甚至克隆了教程中引用的代码,认为我输入了错误的东西,或者忘记添加组件或其他东西。不,同样的问题也存在。

在Stackoverflow上搜索我发现你需要在WebSecurityConfigurerAdapterconfigure方法中定义默认的成功URL,如下所示:

.defaultSuccessUrl("/")

但仍然没有去。访问受保护的资源会导致登录页面,在成功登录后,我不会被重定向到受保护的资源。我到达了"/未定义"页面。然而,强迫成功是有效的:

.defaultSuccessUrl("/", true)

…但这不是我需要的,因为在成功登录后,用户应该被重定向到(最初)请求的安全资源。


以下是项目的相关部分:

WebSecurityConfig:

package ro.rinea.andrei.Security;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
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.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
@Configuration
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.authorizeRequests()
                .antMatchers("/").permitAll()
                .anyRequest().authenticated()
                .and()
            .formLogin()
                .loginPage("/login")
                .defaultSuccessUrl("/")
                .permitAll()
                .and()
            .logout()
                .permitAll();
    }
    @Autowired
    public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
        auth.inMemoryAuthentication()
            .withUser("user").password("password").roles("USER");
    }
}

控制器:

package ro.rinea.andrei.Controllers;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class WebController {
    @RequestMapping("/")
    public String index() {
        return "index";
    }
    @RequestMapping("/salut")
    public String salut() {
        return "salut";
    }
    @RequestMapping("/login")
    public String login() {
        return "login";
    }
}

index, loginsalut定义了视图(如果需要,我会添加它们的内容)

和构建。gradle文件:

buildscript {
    ext {
        springBootVersion = '1.4.0.RELEASE'
    }
    repositories {
        mavenCentral()
    }
    dependencies {
        classpath("org.springframework.boot:spring-boot-gradle-plugin:${springBootVersion}")
    }
}
apply plugin: 'java'
apply plugin: 'idea'
apply plugin: 'spring-boot'
jar {
    baseName = 'tstBut'
    version = '0.0.1-SNAPSHOT'
}
sourceCompatibility = 1.8
targetCompatibility = 1.8
repositories {
    mavenCentral()
}

dependencies {
    compile('org.springframework.boot:spring-boot-devtools')
    compile('org.springframework.boot:spring-boot-starter-jdbc')
    compile('org.springframework.boot:spring-boot-starter-jersey')
    compile('org.springframework.boot:spring-boot-starter-mobile')
    compile('org.springframework.boot:spring-boot-starter-thymeleaf')
    compile('org.springframework.boot:spring-boot-starter-validation')
    compile('org.springframework.boot:spring-boot-starter-web')
    compile('org.springframework.boot:spring-boot-starter-web-services')
    compile('org.springframework.boot:spring-boot-starter-security')
    runtime('org.postgresql:postgresql')
    testCompile('org.springframework.boot:spring-boot-starter-test')
    testCompile('org.springframework.restdocs:spring-restdocs-mockmvc')
}

你可以像这样添加一个successHandler来重定向:

private RedirectStrategy redirectStrategy = new DefaultRedirectStrategy();
   ...
   .formLogin()
   .loginPage("/login")
   .successHandler(new AuthenticationSuccessHandler() {
    @Override
    public void onAuthenticationSuccess(HttpServletRequest request, HttpServletResponse response,
            Authentication authentication) throws IOException, ServletException {
        redirectStrategy.sendRedirect(request, response, "/");
    }
})

我有同样的问题,这是我使用的一个解决方案。首先为根目录"/"创建一个未受保护的映射

@RequestMapping(value = { "/" }, method = RequestMethod.GET)
public ModelAndView projectBase() {
    return new ModelAndView("redirect:/home");
}

让它重定向到你最初想要用户去的地方比如home,例如

@RequestMapping(value = { "/home" }, method = RequestMethod.GET)
public ModelAndView getHome() {
    ModelAndView model = new ModelAndView("account/home");
    model.addObject("user", userFacade.getJsonForUser(userFacade.getUserForClient()));
    return model;
}

确保根url在你的安全配置中是打开的,比如…

 http.
    authorizeRequests()
    .antMatchers("/").permitAll()

将会发生的是,现在它将击中根目录/,并重定向到home,这是受限的,并将它们发送到返回url为home的loginpage。当他们第一次登录

时,它会正确地写为/home

由于某些原因,spring security不尊重默认的成功url,这可能是web服务器的配置问题导致的。在我的本地机器上我没有这个问题,但在其他一些机器上我有。该解决方案在这两个地方都有效,因为您总是以returnUrl.

结束。

最新更新