Spring Securityの2つのログインページ

1前書き

このチュートリアルでは、設定内で2つの異なるSpring Security http 要素を使用して、2つの異なるログインページで動作するようにSpring Securityを設定する方法を説明します。

2 2つのHTTP要素を設定する

2つのログインページが必要になる可能性がある状況の1つは、アプリケーションの管理者用に1ページと通常のユーザー用に別のページがある場合です。

それぞれに関連付けられたURLパターンによって区別される2つの http 要素を設定します。

であるために通常のユーザ認証が必要になるページの /user

アクセスした 管理者がアクセスするページの /admin

http 要素には、異なるログインページと異なるログイン処理URLがあります。

2つの異なる http 要素を設定するには、 @ Configuration でアノテーションを付けた2つの静的クラスを作成して、 WebSecurityConfigurerAdapter を拡張します。

どちらも通常の @ Configuration クラス内に配置されます。

@Configuration
@EnableWebSecurity
public class SecurityConfig {
    ...
}

"ADMIN" ユーザー用に WebSecurityConfigurerAdapter を定義しましょう。

@Configuration
@Order(1)
public static class App1ConfigurationAdapter extends WebSecurityConfigurerAdapter {
    public App1ConfigurationAdapter() {
        super();
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.antMatcher("/admin** ")
          .authorizeRequests()
          .anyRequest()
          .hasRole("ADMIN")

          .and()
          .formLogin()
          .loginPage("/loginAdmin")
          .loginProcessingUrl("/admin__login")
          .failureUrl("/loginAdmin?error=loginError")
          .defaultSuccessUrl("/adminPage")

          .and()
          .logout()
          .logoutUrl("/admin__logout")
          .logoutSuccessUrl("/protectedLinks")
          .deleteCookies("JSESSIONID")

          .and()
          .exceptionHandling()
          .accessDeniedPage("/403")

          .and()
          .csrf().disable();
    }
}

それでは、一般ユーザー向けに WebSecurityConfigurerAdapter を定義しましょう。

@Configuration
@Order(2)
public static class App2ConfigurationAdapter extends WebSecurityConfigurerAdapter {

    public App2ConfigurationAdapter() {
        super();
    }

    protected void configure(HttpSecurity http) throws Exception {
        http.antMatcher("/user** ")
          .authorizeRequests()
          .anyRequest()
          .hasRole("USER")

          .and()
          .formLogin()
          .loginPage("/loginUser")
          .loginProcessingUrl("/user__login")
          .failureUrl("/loginUser?error=loginError")
          .defaultSuccessUrl("/userPage")

          .and()
          .logout()
          .logoutUrl("/user__logout")
          .logoutSuccessUrl("/protectedLinks")
          .deleteCookies("JSESSIONID")

          .and()
          .exceptionHandling()
          .accessDeniedPage("/403")

          .and()
          .csrf().disable();
    }
}

各静的クラスに @ Order アノテーションを付けることで、URLが要求されたときのパターンマッチングに基づいて2つのクラスが考慮される順序を指定していることに注意してください。

2つの構成クラスは同じ順序を持つことはできません。

3カスタムログインページ

ユーザーの種類ごとに独自のカスタムログインページを作成します。管理者ユーザーの場合、ログインフォームには設定で定義されているように "user login" __アクションがあります。

<p>User login page</p>
<form name="f" action="user__login" method="POST">
    <table>
        <tr>
            <td>User:</td>
            <td><input type="text" name="username" value=""></td>
        </tr>
        <tr>
            <td>Password:</td>
            <td><input type="password" name="password"/></td>
        </tr>
        <tr>
            <td><input name="submit" type="submit" value="submit"/></td>
        </tr>
    </table>
</form>

管理者ログインページは似ていますが、フォームはjava設定に従って "admin login" __のアクションを持ちます。

4認証設定

それでは、アプリケーション用に認証を設定する必要があります。そのための2つの方法を見てみましょう。1つはユーザー認証に共通の情報源を使用する方法、もう1つは2つの異なる情報源を使用する方法です。

4.1. 共通のユーザー認証元を使用する

両方のログインページがユーザーを認証するための共通のソースを共有する場合は、認証を処理する UserDetailsS​​ervice タイプの単一のBeanを作成できます。

2人のユーザーを定義する InMemoryUserDetailsManager を使用してこのシナリオを説明しましょう。1人は "USER" の役割を持ち、もう1人は "ADMIN" の役割を持ちます。

@Bean
public UserDetailsService userDetailsService() throws Exception {
    InMemoryUserDetailsManager manager = new InMemoryUserDetailsManager();
    manager.createUser(User
      .withUsername("user")
      .password(encoder().encode("userPass"))
      .roles("USER")
      .build());

    manager.createUser(User
      .withUsername("admin")
      .password(encoder().encode("adminPass"))
      .roles("ADMIN")
      .build());

    return manager;
}

@Bean
public static PasswordEncoder encoder() {
    return new BCryptPasswordEncoder();
}

4.2. 2つの異なるユーザー認証元を使用する

管理者用と一般ユーザー用のユーザー認証用のソースが異なる場合は、各静的 @ Configuration クラス内に AuthenticationManagerBuilder を設定できます。 "ADMIN" ユーザー用の認証マネージャの例を見てみましょう。

@Configuration
@Order(1)
public static class App1ConfigurationAdapter extends WebSecurityConfigurerAdapter {
    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        auth.inMemoryAuthentication()
          .withUser("admin")
          .password(encoder().encode("admin"))
          .roles("ADMIN");
    }
}

この場合、前のセクションの UserDetailsS​​ervice Beanは使用されなくなります。

6. 結論

このクイックチュートリアルでは、2つの異なるログインページを同じSpring Securityアプリケーションに実装する方法を説明しました。

この記事の完全なコードはhttps://github.com/eugenp/tutorials/tree/master/spring-security-mvc-boot[GitHubプロジェクト]にあります。

アプリケーションを実行すると、 /protectedLinks URIで上記の例にアクセスできます。

前の投稿:Spring Security - Persistent Remember Me
次の投稿:Java NIO2非同期チャネルAPIの手引き