Как с помощью Spring Security перенаправить зарегистрированного пользователя на его главную страницу, а незарегистрированного пользователя на другую

Я делаю проект веб-приложения Spring в качестве финального проекта для школы. Мы используем SpringBoot с Hibernate и базой данных H2. Для аутентификации и авторизации мы используем Spring Security. Мы также используем модель View-Controller с репозиториями, сервисами и контроллерами. У меня есть начальная главная страница (with the URL "/"), которая отображается при открытии проекта. Как только вы войдете в систему, вы будете перенаправлены на другую главную страницу с URL-адресом ("/portadaUsuario") (я из Испании, поэтому на испанском языке много имен). Но если вы каким-то образом окажетесь на URL-адресе ("/") после входа в систему, вам будет показана та же главная страница, которая показана незарегистрированным пользователям с параметрами регистрации и входа в систему, которые очевидно неправильно.

Я знаю, что могу показывать разные HTML-элементы с тегами и элементами безопасности spring, но я уже построил свой проект на двух разных главных страницах, и я хотел бы сохранить его таким, если это возможно. Если это невозможно, сообщите мне, как мне поступить, чтобы отобразить разные элементы в одном файле HTML.

Вот методы моего WellcomeController

@Controller
public class PortadaController {

    @GetMapping({"/"})
    public String mostrarPortada() {
        return "portada";
    }

    @GetMapping("/portadaUser")
    public String mostrarPortadaUsuario() {
        return "/usuario/portada";
    }
}

Вот методы, которые аутентифицируют пользователей

@Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.userDetailsService(userDetailsService).passwordEncoder(passwordEncoder());
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
                .authorizeRequests()
                .antMatchers("/css/**","/js/**","/webjars/**", "/h2-console/**", "/", "/newUser/**").permitAll()
                        .antMatchers("/admin/**").hasAnyRole("ADMIN")
                        .anyRequest().authenticated()
                        .and()
                .formLogin()
                        .loginPage("/login")
                        .permitAll()
                        .successHandler(customSuccessHandler)
                        .defaultSuccessUrl("/portadaUser")
                        .and()
                .logout()
                        .logoutUrl("/logout")
                        .permitAll()
                        .logoutSuccessUrl("/")
                        .and()
                .exceptionHandling()
                        .accessDeniedPage("/acceso-denegado");


        http.csrf().disable();
        http.headers().frameOptions().disable();
        }

Я хочу, чтобы приложение обнаруживало, когда зарегистрированный пользователь запрашивает URL-адрес «/», и вместо этого перенаправляло его на /portadaUser.

0
0
59
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Протестировано в jsp + Spring 4.3.13 + Spring Security 4.2.11

1.проверено в jsp

"<%@ taglib prefix="sec" uri="http://www.springframework.org/security/tags" %>"

<script>
    <sec:authorize access="hasRole('ADMIN')">
        location.replace('/yourpage')
    </sec:authorize>
</script>  

2. зарегистрировался контроллер
SpringSecurityUtil.класс

 public class SpringSecurityUtil {

        public static boolean hasRole(String role) {
            Collection<GrantedAuthority> authorities = (Collection<GrantedAuthority>) SecurityContextHolder.getContext().getAuthentication().getAuthorities();
            boolean hasRole = false;
            for (GrantedAuthority authority : authorities) {
                if(authority.getAuthority().equals(role)) {
                    hasRole = true;
                    break;
                }
            }

            return hasRole;
        }

    }

HomeController.класс

@Controller
public class HomeController {

    @RequestMapping(value = "/", method = RequestMethod.GET)
    public String home(HttpServletResponse resp) {
        if(SpringSecurityUtil.hasRole("ADMIN"))
            //if has role send your page
        else
            //if has not role send your page
    }
}  

3. добавьте antMatchers в свой класс Spring Security Config.

antMatchers("/").hasAnyRole("ADMIN")

4. используйте @PreAuthority

@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled=true)
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
    ...
}

HomeController.класс

 @Controller
    public class HomeController {

        @PreAuthorize("hasAuthority('ADMIN')")
        @RequestMapping(value = "/", method = RequestMethod.GET)
        public String home() {
              //If this code starts, you have ADMIN privileges.
        }
    }  

увидеть больше Безопасность метода безопасности Spring

Ответ принят как подходящий

Предполагая, что у вас есть две страницы, одна для входа в систему (вход в систему), а другая для не входа в систему (не вход в систему), вы кодируете что-то вроде этого:

@GetMapping("/")
public String index(Principal principal, Model model) {
   return principal != null ? "signed-in-home" : "not-signed-in-home";
}

Подробнее о принципале читайте здесь - https://www.baeldung.com/get-user-in-spring-security

Другие вопросы по теме