WebAuthnとパスキー実装に関する開発者向けガイド。チートシートをPDFでダウンロードするか、このウェブサイトで一箇所に必要なすべての情報を確認できます。
Lukas R.
作成日: 2024年3月6日
更新日: 2026年7月3日

このページは自動翻訳されています。英語の原文は こちら.
完全版のパスキーチートシートを無料でダウンロードして、すべてのインサイトを手に入れましょう。
究極のパスキー開発者ガイド
プラットフォームのサポート、ブラウザの動作、UXのベストプラクティス、統合のヒントなど、パスキーのすべてを網羅した開発者向けリファレンスを入手してください。

パスキーによる認証は、登録(またはattestationフェーズ)とログイン(またはassertionフェーズ)と呼ばれる2つのプロセス(セレモニーとも呼ばれます)に基づいています。 各フェーズには、サーバーによって生成されたランダムなチャレンジが必要であり、これはAuthenticatorによって署名され、ユーザーを検証するためにWebAuthnサーバーに送り返されます。
Passkeys Debuggerでパスキーフローを試せます。
登録セレモニーでは、PublicKeyCredentialCreationOptionsとattestationという2つの中心的なオブジェクトを使用します。
ログインセレモニーでは、PublicKeyCredentialRequestOptionsとassertionという2つの中心的なオブジェクトを使用します。
実際にどれだけの人がパスキーを使っているか確認できます。
パスキーを使用した登録とログインには、主に4つのオブジェクトがあります。
このセクションでは、PublicKeyCredentialCreationOptionsで使用されるauthenticatorSelectionオブジェクトについても説明します。
Igor Gjorgjioski
Head of Digital Channels & Platform Enablement, VicRoads
We hit 80% mobile passkey activation across 5M+ users without replacing our IDP.
See how VicRoads scaled passkeys to 5M+ users — alongside their existing IDP.
Read the case studyPublicKeyCredentialCreationOptionsは、attestationフェーズ(登録)の中心的なオブジェクトです。これはWebAuthnサーバーによって作成され、返されます。
{ "PublicKeyCredentialCreationOptions": { "rp": { "id": "passkeys.eu", "name": "Corbado Passkeys Demo" }, "user": { "displayName": "john.doe", "id": "dXNyLZ….DU10Tc", "name": "john@doe.com" }, "challenge": "888fix4Bus...pHHr3Y", "pubKeyCredParams": [ { "alg": -7, "type": "public-key" }, { "alg": -257, "type": "public-key" } ], "excludeCredentials": [], "authenticatorSelection": { "authenticatorAttachment": "platform", "residentKey": "required", "userVerification": "required" }, "attestation": "none", "extensions": {} } }
このオブジェクトには以下の属性が含まれます。
最新ニュースを受け取るためにPasskeys Substackを購読しましょう。
PublicKeyCredentialRequestOptionsは、assertionフェーズ(ログイン)の中心的なオブジェクトです。これはWebAuthnサーバーによって作成され、返されます。
{ "publicKeyCredentialRequestOptions": { "challenge": "pT7HMA-…dFPHk", "timeout": 500, "rpId": "passkeys.eu", "userVerification": "preferred", "allowCredentials": [], "extensions": [] } }
このオブジェクトには以下の属性が含まれます。
Attestation / 登録セレモニー中、Authenticatorはこの登録レスポンスを返します。Passkeys Debuggerでご自身でお試しいただけます。
{ "authenticatorAttachment": "platform", "id": "JKZbixUfKN_aZtimefYT-OjH5dw", "rawId": "JKZbixUfKN_aZtimefYT-OjH5dw", "response": { "attestationObject": { "fmt": "none", "attStmt": {}, "authData": { "rpIdHash": "PpZrl-Wqt-OFfBpyy2SraN1m7LT0GZORwGA7-6ujYkM", "flags": { "userPresent": true, "userVerified": true, "backupEligible": true, "backupStatus": true, "attestedData": true, "extensionData": false }, "counter": 0, "aaguid": { "raw": "fbfc3007-154e-4ecc-8c0b-6e020557d7bd", "name": "iCloud Keychain" }, "credentialID": "JKZbixUfKN_aZtimefYT-OjH5dw", "credentialPublicKey": "pQECAyYgASFYIPWLalDzyxIDmAADvfK8iNM5To50kh7TyPH-teEz8RMdIlgg3D7bPIWQJ8z-WFn3zdYZzJw9c7mhPdmflQqD9vV7efA", "parsedCredentialPublicKey": { "keyType": "EC2 (2)", "algorithm": "ES256 (-7)", "curve": 1, "x": "9YtqUPPLEgOYAAO98ryI0zlOjnSSHtPI8f614TPxEx0", "y": "3D7bPIWQJ8z-WFn3zdYZzJw9c7mhPdmflQqD9vV7efA" } } }, "clientDataJSON": { "type": "webauthn.create", "challenge": "k2p6f-upzP_hc6NZvmMAxiI0VSTeQIeXXVRGW62LTj0", "origin": "https://www.passkeys-debugger.io", "crossOrigin": false }, "transports": ["hybrid", "internal"], "authenticatorData": "PpZrl-Wqt-OFfBpyy2SraN1m7LT0GZORwGA7-6ujYkNdAAAAAPv8MAcVTk7MjAtuAgVX170AFCSmW4sVHyjf2mbYpnn2E_jox-XcpQECAyYgASFYIPWLalDzyxIDmAADvfK8iNM5To50kh7TyPH-teEz8RMdIlgg3D7bPIWQJ8z-WFn3zdYZzJw9c7mhPdmflQqD9vV7efA", "publicKey": "MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAE9YtqUPPLEgOYAAO98ryI0zlOjnSSHtPI8f614TPxEx3cPts8hZAnzP5YWffN1hnMnD1zuaE92Z-VCoP29Xt58A", "publicKeyAlgorithm": -7 }, "type": "public-key", "clientExtensionResults": {} }
attestationには、attestationObject、algorithm、transportフラグなどの重要なコンポーネントが含まれています。
W3CのWebAuthn仕様から引用
attestationObjectはCBORエンコードされたオブジェクトであり、新しく作成されたCredential、公開鍵、およびその他の関連データに関する情報を含みます。
extensionsについてもっと読む。
パスキーはCOSEアルゴリズムで生成され、attestationオブジェクトのparsedCredentialPublicKeyのalgorithm属性に使用されたアルゴリズムが示されます。 以下は、最も関連性の高いCOSEアルゴリズムの概要です。
transportsプロパティは、Authenticatorがクライアントと通信できるメカニズムを示します。一般的な値の組み合わせの例は以下の通りです。
Assertion / ログインセレモニー中、Authenticatorはこのログインレスポンスを返します。Passkeys Debuggerでご自身でお試しいただけます。
{ "id": "JKZbixUfKN_aZtimefYT-OjH5dw", "rawId": "JKZbixUfKN_aZtimefYT-OjH5dw", "type": "public-key", "authenticatorAttachment": "platform", "response": { "authenticatorData": { "rpIdHash": "PpZrl-Wqt-OFfBpyy2SraN1m7LT0GZORwGA7-6ujYkM", "flags": { "userPresent": true, "userVerified": true, "backupEligible": true, "backupStatus": true, "attestedData": false, "extensionData": false }, "counter": 0 }, "clientDataJSON": { "type": "webauthn.get", "challenge": "GCVkITWbe2l2dttsn_DgJYvH9QPHPDo0ygWgcgI6B7U", "origin": "https://www.passkeys-debugger.io", "crossOrigin": false, "other_keys_can_be_added_here": "do not compare clientDataJSON against a template. See https://goo.gl/yabPex" }, "signature": "MEQCIA-orC8N2KKWOxyY17BWP8lB-Be5to9btXRnJZf2SLhXAiBGxJe5Eu5LwOTbsyzAYmIXHOhlC3pN7s7Q1fRLvEW57g", "userHandle": "_FKz1uwqmR_3yGq6hJntzoIFwFC_d1u_53YRELh0KlE" } }
assertionには、flags、signature、userHandleなどの重要なコンポーネントが含まれています。
以下は、最も関連性の高いflagsとその組み合わせの概要です。
signatureは、ログインしようとしているユーザーが実際に秘密鍵を持っていることを検証するために使用されます。署名は、authenticatorDataとclientDataHash(つまり、ClientDataJSONのSHA-256バージョン)を連結し、(Authenticator内の)秘密鍵で結果に署名することによって作成されます。公開鍵で検証するには、authenticatorDataとclientDataHashも連結します。検証結果がtrueを返した場合、認証は成功です。
userHandleは実際のuser_idです。user_idの詳細については、セクション4.1 データベーススキーマを参照してください。
authenticatorSelectionオブジェクトを使用すると、サーバーは以下の値を使用してAuthenticatorとCredential作成の設定を指示できます。
Resident Key(Discoverable Credentialとも呼ばれます): Resident KeyはAuthenticatorに保存され、認証時に取得されます。この方法により、クライアントは可能なキーのリストを発見できるため、Conditional UIにはResident Keyが必要です。 Non-Resident Key(Non-Discoverable Credentialとも呼ばれます): Non-Resident Keyの場合、Credential IDはサーバーに保存され、認証時に提供されます。Credential IDは不透明な識別子(opaque identifier)であり、その内部構造は実装固有です。Authenticatorは秘密鍵を直接保存したり、暗号化されたキーラッピングを使用したり、内部シークレットから鍵を派生させたりすることがあります。正確なメカニズムはAuthenticatorの実装によって異なります。
警告: "Preferred"に設定されている場合、ユーザーまたはそのデバイスは認証プロセスでのユーザー検証をスキップできます(詳細はこの記事でご覧ください)。
Conditional UI(パスキーの自動入力)は、ユーザーがRelying PartyにResident Keyを登録している場合に、利用可能なパスキーをユーザー向けの選択ドロップダウンに表示します。パスキーのユーザビリティは向上しますが、追加の開発工数が必要であり、すべてのOSやブラウザの組み合わせで利用できるわけではありません。
通常のログインと同様に、Conditional UIもPublicKeyCredentialRequestOptionsとassertionのオブジェクトを使用します
Conditional UIは、(まだ)すべてのオペレーティングシステムとブラウザの組み合わせで利用できるわけではありません。以下は、現在のブラウザの対応状況の概要です(2024年3月時点)。
最新の概要については、このウェブサイトを参照してください。
Conditional UIメソッドの完全な最小限のコードは次のようになります。
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8" /> <meta name="viewport" content="width=device-width, initial-scale=1.0" /> <title>Conditional UI</title> </head> <body> <input type="text" id="username" autocomplete="username webauthn" /> <script> async function passkeyLogin() { try { // retrieve the request options (incl. the challenge) from the WebAuthn server let options = await WebAuthnClient.getPublicKeyRequestOptions(); const credential = await navigator.credentials.get({ publicKey: options.publicKeyCredentialRequestOptions, mediation: "conditional", }); const userData = await WebAuthnClient.sendSignedChallenge(credential); window.location.href = "/logged-in"; } catch (error) { console.log(error); } } passkeyLogin(); </script> </body> </html>
Conditional UIはResident Key / Discoverable Credentialでのみ機能します。 Conditional UIのログインを開始するには、個別のサーバーエンドポイントを提供することをお勧めします。 クライアントは複数の要件を満たす必要があります。
エラーを回避するために、サーバーはまず次の機能を使用してクライアントの可用性をテストする必要があります。
実際のトラフィックでは、検出やライフサイクルの問題がNotAllowedErrorやAbortErrorとして表面化することがよくあります。予期されるエラーと予期しないエラーの分類、およびネイティブCredential Managerのパスキーエラーについては、WebAuthnエラーガイドを使用してください。
// source: https://developer.mozilla.org/en-US/docs/Web/API/PublicKeyCredential/isConditionalMediationAvailable#examples // Availability of `window.PublicKeyCredential` means WebAuthn is usable. if (window.PublicKeyCredential && PublicKeyCredential.isConditionalMediationAvailable) { // Check if conditional mediation is available. const isCMA = await PublicKeyCredential.isConditionalMediationAvailable(); if (isCMA) { // Call WebAuthn authentication start endpoint let options = await WebAuthnClient.getPublicKeyRequestOptions(); const credential = await navigator.credentials.get({ publicKey: options.publicKeyCredentialRequestOptions, mediation: "conditional", }); /* ... */ } }
入力フィールドは、進行中のリクエストにパスキーを入力するようにクライアントに合図するHTML自動入力トークンを受け取る必要があります。パスキー以外にも、自動入力トークンは既存のトークン(ユーザー名やパスワードなど)と組み合わせることができます。
<label for="name">Username:</label> <input type="text" name="name" autocomplete="username webauthn" /> <label for="password">Password:</label> <input type="password" name="password" autocomplete="current-password webauthn" />
WebAuthnサーバーに必須または標準化されたデータベーススキーマはありません。しかし、このデータベーススキーマの例を使用して、必要な情報を保存し、WebAuthnサーバーのすべての機能を提供することができます。
太字の属性は必要最小限の実装に必須ですが、その他の属性はオプションですが役立つ機能にのみ必要です。
ユーザーDisplayName(user.displayName): ユーザーフレンドリーで読みやすい名前であり、通常はユーザーのフルネームです。ユーザーに表示されますが、認証中には使用されません。
ユーザー名(user.name): 一意で読みやすい名前であり、通常はメールアドレスまたはユーザー名です。ユーザーに表示できますが、認証中には使用されません。
**Relying Party ID(rpID)**はパスキー内に保存されるドメインであり、パスキーが正しいドメインでのみ機能することを保証します(ブラウザのURL、ネイティブアプリについてはこちらの記事を参照してください)。 認証中、rpIDはブラウザのURLと照合され、以下の2つのケースでのみ許可されます。
許可される(または許可されない)組み合わせの例を以下に示します。
以下は、パスキーを実装するための便利なツールとウェブサイトのリストです。
chrome://device-log経由でChromeでのみ利用可能)技術的な実装を超えてパスキーUXを最適化する戦略については、パスキー作成のベストプラクティスとパスキーログインのベストプラクティスに関するガイドをご覧ください。
数行のコードであらゆるアプリケーションにパスキーを実装したい場合は、Corbado Complete(新規アプリ向け)またはCorbado Connect(既存アプリ向け)を使用することもできます。
Corbadoは、大規模なconsumer認証を運用するCIAMチームのためのAuthentication Intelligence Platformです。IDPのログや一般的なanalyticsツールでは見えないものを可視化します。どのデバイス、OSバージョン、ブラウザ、credential managerがpasskeyに対応しているか、なぜ登録がログインにつながらないのか、WebAuthnフローのどこで失敗するか、OSやブラウザのアップデートがいつ静かにログインを壊すか — Okta、Auth0、Ping、Cognito、あるいは自社IDPを置き換えることなく、すべてを把握できます。2つのプロダクト:Corbado Observeは passkeyとその他あらゆるログイン方式のobservabilityを提供します。Corbado Connectは analytics内蔵のmanaged passkeyを追加します(既存のIDPと併用)。VicRoadsはCorbadoで500万人超のユーザーにpasskeyを提供しています(passkey有効化率+80%)。 Passkeyエキスパートに相談する →
Conditional UIを実装するには、認証を開始する前にPublicKeyCredential.isConditionalMediationAvailable()を使用してブラウザのサポートを確認する必要があります。入力フィールドにはautocomplete="username webauthn" HTMLトークンを含める必要があり、ユーザーはResident Key(Discoverable Credential)を登録している必要があります。Conditional UIのログインフローを処理するために、個別のサーバーエンドポイントを設けることを推奨します。
最低限、登録時にAuthenticatorによって生成されるCredential IDと、assertionオブジェクトのuserHandleとして返されるユーザーID(user_id)を保存します。Credential IDを使用して関連付けられたユーザーアカウントを検索し、userHandleを比較して認証を検証します。user.nameは時間の経過とともに変更される可能性があるため、比較に使用しないでください。
Resident Key(Discoverable Credential)はAuthenticator自体に保存され、認証時に取得されます。これはConditional UIが機能するために必要です。Non-Resident KeyはCredential IDをサーバーに保存し、認証時にそれをAuthenticatorに送信します。authenticatorSelectionのresidentKeyフィールドは、"required"、"preferred"、または"discouraged"の値でこの動作を制御します。
userVerificationフィールドは、ログイン時にAuthenticatorがユーザーを検証する必要があるかどうかを制御し、"required"、"preferred"(デフォルト)、または"discouraged"の値を受け入れます。"preferred"に設定されている場合、ユーザーまたはそのデバイスは認証プロセス中に検証を完全にスキップできるため、セキュリティが弱まる可能性があります。"required"に設定すると、認証が完了する前に常に検証が行われます。
関連記事
目次