У меня есть внутренний сервер (Java/Spring/Spring Security). В настоящее время, когда пользователи из мобильного приложения входят в систему, они просто отправляют свое имя пользователя/пароль, а Spring Security создает сеанс и назначает его запросу с JSESSIONID.
Теперь у нас также будет кнопка в мобильном приложении «Войти через Facebook». Вот как я понимаю, как это будет работать.
- мобильное приложение использует facebook SDK для получения «access_token»
- мобильное приложение извлекает профиль пользователя из facebook (имя, фамилия, адрес электронной почты и т. д.)
- мобильные проверки (против МОЕГО сервера), если имя пользователя уникально
- Если имя пользователя уникально, вызовите MY REST api с помощью чего-то вроде этого /login/facebook POST через SSL и передачи access_token, электронной почты, имени пользователя и т. д.)
затем мой сервер проверяет, действителен ли access_token
GET graph.facebook.com/debug_token? input_token={token-to-inspect} &access_token={app-token-or-admin-token}
- Если да, если UID, возвращенный facebook, уже присутствует в моей локальной базе данных, я вхожу в систему следующим образом:
SecurityContextHolder.getContext().setAuthentication(
new UsernamePasswordAuthenticationToken(username, null, ROLE_USER));
Если я не нахожу UID, я просто создаю нового пользователя и вхожу в него.
и с этого момента каждый запрос, сделанный на сервер мобильным устройством, будет иметь SESSION (созданную и прикрепленную Spring Security), и мобильное приложение будет аутентифицировано
Может кто-нибудь сказать мне, если это хороший способ сделать что-то? Должен ли я прекратить использование сеансов и переключиться на Spring-Security-OAUTH2?
ИЗМЕНИТЬ 1
Основываясь на советах Дэйва, вот обновленная конфигурация spring-security:
<!- handle login by providing a token-->
<security:http pattern="/login/facebook" auto-config="false" use-expressions="true" entry-point-ref="loginUrlAuthenticationEntryPoint">
<security:custom-filter ref="facebookLoginFilter" position="FORM_LOGIN_FILTER"/>
<security:intercept-url pattern="/**" access="isAuthenticated()" />
</security:http>
<bean id="loginUrlAuthenticationEntryPoint" class="org.springframework.security.web.authentication.LoginUrlAuthenticationEntryPoint">
<constructor-arg value="/login/facebook"></constructor-arg>
</bean>
<!-- handle basic username + password logins-->
<security:http auto-config="true" use-expressions="true" entry-point-ref="forbiddenEntryPoint">
<security:form-login login-processing-url="/security_check" authentication-failure-handler-ref="authFailureHandler"
default-target-url="/" always-use-default-target="true" authentication-success-handler-ref="authSuccessHandler" />
...
my others patterns..
...
</security:http>
<bean id="forbiddenEntryPoint"
class="org.springframework.security.web.authentication.Http403ForbiddenEntryPoint" />
<bean id="authSuccessHandler" class="my.package.AuthenticationSuccessHandlerImpl"/>
<bean id="authFailureHandler" class="my.package.AuthenticationFailureHandlerImpl"/>
<bean id="facebookLoginFilter" class="pl.jcommerce.ocean.web.ws.controller.FacebookLoginFilter">
<property name="requiresAuthenticationRequestMatcher" ref="loginRequestUrlHandler"></property>
<property name="authenticationManager" ref="authManager"></property>
</bean>
<security:authentication-manager id="authManager">
<security:authentication-provider ref="facebookAuthenticationProvider" />
</security:authentication-manager>
<security:authentication-manager>
<security:authentication-provider ref="webServiceUserAuthenticationProvider" />
</security:authentication-manager>
<bean id="loginRequestUrlHandler" class="org.springframework.security.web.util.matcher.RegexRequestMatcher">
<constructor-arg index="0" value="/login/facebook" />
<constructor-arg index="1" value="POST" />
<constructor-arg index="2" value="false" />
</bean>