Подтвердить что ты не робот

Программное использование Spring Безопасность

Я использую Wicket с проектом Wicket Auth для моего уровня представления, и поэтому я интегрировал его с Spring Security. Это метод, который Wicket вызывает для аутентификации для меня:

@Override
public boolean authenticate(String username, String password) {
    try {
        Authentication request = new UsernamePasswordAuthenticationToken(
                username, password);
        Authentication result = authenticationManager.authenticate(request);
        SecurityContextHolder.getContext().setAuthentication(result);
    } catch (AuthenticationException e) {
        return false;
    }
    return true;
}

Содержимое (внутри) моей конфигурации безопасности Spring безопасности:

<http path-type="regex">
    <form-login login-page="/signin"/>
<logout logout-url="/logout" />
</http>
<global-method-security secured-annotations="enabled" />
<authentication-manager alias="authenticationManager"/>
<authentication-provider user-service-ref="userService">
    <password-encoder ref="bcryptpasswordencoder" />
</authentication-provider>

Раздел 2.3.6. Фиксация защиты от прикрепления сеанса в справочной документации гласит:

Атаки фиксации сеанса - потенциальный риск, когда это возможно для злонамеренного злоумышленника создать сеанса путем доступа к сайту, затем убедить другого пользователя войти в систему с той же сессии (отправив им ссылка, содержащая идентификатор сеанса как параметр, например). SpringБезопасность защищает автоматически, создавая новый когда пользователь входит в систему. Если вы не требуют такой защиты, или противоречит некоторым другим требованиям, вы можете контролировать поведение, используя защита от фиксации сеанса атрибут, который имеет три Параметры:

  • migrateSession - создает новый сеанс и копирует существующие атрибуты сеанса для нового сеанса. Это значение по умолчанию.
  • none - ничего не делайте. Исходный сеанс будет сохранен.
  • newSession - создайте новый "чистый" сеанс, не копируя существующие данные сеанса.

Аутентификация работает, но я, поскольку я довольно новичок в Spring безопасности У меня есть некоторые вопросы, на которые мне тоже нужны ответы:

  • Обычно для входа в систему я бы установил POST-информацию об аутентификации в j_spring_security_check и позволил Spring Security выполнить фактический код аутентификации. Я хотел бы иметь защиту от атак сеансовой фиксации, получу ли это, когда я выполню программный логин, как и я? А если нет, что мне нужно сделать, чтобы получить его?
  • Как выполнить программный выход из системы?
  • Как я буду использовать программный вход и выход из системы, как отключить Spring от перехвата этих URL?

Update: Для защиты от атак с фиксацией сеанса кажется, что мне нужно вызвать метод в классе SessionUtils с сигнатурой startNewSessionIfRequired(HttpServletRequest request, boolean migrateAttributes, SessionRegistry sessionRegistry).

Как мне получить экземпляр SessionRegistry, который мне нужно передать? Я не могу найти способ создать идентификатор псевдонима для него или как получить его идентификатор или имя.

4b9b3361

Ответ 1

Возможно, это не полный ответ на ваши вопросы, но, возможно, это может вам помочь.

Вызывается код, когда вы НЕ используете программный логин, но стандартный файл можно найти здесь:

org.springframework.security.ui.webapp.AuthenticationProcessingFilter

Я думаю, вы были вдохновлены этим в своем коде. Это выглядит очень похоже.

Аналогичным образом код, выполняемый при доступе к /j_spring_security_logout в стандартном подходе, можно найти здесь:

org.springframework.security.ui.logout.LogoutFilter

LogoutFilter вызывает несколько обработчиков. Обработчик, который мы используем, называется: org.springframework.security.ui.logout.SecurityContextLogoutHandler, поэтому вы можете называть тот же код в своем подходе.

Ответ 2

Вы действительно будете открыты для атак сеансовой фиксации. Чтобы исправить это, вы снова можете "вдохновиться" кодом Spring. Для создания нового сеанса вам, очевидно, потребуется доступ к httpsession, поэтому вам может понадобиться сделать рефакторинг.

Если вы видите метод SessionUtils. startNewSessionIfRequired.

Это перенесет аутентификацию на новый сеанс. Вы могли бы вызвать этот метод напрямую или просто немного реорганизовать код.

Что касается программного выхода из системы, вы не можете ошибиться, просто позвонив session.invalidate(), когда вам нужно зарегистрировать человека. Это сделает все необходимое с точки зрения общей безопасности, но имейте в виду, хотя вам может понадобиться очистить некоторые вещи на сеансе. Если у вас очень сложный набор фильтров и т.д., И вам нужно убедиться, что пользователь вышел из системы для остальной части запроса, вы можете добавить:

SecurityContextHolder.getContext().setAuthentication(null);

Что касается перехвата URL-адреса, вы можете просто установить их на что-то неиспользуемое и игнорировать его! Я не уверен, что вы можете отключить перехват в конфигурации - если вы действительно хотите его удалить, посмотрите на AuthenticationProcessingFilter - вы можете настроить это. Если вы это сделаете, вам придется вручную настроить Spring xml безопасности и не использовать предоставленные пространства имен. Это не слишком сложно - посмотрите на некоторые старые документы, и вы увидите, как это сделать.

Надеюсь, это поможет!

Ответ 3

1) Программный выход

  • вызов HttpServletRequest.getSession(false).invalidate
  • вызов SecurityContextHolder.clearContext()

2) Скажите Spring Безопасность НЕ перехватывать определенные URL-адреса, этот вид зависит от того, как настроено пространство вашего приложения. Если все ваши страницы (кроме/logIn и /logout ) проживают в контексте /myApp, вы можете сделать это:

<http ....>
  <intercept-url pattern="/myApp/**" ..>
 ....
</http>

Ответ 4

У меня возникла проблема с программным входом. Я вызвал все методы authenticationManager.authenticate(...) и SecurityContextHolder.getContext().setAuthentication(...), но имел некоторые проблемы с сеансом. Мне нужно было добавить следующие строки для правильного управления сеансом:

HttpSession session = request.getSession();
session.setAttribute("SPRING_SECURITY_CONTEXT", SecurityContextHolder.getContext());

Это не было ясно из приведенного выше примера кода. Подробнее см. http://forum.springsource.org/showthread.php?t=69761

Ответ 5

Чтобы выполнить программный выход из системы, также можно выполнить команду org.springframework.security.core.AuthenticationException. Например, SessionAuthenticationException. В этом случае ExceptionTranslationFilter инициирует выход из системы.

Ответ 6

Вы можете попробовать это

    try {
        HttpSession session = request.getSession(false);
        if (session != null) {
            session.invalidate();
        }

        SecurityContextHolder.clearContext();

    } catch (Exception e) {
        logger.log(LogLevel.INFO, "Problem logging out.");
    }