11 Java EE Security APIの使用
Java EE Security API (JSR 375)は、HTTP認証およびアイデンティティ・ストア用の移植可能なプラグイン・インタフェースや、プログラムによるセキュリティのためのAPIを提供する注入可能なSecurityContext
インタフェースを定義します。プラグインSPIの組込み実装を使用することも、カスタム実装を記述することもできます。
Java EE Security APIを使用すると、アプリケーション内ですべてのセキュリティ情報を直接定義できます。セキュリティ構成を外部で構成せずにアプリケーション内にバンドルすることで、アプリケーションのライフサイクルの管理を向上させることができます。特に、Dockerがホストのマイクロサービスがコンテナに分散されている環境においてはこれが有効です。
WebLogic ServerでのJava EE Security APIの概要
Oracle WebLogic Serverでは、移植可能な認証メカニズム(HttpAuthenticationMechanism
、IdentityStore
など)や、SecurityContext
インタフェースを使用したプログラムによるセキュリティのためのアクセス・ポイントを定義するJava EE Security API (JSR 375)をサポートしています。WebLogic Serverでは、Webコンテナ内でこれらの認証メカニズムがサポートされ、サーブレットおよびEJBコンテナ内でSecurityContext
インタフェースがサポートされています。
Java EE Security API 1.0 (JSR 375)のプログラミング・モデルは、https://www.jcp.org/en/jsr/detail?id=375
の仕様で定義されています。WebLogic Serverは、認証用のプラグイン・インタフェースであるHttpAuthenticationMechanism
をサポートしており、仕様に定義されているBASIC、FORMおよびカスタムFORM認証メカニズムに対する組込みサポートを備えています。また、WebLogic Serverは、RememberMeIdentityStore
インタフェース、およびIdentityStore
インタフェース(LDAPアイデンティティ・ストアとデータベース・アイデンティティ・ストア)とカスタム・アイデンティティ・ストアの組込み実装もサポートしています。
WebアプリケーションおよびEJB用のSecurityContext
インタフェースについてはそれぞれ、「プログラムによるユーザーの認証」および「EJBでのプログラムによるセキュリティの使用」で説明しています。
HttpAuthenticationMechanism
インタフェースは、既存のサーブレットおよびJASPIC認証メカニズムのメリットを活用できるように設計されています。HttpAuthenticationMechanism
はCDI Beanであるため、CDIによってコンテナから自動的に使用可能になります(『Oracle WebLogic Serverアプリケーションの開発』のContexts and Dependency Injection for the Java EE Platformの使用方法に関する項を参照)。コンテナは、HttpAuthenticationMechanism
をサービスに組み込む役割を持ちます。IdentityStore
インタフェースは主にHttpAuthenticationMechanism
実装での使用を意図したものですが、理論上は他のタイプの認証メカニズム(JASPIC ServerAuthModule
など)でも使用できます。HttpAuthenticationMechanism
実装でIdentityStore
を使用することは必須ではなく、どのような方法でもユーザーを認証できますが、IdentityStore
インタフェースが有用で便利なメカニズムです。
サーブレット仕様により定義された宣言メカニズムではなくHttpAuthenticationMechanism
およびIdentityStore
インタフェースを使用することの大きなメリットは、アプリケーションが標準的で移植可能な方法で認証のためのアイデンティティ・ストアを制御できることです。これらのSPIインタフェースの実装はCDI Beanであるため、アプリケーションは、アプリケーション固有の認証メカニズムをサポートする実装を提供することも、デプロイされたアプリケーションの一部であるBeanアーカイブにユーザー資格証明を含めることによって、アプリケーション固有のアイデンティティ・ストアに基づいてユーザー資格証明を検証することもできます。
HttpAuthenticationMechanismインタフェースについて
HttpAuthenticationMechanism
インタフェースは、アプリケーションとともに提供してCDIを介してデプロイできる認証メカニズムを記述するためのSPIを定義します。開発者は、特定の認証トークン・タイプまたはプロトコルをサポートするために、独自のHttpAuthenticationMechanism
実装を記述できます。また、BASIC、FORMおよびカスタムFORM認証メカニズムを実行するいくつかの組込み認証メカニズムもあります。
組込み認証メカニズムの有効化と構成は、使用時に、対応する組込みメカニズムをCDI Beanとして使用可能にするアノテーションを使用して行います。Java EE Security APIでは、動的構成を許可するためにこれらのアノテーションでExpression Language 3.0を使用することもサポートしています。Java Expression Language (EL)の詳細は、https://jcp.org/en/jsr/detail?id=341にあるJSR-000341 Expression Language 3.0の仕様を参照してください。組込み認証メカニズムのアノテーションは次のとおりです:
-
BasicAuthenticationMechanismDefinition
—web.xml
でBASIC <auth-method>
が宣言されているときのサーブレット・コンテナの動作に準拠するBASIC認証を実装します。BASIC認証では、Webクライアントがユーザーからユーザー名とパスワードを取得し、それをWebサーバーに送信します。Webサーバーは、指定されたレルムでユーザーを認証します。 -
FormAuthenticationMechanismDefinition
—web.xml
でFORM <auth-method>
が宣言されているときのサーブレット・コンテナの動作に準拠するFORM認証を実装します。FORMベースの認証では、必要なフォームベース認証メカニズムが導入され、開発者がログイン画面のルック・アンド・フィールを制御できます。Webアプリケーション・デプロイメント記述子には、ログイン・フォームおよびエラー・ページのエントリが含まれています。ログイン・フォームには、ユーザー名とパスワードを入力するためのフィールドを含める必要があります。 -
CustomFormAuthenticationMechanismDefinition
— 変更したバージョンのFORM認証を実装します。WebLogic Serverで異なる点は、アプリケーションで収集された資格証明を使用してSecurityContext.authenticate()
を起動することにより認証が行われる点です。
HttpAuthenticationMechanism
の実装は、実行時に認識されてデプロイされるCDI Beanである必要があり、アプリケーション・スコープであるとみなされます。Beanの検出中、サーブレット・コンテナは、HttpAuthenticationMechanism
を実装するBean (各アプリケーションに1つしかない)を検索し、見つかった場合には、それをアプリケーションの呼出し側の認証のためにデプロイできるように調整します。
サーブレット・コンテナは、JASPIC (Java Authentication Service Provider Interface for Containers)を利用して認証メカニズムをデプロイします。コンテナは、HttpAuthenticationMechanism
に処理を委任できるJASPIC Server Auth Module (SAM)を提供し、そのブリッジSAMをJASPIC AuthConfigFactory
で登録できるように調整します。実行時、通常のJASPIC処理によりブリッジSAMが起動されると、そのSAMは、認証の実行と、呼出し側または認証プロトコル・フローに関与する第三者との必要な対話の駆動をHttpAuthenticationMechanism
に委任します。
HttpAuthenticationMechanismインタフェース・メソッド
HttpAuthenticationMechanism
インタフェースは、3つのインタフェース・メソッドを定義しており、それぞれがJASPIC ServerAuthインタフェースで定義されている3つのメソッドに対応しています。
ブリッジSAMでJASPICメソッドの1つが起動されると、HttpAuthenticationMechanism
の対応するメソッドに処理が委任されます。メソッド名は同じですが、メソッド・シグネチャは同じではありません。ブリッジSAMは、JASPICフレームワークから渡されたパラメータとHttpAuthenticationMechanism
で期待されるパラメータとの双方向のマッピングを行います。
3つのHttpAuthenticationMechanism
インタフェース・メソッドは次のとおりです:
-
validateRequest()
— 受信リクエストを検証し、呼出し側を認証します。 -
secureResponse()
— レスポンス・メッセージを保護します。デフォルトで十分であれば、このメソッドはオプションです。 -
cleanSubject()
— 提供されたプリンシパルおよび資格証明のサブジェクトをクリアします。デフォルトで十分であれば、このメソッドはオプションです。
HttpAuthenticationMechanism
で実装する必要があるのは、validateRequest()
メソッドのみです。このインタフェースには、デフォルトでsecureResponse()
とcleanSubject()
の実装が含まれており、多くの場合はこれで十分です。
HttpAuthenticationMechanismインタフェース・アノテーション
次のアノテーションを使用して、HttpAuthenticationMechanism
に動作を追加できます:
-
AutoApplySession
— 認証メカニズムのJASPICjavax.servlet.http.registerSession
動作を宣言により有効にし、リクエストごとに自動的に適用するための方法をアプリケーションに提供します。 -
LoginToContinue
— 宣言により「ログインして続行する」機能を認証メカニズムに追加する能力をアプリケーションに提供します。また、このアノテーションは、ログイン・ページ、エラー・ページ、および組込みフォームベース認証メカニズムのリダイレクト/転送動作を構成する場合にも使用します。 -
RememberMe
- 認証メカニズムのRememberMe
機能を有効にするためにRememberMe
アイデンティティ・ストアを使用する必要があることを指定します。RememberMe
を使用するには、アプリケーションがそのHAM実装を提供し、HAMにRememberMe
アノテーションを付ける必要があります。
アイデンティティ・ストア・インタフェースについて
WebLogic Serverでは、すべての組込み認証メカニズムはアイデンティティ・ストアを使用して認証する必要があります。Java EE Security APIでは、2つのアイデンティティ・ストア・インタフェース(IdentityStore
およびRememberMeIdentityStore
)が定義されています。IdentityStore
インタフェースは、ユーザー名やパスワードなどの呼出し側の資格証明を検証してグループ・メンバーシップ情報を返すメソッドを定義します。RememberMeIdentityStore
インタフェースは、認証されたユーザーのアイデンティティを長期間記憶する必要がある場合に対処するための、IdentityStore
インタフェースのバリエーションです。
次の各トピックで、アイデンティティ・ストア・インタフェースについて詳しく説明します:
IdentityStoreインタフェース
IdentityStore
インタフェースは、ユーザー・アカウント情報を含むディレクトリまたはデータベースであるアイデンティティ・ストアと対話するためのSPIを定義します。IdentityStore
インタフェースの実装により、ユーザーの資格証明の検証や、ユーザーが属するグループに関する情報の提供を行えます。ほとんどの場合、IdentityStore
実装は外部アイデンティティ・ストア(LDAPサーバーなど)と対話して実際の資格証明検証やグループ・ルックアップを実行しますが、IdentityStore
がユーザー・アカウント・データそのものを管理する場合もあります。
IdentityStore
の組込み実装には、LDAPアイデンティティ・ストアとデータベース・アイデンティティ・ストアの2つがあります。これらのアイデンティティ・ストアは、すでに存在する必要がある外部ストアに処理を委任します。IdentityStore
実装が外部ストアの提供や管理を行うことはありません。次のアノテーションを使用して、IdentityStore
インタフェースと外部ストアの間の通信を構成します:
-
LdapIdentityStoreDefinition
— 外部LDAPサーバーとの通信、ユーザー資格証明の検証またはユーザー・グループのルックアップに必要なパラメータを使用して、アイデンティティ・ストアを構成します。 -
DatabaseIdentityStoreDefinition
— 外部データベースへの接続、ユーザー資格証明の検証、またはユーザー・グループのルックアップに必要なパラメータを使用して、アイデンティティ・ストアを構成します。データベース・アイデンティティ・ストアを構成するときは、PasswordHash
実装を提供する必要があります。
アプリケーションは、独自のカスタム・アイデンティティ・ストアを提供することも、組込みのLDAPアイデンティティ・ストアまたはデータベース・アイデンティティ・ストアを使用することもできます。インストールされたWebLogic Serverには、組込みデータベース・アイデンティティ・ストアの使用方法を示すオプション・サンプルが含まれています。このサンプルは、EXAMPLES_HOME\examples\src\examples\javaee8\security
ディレクトリにあります。EXAMPLES_HOMEは、WebLogic Serverサンプル・コードが構成されているディレクトリです。デフォルトでは、このディレクトリはORACLE_HOME\wlserver\samples\server
です。WebLogic Serverサンプル・コードの詳細は、Oracle WebLogic Serverの理解のサンプル・アプリケーションおよびサンプル・コードを参照してください。
IdentityStore
の実装は、実行時に認識されてデプロイされるCDI Beanである必要があり、アプリケーション・スコープであるとみなされます。複数のIdentityStore
実装が存在する場合もあります。その場合は、IdentityStoreHandler
の制御下で起動されます。
IdentityStoreHandler
認証メカニズムはIdentityStore
と直接やり取りするのではなく、IdentityStoreHandler
を呼び出します。IdentityStoreHandler
インタフェースの実装は、単一のメソッドvalidate(Credential)
を提供します。このメソッドは、起動されると、使用可能なIdentityStoresを反復処理して集計結果を返します。IdentityStoreHandler
もCDI Beanである必要があり、アプリケーション・スコープであるとみなされます。実行時に、認証メカニズムはIdentityStoreHandler
を注入し、これを基に起動します。次にIdentityStoreHandler
が使用可能なIdentityStoreを検索し、これを基に起動して、集計結果を判別します。
Java EE Security API仕様で定義されている標準アルゴリズムを実装する、組込みのIdentityStoreHandler
が存在します。必要なアルゴリズムを使用し、IdentityStoreを選択してそれに基づいて起動し、集計(非集計)結果を返すことができる、独自のIdentityStoreHandler
をアプリケーションが提供することもできます。
IdentityStoreインタフェース・メソッド
IdentityStore
インタフェースには、次の4つのメソッドがあります:
-
validate(Credential)
— 資格証明を検証し、その検証の結果を返します。 -
getCallerGroups(CredentialValidationResult)
— 提供されたCredentialValidationResult
(前回成功した検証の結果)に示された呼出し側に関連付けられたグループを返します。 -
validationTypes()
—IdentityStore
のこのインスタンスでサポートされる操作を示す検証タイプのセット(VALIDATE
、PROVIDE_GROUPS
の1つ以上)を返します。 -
priority()
— このIdentityStore
の自己宣言優先順位を表す正の整数を返します。値が小さいほど優先順位は高くなります。
getCallerGroups()
は機密操作であり、任意のユーザーに関する情報を戻せるうえ、呼出し側にユーザーの資格証明やアイデンティティの証明の提供を要求することもありません。このため、呼出し側が IdentityStorePermission("getGroups")
権限を持っている必要があります。この権限チェックが実行されるように、Javaセキュリティ・マネージャが有効になっていることを確認してください。「Javaセキュリティ・マネージャを使用したWebLogicリソースの保護」を参照してください。
RememberMeIdentityStoreインタフェース
RememberMeIdentityStore
インタフェースは、特殊なタイプのアイデンティティ・ストアを表します。これはIdentityStore
インタフェースを実装も拡張もせず、このインタフェースとの直接の関連はありません。ただし、実行される機能は特殊ではありますが、似ています。アプリケーションが、ユーザーの認証済セッションを長期間記憶する必要がある場合は、RememberMeIdentityStore
インタフェースを使用します。これにより、呼出し側は、プライマリ認証資格証明を毎回提示しなくても、定期的にアプリケーションに戻ることができます。たとえば、あるWebサイトにアクセスしたときに、そのサイトにユーザーの情報を記憶しておき、明示的にログアウトしないかぎり、パスワードの入力は定期的に(2週間に1回など)のみ要求されるようにすることができます。
RememberMeの仕組みは次のとおりです:
-
認証されていないユーザーからのリクエストを受信すると、そのユーザーはアプリケーションから提供された
HttpAuthenticationMechanism
を使用して認証されます(これは必須で、RememberMeIdentityStore
は、アプリケーションにより提供されたHttpAuthenticationMechanism
と組み合せてのみ使用できます)。 -
認証後、構成された
RememberMeIdentityStore
によって、ユーザーの認証済アイデンティティに関する情報が後でリストアできるように保存され、クライアントに戻される長期間有効な「remember me」ログイン・トークンがCookieなどとして生成されます。 -
以降にアプリケーションにアクセスすると、クライアントによってログイン・トークンが表示されます。次に
RememberMeIdentityStore
によってトークンが検証され、格納済のユーザー・アイデンティティが返されると、これがユーザーの認証済アイデンティティとして確立されます。トークンが無効または有効期限切れになっている場合は破棄されますが、ユーザーは再び正常に認証されて、新しいログイン・トークンが生成されます。
RememberMeIdentityStore
インタフェースは次のメソッドを定義します:
-
generateLoginToken(CallerPrincipal caller, Set<String> groups)
— 新しく認証されたユーザーに対してログイン・トークンを生成し、提供された呼出し側/グループ情報にそれを関連付けます。 -
removeLoginToken(String token)
— (有効期限が切れている、または無効であると考えられる)ログイン・トークンおよび関連付けられた呼出し側/グループ情報を削除します。 -
validate(RememberMeCredential credential)
— 提供された資格証明を検証し、それが有効な場合は、関連付けられた呼出し側/グループ情報を返します。(RememberMeCredentialは基本的に、ログイン・トークンのホルダーにすぎません。)
RememberMeIdentityStore
の実装はCDI Beanである必要があり、アプリケーション・スコープであるとみなされます。RememberMeIdentityStore
を構成するには、RememberMe
アノテーションをアプリケーションのHttpAuthenticationMechanism
に追加します。これは、RememberMeIdentityStore
が使用中であることを示し、関連する構成パラメータを提供します。次に、コンテナ提供のインターセプタがHttpAuthenticationMechanism
のコールをインターセプトし、必要に応じて認証メカニズムのコールの前後にRememberMeIdentityStore
を起動して、セッションにユーザーのアイデンティティが正しく設定されるようにします。Java EE Security API仕様(JSR 375) (https://jcp.org/en/jsr/detail?id=375
)に、必要なインターセプタ動作について詳しく説明されています。
RememberMeIdentityStore
の実装では、トークンおよびユーザー・アイデンティティ情報を安全に管理するために注意を払う必要があります。たとえば、攻撃者がログイン・トークンにアクセスできてしまった場合にその情報を公開することがないように、ログイン・トークンには資格証明や機密属性などの機密的なユーザー情報を含めないようにする必要があります。暗号化されたトークンでさえ、攻撃者に十分な時間/リソースがあれば脆弱性を持つ可能性があります。同様に、トークンは可能なかぎり暗号化または署名し、セキュアなチャネル(HTTPS)を介してのみ送信する必要があります。RememberMeIdentityStore
によって管理されるユーザー・アイデンティティ情報は、可能なかぎり安全に格納する必要があります(ただし、必ずしも確実に永続化する必要はありません。セッションが「記憶されなかった」としても、ユーザーが再度ログインを求められるだけです)。
使用の要件
Java EE Security APIメカニズムを使用するために特定の構成は必要ありませんが、JASPICやCDIなどの他の機能が有効になっていることを確認する必要があります。
WebLogic ServerでJava EE Security API機能を使用する場合は、次の要件に注意してください:
-
CDI仕様で規定されているように、WebアプリケーションではアプリケーションのWARファイルまたはEARファイルに
beans.xml
デプロイメント記述子ファイルを含める必要があります。HttpAuthenticationMechanism
インタフェースとIdentityStore
インタフェースはCDI Beanとして実装されるため、CDIを介してコンテナから参照できます。 -
Webアプリケーションの
web.xml
ファイル内にあるmetadata-complete
属性をtrue
に設定しないでください。WebLogic Serverのデフォルトは、false
です。 -
JASPICはドメイン・レベルで有効にする必要があります。WebLogic Serverでは、デフォルトでJASPICはドメインに対して有効になっています。