Директива Spring security «forward:» не может пересылать в форму входа - PullRequest
9 голосов
/ 28 января 2011

После того, как пользователь создает свою учетную запись, я хочу автоматически войти в систему этого пользователя.

У меня стандартные логины форм, обрабатываемые фильтром Springs на /postlogin. Если я перехожу на http://localhost/postlogin, он пытается войти в систему (не удается, потому что я не включил параметры записи), но делает правильную попытку.

Но если я хочу войти в систему пользователя программно и попытаться вернуться с контроллера: «forward: / postlogin» я получаю 404.

Я предполагаю, что директива forward: не проходит через фильтры, поэтому UsernamePasswordAuthenticationFilter не обрабатывается.

Как вручную запрограммировать вход в систему? Я хочу сделать это после того, как пользователь создаст новую учетную запись (они должны войти в эту учетную запись сразу после завершения регистрации).

Ответы [ 3 ]

17 голосов
/ 28 января 2011

Я неверно прочитал другое руководство и понял, что правильный способ обработки этого заключается в следующем:

1) Установите токен аутентификации вручную на SecurityContextHolder

    UsernamePasswordWithAttributesAuthenticationToken authenticationToken = new UsernamePasswordAuthenticationToken( loadUserByUsername(username), password, authorities );
    SecurityContextHolder.getContext().setAuthentication(authenticationToken);

2) Не визуализируйте страницу на этом этапе или используйте директиву forward :.Вы должны использовать директиву redirect:

return "redirect:/accountcreated";

Если вы отобразите страницу, страница будет нормально загружаться, но объект сеанса будет утерян, потому что будет создан новый j_session_id, но он не попадет в браузерmid-request и следующий запрос будут использовать старый j_session_id, теряя новый объект сеанса и аутентификацию.

Использование директивы forward: обойдёт фильтры аутентификации, не очень хорошо.

Но перенаправление:приводит к тому, что обновленная информация о сеансе попадает в браузер.

4 голосов
/ 02 ноября 2011

Новая функция фильтрации в Servlet 2.4 в основном снимает ограничение, заключающееся в том, что фильтры могут работать только в потоке запросов до и после фактической обработки запроса сервером приложений. Вместо этого фильтры Servlet 2.4 теперь могут взаимодействовать с диспетчером запросов в каждой точке отправки. Это означает, что когда веб-ресурс направляет запрос другому ресурсу (например, сервлету, перенаправляющему запрос на страницу JSP в том же приложении), фильтр может работать до того, как запрос будет обработан целевым ресурсом. Это также означает, что если веб-ресурс включает выходные данные или функцию из других веб-ресурсов (например, страницы JSP, включающей в себя выходные данные нескольких других страниц JSP), фильтры Servlet 2.4 могут работать до и после каждого из включенных ресурсов. ,

Чтобы включить эту функцию, вам нужно:

web.xml

<filter>   
    <filter-name>springSecurityFilterChain</filter-name>   
    <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class> 
</filter>  
<filter-mapping>   
    <filter-name>springSecurityFilterChain</filter-name>   
    <url-pattern>/<strike>*</strike></url-pattern>
    <dispatcher>REQUEST</dispatcher>
    <dispatcher>FORWARD</dispatcher>
</filter-mapping>

RegistrationController

return "forward:/login?j_username=" + registrationModel.getUserEmail()
    + "&j_password=" + registrationModel.getPassword();
2 голосов
/ 02 марта 2015

Аутентификация Spring через REST (Джерси)

Просто для иллюстрации @ ответа Дэвида (максимально упрощенного):

@POST
@Path("login")
public Response login(@FormParam("login") String login, @FormParam("pass") String pass)
{
    if (yourCheck(login, pass))
    {
        List<GrantedAuthority> authorities = new ArrayList<GrantedAuthority>();
        authorities.add(new SimpleGrantedAuthority("ROLE_USER"));
        Authentication auth = new UsernamePasswordAuthenticationToken(login, pass, authorities);
        SecurityContextHolder.getContext().setAuthentication(auth);

        // IMPORTANT: Do not pass any data in the response body

        // show empty 200 page (suitable for REST clients)
        return Response.ok().build();
        // or redirect to your home page (for web UI)
        return Response.temporaryRedirect(new URI("/homepage/")).build();
    }
    else
    {
        return Response.status(Status.UNAUTHORIZED).build();
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...