Passkeyを調査する
OAuth2.0とOIDC, SSOLogin, FIDO2, Passkeysの違い
各技術の違いを踏まえて、以下に説明します。
1. OAuth 2.0
OAuth 2.0は、リソース所有者(例えば、ユーザー)がサードパーティーアプリケーションに自分のリソース(例:GoogleのカレンダーやFacebookのプロフィール情報)へのアクセスを許可するためのフレームワークです。OAuth 2.0は、アクセス権限の委任を扱うプロトコルで、サードパーティーアプリケーションがリソースサーバー(例えばGoogle)からリソースを取得できるようにします。
2. OpenID Connect (OIDC)
OIDCは、OAuth 2.0をベースにした認証プロトコルです。OAuth 2.0が認可(権限付与)にフォーカスしているのに対して、OIDCは認証に焦点を当てています。これにより、ユーザーが誰であるかを識別するためにトークンを用いて、クライアントアプリケーションに対してユーザーの認証情報を安全に提供します。簡単に言えば、OAuth 2.0を拡張してユーザー認証を行うのがOIDCです。
3. SSO (Single Sign-On) Login
SSOは、複数のサービスに対して一度のログインでアクセスできるようにする仕組みです。ユーザーは一度認証するだけで、他の関連サービスにもアクセスできるようになります。SSOはOAuth 2.0やOIDCを活用して実装されることが多いです。例えば、Googleアカウントでログインすると、GmailやYouTubeなどの他のGoogleサービスにもアクセスできるのがSSOの例です。
4. FIDO2
FIDO2は、パスワードレス認証を実現するためのオープン標準です。従来のパスワードに代わる生体認証(指紋や顔認証など)やセキュリティキー(例えばYubiKey)を使用して、認証を行います。FIDO2は、WebAuthn(Web Authentication API)とCTAP(Client to Authenticator Protocol)という2つの主要なプロトコルで構成されています。FIDO2により、フィッシング攻撃などを防ぎ、より安全な認証が可能になります。
5. Passkeys
Passkeysは、FIDO2標準に基づいた技術で、パスワードの代替として、ユーザーのデバイス(スマートフォンなど)を使って安全にログインできる手段です。AppleやGoogleなどがこの技術を推進しており、パスキーはユーザーのデバイスに保存される秘密鍵と公開鍵のペアを使って認証を行います。Passkeysは、ユーザーがパスワードを覚える必要がなく、またフィッシングなどの脅威に対して非常に強力な防御策となります。
まとめ
- OAuth 2.0: 権限委任のためのフレームワーク。
- OIDC: OAuth 2.0に基づいた認証プロトコル。
- SSO: 一度のログインで複数のサービスにアクセスする仕組み。
- FIDO2: パスワードレス認証を実現するためのオープン標準。
- Passkeys: FIDO2標準に基づき、パスワードを使わずに安全に認証する手段。
これらの技術はそれぞれ異なる目的やシナリオに適用されますが、現代の認証システムを支える重要な要素です。
学習に使用した本や記事
-
FIDOやpasskeysの解説 FIDOアライアンス
https://fidoalliance.org/passkeys/?lang=ja -
passkeysとWebAuthnの違い (技術とライブラリ)
https://webauthn.me/passkeys -
GoでWebAuthnを使ってPasskeysを実装する方法
https://blog.cateiru.com/entry/2023/12/09/211516 -
GoでWebAuthnを使ってPasskeysを実装する方法
https://zenn.dev/shibata/articles/750e521e7050f2 -
雰囲気でOAuth2.0を使っているエンジニアがOAuth2.0を整理して、手を動かしながら学べる本
https://authya.booth.pm/items/1296585 -
go-webauthn GitHub
https://github.com/go-webauthn/webauthn?tab=readme-ov-file
PasskeysとSSOの使い分け
大部分のアカウントを SSO で保護し、その他のアカウント (SSO アカウントを含む) を強力なパスキーで保護します。
うまく連携する機能といえば、多くの SSO プロバイダーでは、従来のユーザー名とパスワードの組み合わせではなく、パスキーを使用してサインインできます。つまり、組織は SSO の管理権限を維持しながら、従業員が弱いパスワードや使い古されたパスワードを使用するリスクを軽減できます。
2 つのシステムは連携して機能し、ビジネス全体のセキュリティ確保の負担を軽減します。大部分のアカウントを SSO で保護し、その他のアカウント (SSO アカウントを含む) を強力なパスキーで保護します。
例:
SSO を使用して 1Password のロックを解除し、1Password (現在はベータ版)を使用してパスキーでアカウントを作成、保存、サインインします。
SaaSに取り入れるとしたら
-
評価軸
- 利用者がより素早く、簡単にログインできるか
-
toBの場合
- 顧客企業では管理のためにIdPを導入していることが多く、SSO Loginに対応することで従業員側はシームレスに、管理者側はIdPのみを管理すれば良くなり手間が省ける。
- SaaSへのログインはSSO Loginしつつ、IdPへのログインをPasskeysにすることで従業員が脆弱なパスワードを使いまわすことを防げセキュリティリスクを減らせる。しかもパスワードリセット業務がなくなる。
- 従業員としてもパスワードを覚える必要がなくなる。
-
toCの場合
docker compose の healthcheckでコンテナが落ち続ける
alpineイメージではcurlが入っていないため、healthcheckでcurlを実行しようとすると待ち状態になってコンテナ起動に失敗する。
RUN apk update && apk add --no-cache curl
を入れてあげると良い。
Passkey用のDBを考える
BE参考
謎にDev Toolでは表示されているCookieがresponse.header.get()で取れない
issueも上がっていたが、理由不明。
ライブラリで無理に取り出すSet CookieはサーバサイドでCookieを入れ込むことができる
Set Cookieは基本的にブラウザ側で触ることは出来ない。
次のリクエスト時にCookieとしてサーバサイド側に渡ってくる
完成
使ったライブラリ
-
webauthn
https://github.com/go-webauthn/webauthn?tab=readme-ov-file -
webauthn-json
https://github.com/github/webauthn-json
webauthnはFE, BE間で受け渡す値が複雑であるため、OpenAPIのschemaを書いているところのほうが少ない。
そのため、基本的にJSONそのまま渡して型を意識せずそのまま使用できるようにしたい。
それを実現するためにFEではJSONを型にparseしてくれるライブラリ webauthn-jsonを利用した。
もっとやりたいこと
passkeys用のDBスキーマを考えたいが、結構複雑であるため断念した。