ホームページ > バックエンド開発 > Golang > JWT 認証を理解する: Spring Security のアーキテクチャと Go 実装

JWT 認証を理解する: Spring Security のアーキテクチャと Go 実装

Patricia Arquette
リリース: 2024-12-01 14:15:11
オリジナル
355 人が閲覧しました

JWT ステートレス認証 (こちらから入手可能) を設定した後、主要なコンポーネントとその相互作用を特定することで Spring Security の抽象化の下で何が起こるかを理解したいと思いました。この探索をより魅力的にするために、標準の HTTP ライブラリを使用して最小限のバージョンを Go に再実装しました。 3 つのコア フロー (登録、トークン生成、保護されたリソースへのアクセス) を分解し、Go で再構築することで、Spring Security の認証パターンをより単純なコンポーネントにマッピングすることに着手しました。

この投稿では、認可ではなく、認証フロー、つまりシステムがユーザー ID を検証する方法に特に焦点を当てています。 Spring Security のアーキテクチャのさまざまなコンポーネントを介してリクエストを追跡するシーケンス図を使用してフローを調べます。

主要コンポーネント

システムは 3 つのエンドポイントを提供します:

  1. ユーザー登録: 新規ユーザーからのユーザー名とパスワードを受け入れます
  2. トークン生成 (ログイン): ユーザーが有効な資格情報で正常にログインすると、JWT トークンを作成します
  3. 保護されたアクセス: 認証されたユーザーがトークンを使用して保護されたリソースにアクセスできるようにします。 getAuthenticatedUser エンドポイントは例として機能し、認証されたトークン所有者のプロファイル情報を返します

次のセクションでは、各フローに含まれるコア コンポーネントについて、それぞれのシーケンス図を使用して説明します。

登録の流れ

Understanding JWT Authentication: Spring Security

ユーザー名とパスワードを含む登録リクエストは、Spring Security フィルター チェーン を通過します。ここでは、登録エンドポイントが SecurityConfiguration で認証を必要としないように構成されているため、最小限の処理が発生します。次に、リクエストは Spring の DispatcherServlet を通過し、URL パターンに基づいて UserController の適切なメソッドにルーティングされます。リクエストは UserController の登録エンドポイントに到達し、ユーザー情報が ハッシュ化された パスワードとともに保存されます。

トークン生成の流れ

Understanding JWT Authentication: Spring Security

ユーザー名とパスワードを含むログイン要求は Spring Security フィルター チェーン を通過します。このエンドポイントは SecurityConfiguration で認証を必要としないように構成されているため、最小限の処理が発生します。リクエストは Spring の DispatcherServlet を介して UserController のログイン エンドポイントに移動し、AuthenticationManager に委任されます。 ApplicationConfiguration で定義された構成済み Bean を使用して、AuthenticationManager は提供された資格情報を保存されている資格情報と照合して検証します。認証が成功すると、UserController は JwtService を使用して、ユーザーの情報と作成時間などのメタデータを含む JWT トークンを生成します。これは、後続の認証されたリクエストのためにクライアントに返されます。

保護されたリソースへのアクセス フロー

認証成功フロー (200)

Understanding JWT Authentication: Spring Security

失敗した認証フロー (401)

Understanding JWT Authentication: Spring Security

Authorization ヘッダーに JWT トークンを含むリクエストが到着すると、JwtService を使用してトークンを処理する JwtAuthenticationFilter (カスタム定義された OncePerRequestFilter) を通過します。有効な場合、フィルターは ApplicationConfiguration で構成された UserDetailsS​​ervice を介してユーザーを取得し、SecurityContextHolder で認証を設定します。トークンが欠落しているか無効な場合、フィルターは認証を設定せずにリクエストを続行することを許可します。

チェーンの後半で、AuthorizationFilter は、リクエストが SecurityContextHolder を介して適切に認証されているかどうかをチェックします。認証の欠落を検出すると、AccessDeniedException をスローします。この例外は ExceptionTranslationFilter によってキャッチされ、ユーザーが匿名かどうかをチェックし、SecurityConfiguration で構成された JwtAuthenticationEntryPoint に委任して 401 Unauthorized 応答を返します。

すべてのフィルターが通過すると、リクエストは Spring の DispatcherServlet に到達し、UserController の getAuthenticatedUser エンドポイントにルーティングされます。このエンドポイントは、フィルター チェーン プロセス中に設定された SecurityContextHolder から認証されたユーザー情報を取得します。

注: Spring Security は、フィルターと特殊なコンポーネントの豊富なエコシステムを採用して、さまざまなセキュリティ上の懸念事項に対処します。核となる認証フローを理解するために、JWT トークンの検証とユーザー認証の主要なプレーヤーだけに焦点を当てました。

Go 実装: コンポーネントのマッピング

Go 実装は、主要な Spring Security コンポーネントにマップする簡素化されたアーキテクチャを通じて同様の機能を提供します。

フィルターチェーン

  • Spring Security のフィルター チェーンの最小バージョンを提供します
  • リクエストごとにフィルターを順番に処理します
  • スレッド セーフティのためにリクエストごとのチェーン インスタンス (VirtualFilterChain) を使用します。

ディスパッチャー

  • Spring の DispatcherServlet にマップします
  • セキュリティフィルター処理後にリクエストを適切なハンドラーにルーティングします

認証コンテキスト

  • Go のコンテキスト パッケージを使用してリクエストごとに認証状態を保存します
  • Spring の SecurityContextHolder にマッピングされます

JwtFilter

  • Spring の JwtAuthenticationFilter と直接的に同等
  • JWT トークンを抽出して検証します
  • 検証が成功した場合に認証コンテキストを設定します

認証フィルター

  • Spring の AuthorizationFilter の簡易バージョン
  • 認証検証のみに焦点を当てます
  • 認証コンテキストをチェックし、見つからない場合は 401 を返します

JwtService

  • Spring の JwtService に似ています
  • トークンの生成と検証を処理します
  • 同じコア JWT 操作を使用しますが、構成はより単純です

テスト範囲

どちらの実装にも、主要な認証シナリオを検証する統合テスト (auth_test.go と AuthTest.java) が含まれています。

登録の流れ

  • 有効な認証情報によるユーザー登録が成功しました
  • 重複したユーザー名の登録試行

ログインの流れ

  • 有効な資格情報によるログイン成功
  • 存在しないユーザー名でログインしようとしました
  • 間違ったパスワードでログインしようとしました

保護されたリソース アクセス

  • 有効なトークンによるアクセス成功
  • 認証ヘッダーなしのアクセス試行
  • 無効なトークン形式によるアクセス試行
  • 期限切れのトークンによるアクセス試行
  • 有効なトークン形式でアクセス試行されましたが、ユーザーは存在しません

Java 実装には、Spring Security のフィルター チェーンを介した各テスト シナリオのフローを説明する詳細なコメントが含まれています。これらの同じフローは、同等のコンポーネントを使用して Go 実装で複製されます。

旅のまとめ

Spring Security の JWT 認証をフローとテスト ケースに分割して調べました。次に、これらのパターンを Go コンポーネントにマッピングしました。統合テストでは、リクエストが Spring Security のフィルター チェーンとコンポーネントをどのように流れるかを示しました。これらのパターンの単純なバージョンを構築することで、Spring Security の設計を理解することができました。テストでは、両方の実装が同じ方法で認証を処理することが証明されました。分析、テスト、再構築を通じて、Spring Security の認証がどのように機能するかをより深く理解できました。

以上がJWT 認証を理解する: Spring Security のアーキテクチャと Go 実装の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ソース:dev.to
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
著者別の最新記事
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート