Выход из системы Grails Spring Security Rest

Я использую Grails 3.1.4 вместе с подключаемым модулем Spring Security Rest 2.0.0.M2 для реализации одностраничного приложения с AngularJS. Вход и проверка работают отлично, но когда я вызываю выход, я получаю ошибку 404.

При отладке получаю исключение в плагине RestLogoutFilter:

try {
    log.debug "Trying to remove the token"
    tokenStorageService.removeToken accessToken.accessToken
} catch (TokenNotFoundException tnfe) {
    servletResponse.sendError HttpServletResponse.SC_NOT_FOUND, "Token not found"
}

Исключение:

grails.plugin.springsecurity.rest.token.storage.TokenNotFoundException: 
Token eyJh... cannot be removed as this is a stateless implementation

Вызов

tokenStorageService.loadUserByToken(accessToken.accessToken)

работает, значит токен точно есть в tokenStorage.

Моя конфигурация безопасности Spring

grails.plugin.springsecurity.userLookup.userDomainClassName = 'myapp.User'
grails.plugin.springsecurity.userLookup.authorityJoinClassName = 'myapp.UserRole'
grails.plugin.springsecurity.authority.className = 'myapp.Role'
grails.plugin.springsecurity.userLookup.usernamePropertyName='email'
grails.plugin.springsecurity.rest.login.usernamePropertyName='email'
grails.plugin.springsecurity.rest.token.storage.gorm.usernamePropertyName='email'
grails.plugin.springsecurity.rest.logout.endpointUrl = '/api/logout'
grails.plugin.springsecurity.controllerAnnotations.staticRules = [
        [pattern: '/',               access: ['permitAll']],
        [pattern: '/error',          access: ['permitAll']],
        [pattern: '/index',          access: ['permitAll']],
        [pattern: '/index.gsp',      access: ['permitAll']],
        [pattern: '/shutdown',       access: ['permitAll']],
        [pattern: '/assets/**',      access: ['permitAll']],
        [pattern: '/**/js/**',       access: ['permitAll']],
        [pattern: '/**/css/**',      access: ['permitAll']],
        [pattern: '/**/images/**',   access: ['permitAll']],
        [pattern: '/**/favicon.ico', access: ['permitAll']],
        [pattern: '/api/logout',     access: ['isAuthenticated()']]
]

grails.plugin.springsecurity.filterChain.chainMap = [
        [pattern: '/assets/**',      filters: 'none'],
        [pattern: '/**/js/**',       filters: 'none'],
        [pattern: '/**/css/**',      filters: 'none'],
        [pattern: '/**/images/**',   filters: 'none'],
        [pattern: '/**/favicon.ico', filters: 'none'],
        [pattern: '/api/**',       filters: 'JOINED_FILTERS,-anonymousAuthenticationFilter,-exceptionTranslationFilter,-authenticationProcessingFilter,-securityContextPersistenceFilter,-rememberMeAuthenticationFilter']
]

Есть ли ошибка в моей конфигурации или что-то еще не так?


person Tobi    schedule 26.03.2016    source источник


Ответы (1)


Ответ нашел через несколько минут после того, как задал вопрос.

Spring Security Rest документация по плагину указывает:

Выход из системы невозможен при использовании токенов JWT (стратегия по умолчанию), поскольку на сервере не сохраняется состояние. Если вы все еще хотите выйти из системы, вы можете предоставить свою собственную реализацию, создав подкласс JwtTokenStorageService и переопределив методы storeToken и removeToken. Затем зарегистрируйте свою реализацию в resources.groovy как tokenStorageService.

Однако более рациональным подходом было бы просто удалить токен из клиента (например, из локального хранилища браузера) и дать истечение срока действия токенов (срок их действия и так истечет, в отличие от других хранилищ, таких как Memcached или Redis, где они обновляются при каждом доступе). .

Таким образом, достаточно просто удалить токен на клиенте, если он использует JWT для авторизации.

person Tobi    schedule 26.03.2016
comment
Есть ли у вас какие-либо учебные пособия, которые показывают, как реализовать первое предложение; Если вы все еще хотите выйти из системы, вы можете предоставить свою собственную реализацию, создав подкласс JwtTokenStorageService и переопределив методы storeToken и removeToken. Затем зарегистрируйте свою реализацию в resources.groovy как tokenStorageService. - person Pila; 05.04.2018
comment
Нет, не пробовал, но основная идея проста. Вы создаете класс, подобный CustomJwtTokenStorageService, и наследуете его от JwtTokenStorageService. Затем вы реализуете некоторый механизм хранения и удаления и регистрируете новую службу в resources.groovy, как описано здесь docs.grails.org/latest/guide/spring.html . Важно понимать, что ваш токен JWT на самом деле не сохраняется на вашем сервере, поэтому в этом нет необходимости, чтобы реализовать механизм выхода таким образом, и удаления токена на клиенте должно быть достаточно. - person Tobi; 05.04.2018