私はOAuth2とSpringSecurity OAuth、特にOAuthプロバイダーサービスに頭を悩ませようとしています。次のことを実装しようとしています。
これらのモジュールはすべて互いに独立しています。つまり、異なるプロジェクトに分離されており、(1) http://oauth.web.com 、( 2) http://rest.web.com 、(3) http://web.com
私の2つの質問は次のとおりです。
A. Webクライアントプロジェクトを実装して、ユーザーが保護されたページにログインするか、[ログイン]ボタンをクリックすると、OAuthプロバイダーのURLにリダイレクトされ、ログインして、で認証されるようにするにはどうすればよいですか?すべてのユーザーロールを持つWebクライアントであり、どのクライアントが使用されたかを知る必要もあります。@EnableResourceServer
(Resource Serverの実装と同じ方法。以下のコードを参照)このプロジェクトでユーザーの詳細を取得しますか?アクセストークンを管理し、常にリソースサーバーへの呼び出しに含める必要がありますか、それとも何らかの方法で自動的に行うことができますか?
B.開発するモバイルアプリにセキュリティを実装するための最良の方法は何ですか。この認証にはパスワードグランドを使用する必要があります。アプリは自分で作成し、ユーザー名とパスワードをネイティブ画面に表示してから、SSLを介した基本認証としてサーバーに送信するためです。 Spring Security OAuthとユーザーの詳細を返すことについての話を見ることができるサンプルはありますか。
OAuthプロジェクト(1)とリソースプロジェクト(2)の実装は次のとおりです。
OAuth2サーバー構成(ほとんどのコードは [〜#〜]ここ[〜#〜] から取得されました)
@Configuration
@EnableAuthorizationServer
public class OAuth2ServerConfig extends AuthorizationServerConfigurerAdapter {
@Autowired
@Qualifier("authenticationManagerBean")
private AuthenticationManager authenticationManager;
@Autowired
DataSource dataSource;
@Override
public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
endpoints
.tokenStore(tokenStore())
.approvalStore(approvalStore())
.authorizationCodeServices(authorizationCodeServices())
;
}
@Bean
public JdbcClientDetailsService clientDetailsService() {
return new JdbcClientDetailsService(dataSource);
}
@Bean
public TokenStore tokenStore() {
return new JdbcTokenStore(dataSource);
}
@Bean
public ApprovalStore approvalStore() {
return new JdbcApprovalStore(dataSource);
}
@Bean
public AuthorizationCodeServices authorizationCodeServices() {
return new JdbcAuthorizationCodeServices(dataSource);
}
@Override
public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
clients.withClientDetails(clientDetailsService());
}
@Override
public void configure(AuthorizationServerSecurityConfigurer oauthServer) throws Exception {
oauthServer.checkTokenAccess("permitAll()");
}
}
Webセキュリティ構成
@Configuration
@Order(SecurityProperties.ACCESS_OVERRIDE_ORDER)
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter{
@Autowired
private CustomUserDetailsService customUserDetailsService;
@Override
protected void configure(HttpSecurity http) throws Exception {
http.csrf().disable(); // TODO. Enable this!!!
http.authorizeRequests()
.and()
.formLogin()
// .loginPage("/login") // manually defining page to login
// .failureUrl("/login?error") // manually defining page for login error
.usernameParameter("email")
.permitAll()
.and()
.logout()
// .logoutUrl("/logout")
.logoutSuccessUrl("/")
.permitAll();
}
@Override
public void configure(AuthenticationManagerBuilder auth) throws Exception {
auth
.userDetailsService(customUserDetailsService)
.passwordEncoder(new BCryptPasswordEncoder());
}
@Override
@Bean
public AuthenticationManager authenticationManagerBean() throws Exception {
return super.authenticationManagerBean();
}
}
UserDetailsService(customUserDetailsService)
@Service
public class CustomUserDetailsService implements UserDetailsService{
private final UserService userService;
@Autowired
public CustomUserDetailsService(UserService userService) {
this.userService = userService;
}
public Authority loadUserByUsername(String email) throws UsernameNotFoundException {
User user = userService.getByEmail(email)
.orElseThrow(() -> new UsernameNotFoundException(String.format("User with email=%s was not found", email)));
return new Authority(user);
}
}
構成(スケルトンコードのほとんどは [〜#〜] this [〜#〜] の例から取得されました)
@Configuration
@EnableResourceServer
public class OAuth2ResourceConfig extends ResourceServerConfigurerAdapter{
@Autowired
DataSource dataSource;
String RESOURCE_ID = "data_resource";
@Override
public void configure(ResourceServerSecurityConfigurer resources) throws Exception {
TokenStore tokenStore = new JdbcTokenStore(dataSource);
resources
.resourceId(RESOURCE_ID)
.tokenStore(tokenStore);
}
@Override
public void configure(HttpSecurity http) throws Exception {
http
// For some reason we cant just "permitAll" OPTIONS requests which are needed for CORS support. Spring Security
// will respond with an HTTP 401 nonetheless.
// So we just put all other requests types under OAuth control and exclude OPTIONS.
.authorizeRequests()
.antMatchers(HttpMethod.GET, "/**").access("#oauth2.hasScope('read')")
.antMatchers(HttpMethod.POST, "/**").access("#oauth2.hasScope('write')")
.antMatchers(HttpMethod.PATCH, "/**").access("#oauth2.hasScope('write')")
.antMatchers(HttpMethod.PUT, "/**").access("#oauth2.hasScope('write')")
.antMatchers(HttpMethod.DELETE, "/**").access("#oauth2.hasScope('write')")
.and()
// Add headers required for CORS requests.
.headers().addHeaderWriter((request, response) -> {
response.addHeader("Access-Control-Allow-Origin", "*");
if (request.getMethod().equals("OPTIONS")) {
response.setHeader("Access-Control-Allow-Methods", request.getHeader("Access-Control-Request-Method"));
response.setHeader("Access-Control-Allow-Headers", request.getHeader("Access-Control-Request-Headers"));
}
});
}
}
WSコントローラー:
@RestController
@RequestMapping(value = "/todos")
public class TodoController {
@Autowired
private TodoRepository todoRepository;
@RequestMapping(method = RequestMethod.GET)
public List<Todo> todos() {
return todoRepository.findAll();
}
// other methods
}
ユーザーが保護されたページにログインするか、[ログイン]ボタンをクリックすると、OAuthプロバイダーのURLにリダイレクトされ、ログインして、Webで認証されるように、Webクライアントプロジェクトを実装するにはどうすればよいですかすべてのユーザーロールを持ち、どのクライアントが使用されたかを知る必要があるクライアント
OAuthをSSOとして使用します。
オプション1、Spring Cloudを使用 https://spring.io/blog/2015/02/03/sso-with-oauth2-angular-js-and-spring-security-part-v
オプション2、SSOプロセスを手動で処理します。
webクライアントで、認証付与を使用してログインページをOAuthサーバーに構成します。
protected void configure(HttpSecurity http) throws Exception {
http.csrf().disable(); // TODO. Enable this!!!
http.authorizeRequests()
.and()
.formLogin()
.loginPage("http://oauth.web.com/oauth/authorize?response_type=code&client_id=webclient&redirect_uri=http://web.com") // manually defining page to login
//.failureUrl("/login?error") // manually defining page for login error
.usernameParameter("email")
.permitAll()
.and()
.logout()
//.logoutUrl("/logout")
.logoutSuccessUrl("/")
.permitAll();
}
認証と認証のプロセスが完了すると、認証コードhttp://web.com/?code=jYWioI
でWebクライアントにリダイレクトされます。 Webクライアントは、このコードをoauthサーバー上のトークンアクセスと交換する必要があります。oauthサーバー上で、ユーザー情報を取得するためのエンドポイントを作成します
@RestController
public class UserRestService {
@RequestMapping("/user")
public Principal user(Principal user) {
// you can also return User object with it's roles
// {"details":...,"principal":{"username":"user",...},"name":"user"}
return user;
}
}
次に、Webクライアントは、上記のRESTエンドポイントへのトークンアクセスを使用してリクエストを送信することでユーザーの詳細情報にアクセスし、応答に基づいてユーザーを認証できます。
アクセストークンを管理し、常にリソースサーバーへの呼び出しに含める必要がありますか、それとも何らかの方法で自動的に行うことができますか?
すべてのリクエストにはトークンアクセスが含まれている必要があります。自動的に実行したい場合、springはOauth 2 client http://projects.spring.io/spring-security-oauth/docs/oauth2.html ==
私が開発するモバイルアプリにセキュリティを実装するための最良の方法は何ですか。この認証にはパスワードグランドを使用する必要があります。アプリは自分で作成し、ユーザー名とパスワードをネイティブ画面に表示してから、SSLを介した基本認証としてサーバーに送信するためです。
ネイティブ画面を使用しているため、パスワードの付与で十分ですが、更新トークンを保存できます。これにより、認証プロセスを繰り返さずにトークンアクセスをリクエストできます。
Spring Security OAuthとユーザーの詳細を返すことについての話を見ることができるサンプルはありますか。
上記のサンプルコードを参照するか、これをご覧ください https://spring.io/blog/2015/02/03/sso-with-oauth2-angular-js-and-spring-security-part-v