【Nest.js】アクセストークンの検証方法がわからん

アクセストークン検証の実装がわからない
【6/19開催】Kong Community Japan Meetup #4
本イベントでは、Kong Inc. のVP of ProductであるReza Shafii氏もプレゼンターとして参加。当社からはアーキテクト マネージャーの槌野の登壇が決定!参加無料です!!

【6/21開催】開発者目線でのSBOMとの向き合い方
SBOMの導入から開発者がSBOMの作成・管理を自動で行っていくための方法(デモ)を紹介します。

【7/5開催】azd+Terraform? ~ポイントを押えてAzure上へのアプリケーション環境をラクチン構築~
ツールの概要説明から、実際の開発におけるポイントをお伝えします!

【7/19開催】現場で役立つAzure神小技10+α 〜生成AI,RAG,コスト削減など旬な技術満載のLT大会〜
Azureの最新技術や実用的な小技を紹介する特別なライトニングトーク大会を開催します!

【7/26開催】最適なIaCツールを選ぼう
プロジェクトでのツール選びに困らないための重要な観点をご説明します!

今回も失敗談を書き連ねていきたいと思います。Nest JSを用いて、Azure AD B2Cのアクセストークンを検証する方法を調べてみました。公式が提供しているライブラリではなく、Auth0が提供しているライブラリとpassportというライブラリを組み合わせて、アクセストークンの検証を実装しています。わからん!

挨拶というか導入というか…

どもども!最近は暑くて寒いのでドアを窓という窓を全開にして換気している龍ちゃんです。いつもは、検証して納得した内容をブログに書いているのですが、今回は上司に質問するために現情報を報告するためだけにブログ化していきたいと思います。ちなみにプロジェクトではないので、そんな急ぎの内容ではないことだけ、先に書いておきます。

今回は、「フロントとバックエンドの接続時にアクセストークンを使用してセキュアに運用する」で触れていた内容に対して、具体的な対処法のサンプルが動いたのでまとめていきたいと思います。具体的なシナリオとしては「アクセストークンをを検証する方法をNest.jsで実装したい」になります。

以下が簡単なアーキ図になります。

アクセストークンが必要になった実装をかなえた場合

今回のブログでは、前提知識として「Azure AD B2Cでのログイン」と「Headerにアクセストークンを挿入する」の2つが求められます。以下が、それぞれについてまとめたブログになっているので、もしお時間があれば読んでみてください。

さて、前提知識や物語の導入は終わりました。

本題のようなもの…

今回は、いつもの形式と異なる感じでブログを執筆していきたいと思います。若干の物語形式で書いていこうと思います。失敗談がたくさんありますので、供養もかねて書いていこうと思います。

Step.1 公式のライブラリが非推奨というちょっと怖い話

導入でも触れましたが今回は、「アクセストークンをを検証する方法をNest.jsで実装したい」になります。もちろんこの方法については、公式で解説されています。どうやら以下のライブラリを使用するようです。

npm install passport passport-azure-ad

公式が解説を載せているので、これを「Nest.js」用にカスタマイズするだけで済みそうです….

と!!思うじゃないですか?というか僕も思っていました。なかなか動かないので、公式のGitHubを覗きに行ったときに問題が発覚しました。この「passport-azure-ad」というライブラリがアーカイブされていました。はい、しかも明確に非推奨になっていました。

とりあえず、これを見つけてから頭を抱えましたね。とりあえず、一度見なかったことにして実装しました。実装に必要だった足跡だけ記載しておきました。

非推奨のpassport-azure-adを使用してトークンの検証を行うための足跡

Step.2 自前でトークンの検証を行うことはムリゲー

さて、Nest.jsの公式を見ると、トークンの検証にpassortを使用することは問題なさそうであるということまではわかりました。

もう一度、公式のAuthenticationのページを見るとJWTを自前で発行して、自前で検証する方法についての記載はありました。どうやらNest,jsの@nestjs/jwt内のJwtServiceを使用すると、トークンをデコードできるようです。そのため、トークンの検証を自前で実行することはできそうです。とりあえず、デコードして値を抽出する部分まで実装することができました。

今度は、Azureの公式にある「署名の検証」というページにたどりつきました。トップに書いてある文言を引用します。

To validate a token, your application should check both the signature and claims of the token. Many open-source libraries are available for validating JWTs, depending on your preferred language. It’s recommended that you explore those options rather than implement your own validation logic.

要約すると「自前で署名の検証すると危ないよ~ライブラリを使おうね~」とのことです。さて全力で困りました。とりあえず、こちらも実装のめどが立ったので足跡だけ記載しておきます。

Azureがおすすめしない自前でトークンを検証するための足跡

Step.3 そもそもトークンの検証って何をしたいんや??

とりあえず、3日ほどかけてやっていたことは非推奨であるという結論が出てフリーズしていました。そういえば、アクセストークンの検証はどうするものか?ということについて疑問を持ったので調べてみました。

JWTの構成図
ヘッダーと本文・署名の三つから構成されている

とりあえず、3つの要素から構成されていることがわかりました。厳密に署名の検証をする場合は、本文の中の検証だけでなく、ヘッダーと署名両方をチェックする必要があり、自前で実装するとなると骨が折れるというところまでは理解できました。こちらのサイトで勉強しました。

なんとなくですが、検証に必要な知識を手に入れることに成功しつつあるような気がするので、いったんここで図に起こしておきます。

トークンを検証する考え方

「JWTの発行元から検証に必要な情報を取得して、それを用いてトークン検証を実行する」までが一連の流れかと思います。そして、この憲章に必要な形式もOpen ID Connectの標準仕様という便利な言葉によって共通化されているようです。つまり、「トークンの検証に必要な情報」をAzure AD B2Cから取得することができれば、passportのライブラリで検証することができるようです。

Step.4 別のライブラリで解消したっていう解決策

最終的にこちらの記事にたどりつきました。こちらの記事では、Auth0が提供しているpassport-jwksというライブラリを使用して、検証に必要な情報を収集しています。Azureのこちらのページから情報を取得して、jwks_uriを取得してJWKSを取得してます。ひとまず、こちらで非推奨のpassport-azure-adと同等の結果が得られました。

passportとjwks-rsaを用いてトークンの検証を行う足跡

終わりに

お疲れ様です。今回は、一週間の行動ログみたいな流れでブログを書いてみました。フロント側の実装は簡単に実装できたのですが、バックエンドの検証がうまくいっていないので悩ましいです。

ひとまず動くものは実装することができたので、「上手くいった」といっても良いかもしれません。

といいますか!!バックエンドの検証をしたい理由はStripeをもっと素振りしたいからなんですよね!ひとまず、ここは実装としてうまくいったとして次に進みます。2つしかStripe関連の記事は書いていないのですが、これが増えると良いですね。

今回のサムネは結構お気に入りです!

ではまた~~!グッ!(  •̀ᴗ•́  )و ̑̑

アバター画像
About 龍:Ryu 109 Articles
2022年入社で主にフロントエンドの業務でTailwindと遊ぶ日々。お酒とうまいご飯が好きで、運動がちょっと嫌いなエンジニアです。しゃべれるエンジニアを目指しておしゃべりとブログ執筆に注力中(業務もね)//
ご覧いただきありがとうございます! この投稿はお役に立ちましたか?

役に立った 役に立たなかった

0人がこの投稿は役に立ったと言っています。


ご覧いただきありがとうございます。
ブログの最新情報はSNSでも発信しております。
ぜひTwitterのフォロー&Facebookページにいいねをお願い致します!



>> 雑誌等の執筆依頼を受付しております。
   ご希望の方はお気軽にお問い合わせください!

Be the first to comment

Leave a Reply

Your email address will not be published.


*


質問はこちら 閉じる