最終更新日: 2025 年 9 月 10 日
概要
このドキュメントでは、TS.43 電話番号確認を介して携帯通信会社を Firebase 電話番号確認(FPNV)にオンボーディングするための必須の手順をすべて説明します。
用語
関係者
- CSP: 通信サービス プロバイダ
- 例: 携帯通信会社
- アグリゲータ
- アプリ向けアグリゲータ: アプリが携帯通信会社と直接やり取りすることなく検証を実行できるようにするアグリゲータ
- (例: Firebase 電話番号の確認)
- Meta-Aggregator: アプリ向けアグリゲータにオンボーディングするキャリアをサポートするアグリゲータ
- メタ アグリゲータは、携帯通信会社の利用資格サーバーの設定、およびアプリ向けアグリゲータによる利用資格サーバーの詳細の構成を担当する場合があります。
- FPNV: Firebase 電話番号認証
- Google TAM: Google のテクニカル アカウント マネージャー。携帯通信会社が FPNV にオンボーディングするのを支援します。
- Android Telephony: 携帯通信会社やアグリゲータが TS.43 検証を提供するためのプラットフォームなど、Android で電話番号 API を提供します。
- GSMA: TS.43 などの仕様を定義する携帯通信会社の団体
- CAMARA: GSMA と協力して通信事業者 API を定義する Linux オープンソース プロジェクト
確認の利用規約
- PNV: 電話番号の確認
- TS.43: モバイル クライアントとサーバーが HTTP を使用して携帯通信会社と通信するためのプロトコルを定義します。
- EAP-AKA: https://www.rfc-editor.org/rfc/rfc4187 で定義されている認証方法。ユーザーとのやり取りは不要です。
- ECS: Entitlement Configuration Server(利用資格構成サーバー)
- アグリゲータが携帯通信会社と通信するためのエントリ ポイント
- ODSA: オンデバイス サービス アクティベーション
- デバイスでサービスを有効にするために ECS によって提供されるさまざまなオペレーションを指します。
- 例: AcquireTemporaryToken、GetPhoneNumber
携帯通信会社の利用資格サーバーと PNV エンドポイント
必要なエンドポイントの作成
アクション 1: 携帯通信会社は、インターネット経由でアクセス可能な次のエンドポイントを実装します。実装の詳細については、付録 A をご覧ください。
技術要件
一般的なパフォーマンス: すべてのエンドポイントの稼働時間は 99.99% 以上とします。
セキュリティ: セキュリティ上の理由から、携帯通信会社のエンドポイントは次の要件を満たす必要があります。
- EAP-AKA 認証トークン: 1 時間以内に期限切れになる必要があります
- 一時トークン: 1 回限りの使用で、有効期限は 5 分
- オプション 1 - バニラ TS.43
- OAuth トークン: 1 時間以内に期限切れにする必要があります
- オプション 2 - CAMARA
- CAMARA アクセス トークン: 1 回限りの使用で、有効期限は 5 分
API データ品質: 成功したレスポンスの内容の 100%(つまり、MSISDN が正確である必要があります)。
FPNV は、TS.43 の 2 つのフレーバーをサポートしています。主な違いは、FPNV サーバーが TempToken を携帯通信会社と交換する方法です。
- バニラ TS.43: TS.43 仕様で規定されている実装を指します。
- CAMARA: CAMARA の JWT ベアラー フローで規定されている実装を指します。
オプション 1 - バニラ TS.43 実装
Android デバイスからのリクエスト
- EAP-AKA エンドポイント: 認証トークンを返します
- AcquireTemporaryToken エンドポイント: 認証トークンを指定すると、TempToken を返します
FPNV サーバーからのリクエスト
- OAuth 2.0 エンドポイント - OAuth クライアント ID/シークレット フロー: OAuth クライアント ID/シークレットを指定すると、OAuth アクセス トークンを返します。
- GetPhoneNumber エンドポイント: OAuth アクセス トークンと TempToken が指定された場合、対応する電話番号を返します。
オプション 2 - CAMARA の実装
CAMARA の実装は、FPNV サーバーからのリクエストを処理するエンドポイントを除き、バニラ TS.43 の実装と似ています。
Android デバイスからのリクエスト
- EAP-AKA エンドポイント: 認証トークンを返します
- AcquireTemporaryToken エンドポイント: 認証トークンを指定すると、TempToken を返します
FPNV サーバーからのリクエスト
- OAuth 2.0 エンドポイント - JWT Bearer フロー: TempToken を含む JWT が指定された場合、CAMARA アクセス トークンを返します
- CAMARA NumberVerification v2 エンドポイント: CAMARA アクセス トークンを指定すると、対応する電話番号が返されます。
Android Telephony と FPNV へのオンボーディング
携帯通信会社のテストアプリ
アクション 2: 携帯通信会社が Google テクニカル アカウント マネージャー(TAM)に連絡します。TAM は FPNV 携帯通信会社テストアプリを携帯通信会社と共有します。この携帯通信会社テストアプリは、FPNV サーバーを介さずに、FPNV によって送信されるリクエストを模倣します。この携帯通信会社テストアプリは、携帯通信会社がエンドポイントが正しく機能していることを検証するのに役立ちます。
ACTION3: 携帯通信会社は、FPNV 携帯通信会社テストアプリを使用して、上記のエンドポイントがエンドツーエンドで動作することを確認します。
必要な本番環境構成を設定する
Android 構成 - EAP-AKA / AcquireTempToken
ACTION4: 携帯通信会社は、Android Telephony からの EAP-AKA/AcquireTempToken リクエストのプロダクション設定を定義します
- 構成:
- この携帯通信会社の Android Canonical Carrier ID
- TS.43 use_cases の値:
use_case=GetPhoneNumber - EAP-AKA/AcquireTempToken の本番環境の利用資格サーバーの URL
- Firebase の本番環境用 x509 証明書の SAN とフィンガープリント
- SAN:
fpnv.googleapis.com - 指紋:
aad068c93399a22fc2b11ab58468e8cb72b8f9fc53700991799a8b764c589c7e
Firebase Config - TempToken を Phone と交換
ACTION5: 携帯通信会社から OAuth トークンを取得するための Firebase 認証情報
- Vanilla TS.43
- 携帯通信会社は、FPNV のリクエスト用に OAuth クライアント ID とシークレットを作成します。その後、携帯通信会社は、これらの認証情報のアクセス トークンを返すように OAuth エンドポイントを構成します。
- CAMARA
- Google TAM は Google の公開鍵を提供します。これにより、携帯通信会社の OAuth エンドポイントは JWT が Google によって署名されたことを確認できます。
アクション 6: 携帯通信会社が、電話の TempToken を交換するための FPNV サーバーのプロダクション構成を定義する
- この MNO の Android 正規携帯通信会社 ID
- Vanilla TS.43
- OAuth - クライアント ID/シークレット フロー
- OAuth エンドポイント URL
- OAuth クライアント ID/シークレット
- OAuth スコープ(ある場合)
- GetPhoneNumber
- GetPhoneNumber エンドポイントの URL
- CAMARA
- OAuth - JWT Bearer フロー
- OAuth エンドポイント URL
- NumberVerification API v2
- NumberVerification エンドポイントの URL
認証情報/構成の共有
Firebase 電話番号の確認
アクション 7: 携帯通信会社は、アクション 4 とアクション 6 の本番環境設定を Google のテクニカル アカウント マネージャーと共有します。
- [重要] OAuth シークレットは、安全なアウトオブバンド(メールやドキュメントなどを使用しない)メカニズムを使用して Google と共有する必要があります。この帯域外メカニズムは、携帯通信会社と Google TAM の間で合意されます。
アクション 8: Google TAM は、携帯通信会社のテストアプリを使用して、構成がエンドツーエンドで機能することを検証します。その後、Google TAM は OAuth 認証情報を Google の安全なストレージに保存し、FPNV の構成を更新して、TempToken を電話番号と交換します(アクション 6 の構成)。
Android Telephony
アクション 9: 携帯通信会社は「Google Open Gateway CSP オンボーディング」ドキュメント(Google TAM が携帯通信会社と共有)に沿って対応します。携帯通信会社または Google TAM が、Android Telephony の設定にオンボーディングするための Buganizer チケットを提出します: https://issuetracker.google.com/issues/new?component=1861595&template=2168610。このバグは、ACTION4 から本番環境の構成を取得します。
メタアグリゲーターが運送業者の代理で FPNV 統合を設定する場合は、運送業者のリーダーシップ(ディレクター以上)からの同意書(メール、PDF、手紙など)で、当該事業者とのビジネス関係を確認する必要があります。その後、メタアグリゲータは、携帯通信事業者に代わって Android Telephony に携帯通信事業者の設定を提供できます。
付録 A. 詳細な実装
大文字と小文字の区別
- HTTP ヘッダーでは大文字と小文字が区別されません
- ただし、XML 形式と JSON 形式では大文字と小文字が区別されます。リクエスト/レスポンス フィールドについては、フィールドがこのドキュメントと完全に一致していることを確認してください。
ステップ 1 - EAP-AKA / AcquireTempToken
エンドポイント: EAP-AKA と AcquireTempToken は同じ ECS エンドポイントを使用する必要があります。
EAP-AKA チャレンジ
参照: TS.43 v12.0 - Section 2.8.1 - 「Embedded EAP-AKA Authentication by Entitlement Configuration Server」。
EAP-AKA ステップ 1 - 認証チャレンジ
EAP-AKA #1 - ECS への GET リクエスト
Android Telephony モジュールは、携帯通信会社の利用資格サーバーに TS.43 EAP-AKA リクエストを送信します。
Android のリクエスト ヘッダー
Accept:application/vnd.gsma.eap-relay.v1.0+json- これは
application/jsonだけでなく、GSMA 固有の JSON 形式です。
- これは
Android のリクエスト フィールド
eap_id: RCC.14 付属書 C を参照してください。- 例:
0<IMSI>@<realm>.mnc<MNC>.mcc<MCC>.3gppnetwork.org
- 例:
GID1: 利用資格のバージョンが 12.0 の場合にのみ指定されますapp_name: エンコードされた AppName には、電話番号の確認を行うユースケースの MD5 ハッシュ値が含まれます。- アプリ向けのすべてのアグリゲーター リクエストのアプリ名は
Google-OGIになります。
- アプリ向けのすべてのアグリゲーター リクエストのアプリ名は
app: アプリ IDap2014は電話番号情報を表しますterminal_vendor/model/sw_version: 任意の値に設定します。Android は、これらのフィールドに実際のデバイスの情報が含まれることを保証しません。vers: 構成バージョン(0 や 1 など)entitlement_version: 携帯通信会社に送信される利用資格のバージョンは、携帯通信会社の要求に基づいて Google が構成します。- 通常、
entitlement_versionは 10.0 または 12.0 です。
- 通常、
EAP-AKA #1 - ECS からのレスポンス
ECS レスポンス ヘッダー
Content-Type: Android は、レスポンス タイプがリクエストの Accept ヘッダーと一致することを想定しています。- 例:
application/vnd.gsma.eap-relay.v1.0+json
- 例:
ECS レスポンス フィールド
eap-relay-packet: RCC.14 - セクション C.2 に準拠した EAP パッケージを含みます。
EAP-AKA ステップ 2 - 認証トークンを取得する
EAP-AKA #2 - ECS への POST リクエスト
Android Telephony モジュールは、受信した eap-relay-packet を同じエンドポイントに送り返します。
Android のリクエスト ヘッダー
Accept: Android は 2 つの Accept ヘッダーを設定します。application/vnd.gsma.eap-relay.v1.0+json: デバイスが EAP-AKA リクエストを再度送信する必要がある場合、キャリアが JSON を再度返すことを指します。text/vnd.wap.connectivity-xml: 携帯通信会社が EAP-AKA 認証トークンを返す際に Android が想定する実際の形式を指します。
Content-Type:application/vnd.gsma.eap-relay.v1.0+json
Android のリクエスト フィールド
eap-relay-packet: 前の EAP-AKA レスポンスの eap-relay-packet を含みますが、RFC 4817 - セクション 9.2 に従った EAP-Response/AKA-Challenge 形式です。
EAP-AKA #2 - ECS からのレスポンス
EAP-AKA 認証に成功すると、携帯通信会社は認証トークンを返します。
ECS レスポンス ヘッダー
Content-Type: Android は、リクエストの Accept ヘッダーに一致するレスポンスを想定しています。- つまり、Android は、認証トークンを含むレスポンスの型が
text/vnd.wap.connectivity-xmlであることを想定しています。 - もう 1 つの Accept ヘッダー
application/vnd.gsma.eap-relay.v1.0+jsonは、携帯通信会社が Android に別の EAP-AKA リクエストを実行させたい場合に使用します。
- つまり、Android は、認証トークンを含むレスポンスの型が
ECS レスポンス フィールド
TOKEN.token: 認証トークンが含まれますTOKEN.validity: デバイスがレスポンスを受信してからレスポンスが有効になるまでの秒数- Google は、認証トークンが技術要件を満たしていることを検証します。
AcquireTemporary Token
AcquireTempToken - ECS への GET リクエスト
Android クライアントは、EAP-AKA から受け取った認証トークンを使用して、携帯通信会社の AcquireTemporaryToken エンドポイントを呼び出し、一時トークンを取得します。リクエスト
- 例: TS.43 v12.0 - Section 6.4.6 - "AcquireTemporaryToken Request Example"
- AcquireTempToken は、EAP-AKA #1 と同様のパラメータを持ちますが、次の点が異なります。
- AcquireTempToken は
IMSI, operationとoperation_targetsも指定します。 - AcquireTempToken が
EAP_IDを指定していない
- AcquireTempToken は
Android のリクエスト ヘッダー
Accept: Android がtext/vnd.wap.connectivity-xmlを設定します
Android のリクエスト フィールド
terminal_vendor/model/sw_version: Android は、これらのフィールドに実際のデバイスの情報が含まれることを保証しません。operation_targets- FPNV: オペレーションのターゲットは
GetPhoneNumber
- FPNV: オペレーションのターゲットは
AcquireTempToken - ECS からのレスポンス
例: TS.43 v12.0 - Section 6.6.6 - "AcquireTemporaryToken Response Example"
ECS レスポンス ヘッダー
Content-Type: Android は、レスポンス タイプがリクエストの Accept ヘッダーと一致することを想定しています。- 例:
text/vnd.wap.connectivity-xml
- 例:
ECS レスポンス フィールド
APPLICATION.TemporaryToken: FPNV サーバーが電話番号と交換できる TemporaryTokenAPPLICATION.TemporaryTokenExpiry: YYYY-MM-DDThh:mm:ssTZD 形式の有効期限- Google は、TempToken の有効期限が技術要件を満たしていることを検証します。
APPLICATION.OperationResult: TS.43 v12.0 - Section 6.5.1 を参照してください。- 具体的には、オペレーションが
SUCCESSの場合は 1 を返します。
- 具体的には、オペレーションが
ステップ 2 - TempToken を電話番号と交換する
オプション 1 - バニラ TS.43
エンドポイント: OAuth エンドポイントと GetPhoneNumber エンドポイントは、それぞれ異なるサーバー/エンドポイントにすることができます。これらのエンドポイントは、EAP-AKA/AcquireTempToken エンドポイントと異なる場合もあります。
OAuth
携帯通信会社は、この OAuth ガイドに沿って、必要な OAuth 情報(クライアント ID、クライアント シークレット、OAuth サーバー URL)を Google に提供する必要があります。
OAuth - 携帯通信会社の認証サーバーへの POST リクエスト
FPNV リクエスト ヘッダー
Authorization: FPNV はBasic $BASE64_ENCODED_CREDENTIALSを設定します。- Base64 でエンコードされた認証情報は、OAuth
$CLIENT_ID:$CLIENT_SECRETの Base64 エンコードです。
- Base64 でエンコードされた認証情報は、OAuth
Content-Type: FPNV がapplication/x-www-form-urlencodedを設定しますAccept: FPNV がapplication/jsonを設定します
FPNV リクエスト フィールド
grant_type:client_credentials
POST HTTP/1.1
Host: $OAUTH_ENDPOINT
Authorization: Basic $BASE64_ENCODED_CREDENTIALS
Content-Type: application/x-www-form-urlencoded
Accept: application/json
grant_type=client_credentials
OAuth - 携帯通信会社の認証サーバーからのレスポンス
携帯通信会社のレスポンス ヘッダー
Content-Type: FPNV は、レスポンス タイプがリクエストの Accept ヘッダーと一致することを想定しています。- 例:
application/json
- 例:
携帯通信会社のレスポンス フィールド
access_token: OAuth アクセス トークンtoken_type:bearerexpires_in: OAuth アクセス トークンの有効期限(秒単位)- Google は、OAuth トークンの有効期限が技術要件を満たしていることを検証します。
200 OK
Content-Type: application/json
{
"access_token": $ACCESS_TOKEN,
"token_type": "bearer",
"expires_in": $EXPIRATION_IN_SECS,
}
GetPhoneNumber
GetPhoneNumber - ECS への POST リクエスト
Google 確認サーバーは、GetPhoneNumber オペレーションを使用して電話番号を取得します。
- 例: TS.43 v12.0 - セクション 6.4.7 - 「GetPhoneNumber Request Example」
FPNV のリクエスト ヘッダー
Accept:application/jsonContent-Type:application/json
FPNV のリクエスト フィールド
requestor_id: GetPhoneNumber TS.43 オペレーションを呼び出すサービスを識別します。- Firebase 電話番号確認 UUID:
191fd7cc-f7cd-4bb4-a5d2-455ae1fb9a19
- Firebase 電話番号確認 UUID:
temporary_token: AcquireTempToken からの TemporaryTokenaccess_token: Google が携帯通信会社との認証に使用する OAuth トークンterminal_vendor/model/sw_version: FPNV はこれらのフィールドに任意の値を入力します。entitlement_version: 携帯通信会社に送信される利用資格のバージョンは、携帯通信会社の要求に基づいて Google が構成します。- 通常、
entitlement_versionは 10.0 または 12.0 です。
- 通常、
app: FPNV がap2014を設定しますapp_name: FPNV は、すべての FPNV リクエストに対してfirebaseを設定します。- 注: 使用するアグリゲータに関係なく、AcquireTempToken の
app_nameはGoogle-OGIになります。
- 注: 使用するアグリゲータに関係なく、AcquireTempToken の
operation: FPNV がGetPhoneNumberを設定します
GetPhoneNumber - ECS からのレスポンス
例: TS.43 v12.0 - Section 6.6.7 - 「GetPhoneNumber Response Example」
携帯通信会社のレスポンス ヘッダー
Content-Type: FPNV は、レスポンス タイプがリクエストの Accept ヘッダーと一致することを想定しています。- 例:
application/json
- 例:
携帯通信会社のレスポンス フィールド
ap2014.MSISDN: FPNV は、電話番号が E164 形式で返されることを想定しています。- JSON では大文字と小文字が区別されるため、MSISDN は大文字にする必要があります
TemporaryToken エラーコード
TS.43 v12.0 のセクション 2.8.6 からの参照。
次の表に、ECS が GetPhoneNumber リクエストに対して Google 検証サーバーに返すことが想定されるエラー レスポンスの詳細を示します。
シナリオ |
ECS からの GET/POST レスポンス コード |
サードパーティ サーバー アクション |
リクエストのパラメータが無効であるか、不明であるか、形式が間違っている |
400 Bad Request(不正なリクエスト) |
次のユーザー呼び出し時 / クライアントの再起動後に再試行 |
リクエストの Temporary Token が無効または期限切れ |
401 Unauthorized(未承認) |
可能であれば、デバイスをトリガーして ECS から(新しい)有効な一時トークンを取得します |
一時トークンとの組み合わせで無効なオペレーションが検出されました |
403 Forbidden(アクセス拒否) |
次のユーザー呼び出し時 / クライアントの再起動後に再試行 |
リクエストされたリソースが見つかりません |
404 Not Found |
次のユーザー呼び出し時 / クライアントの再起動後に再試行 |
リクエストの処理中に ECS で内部エラーが発生する |
500 Internal Server Error(内部サーバーエラー) |
次のユーザー呼び出し時 / クライアントの再起動後に再試行 |
オプション 2 - CAMARA
エンドポイント: CAMARA アクセス トークンの取得と電話番号の取得は、それぞれ異なるサーバー/エンドポイントで行うことができます。これらのエンドポイントは、EAP-AKA / AcquireTempToken エンドポイントと異なる場合もあります。
OAuth - CAMARA アクセス トークンを取得する
Google は、CAMARA の JWT ベアラー フローのみをサポートし、CIBA フローはサポートしません。
CAMARA アクセス トークン - 携帯通信会社への POST リクエスト
Google は、次のフィールドを含む JWT を作成します。
iss: JWT の発行者(クライアント ID)- (
firebase(実際の FPNV 統合)またはfpnv-carrier-tester-app(携帯通信会社のテストアプリ)など)
- (
sub: JWT のサブジェクト- 例:
operatortoken:$TEMP_TOKEN
- 例:
aud: オーディエンス。JWT の対象となる受信者- トークン エンドポイントの URL(認証サーバーの URL)
exp: 有効期限(秒単位)- Google は、CAMARA アクセス トークンの有効期間(技術要件を参照)に一致する有効期限を送信します。
iat: 発行時刻(秒単位)jti: リプレイ攻撃を回避するための固有識別子- 例: ランダムに生成された UUID
scope: リクエストの目的- 例:
dpv:FraudPreventionAndDetection number-verification:device-phone-number:read
- 例:
{
"iss": "firebase",
"sub": "operatortoken:ey...",
"aud": $OAUTH_ENDPOINT,
"exp": $EXPIRATION_TIME_IN_SECS,
"iat": $ISSUED_AT_TIME_IN_SECS,
"jti": $RANDOMLY_GENERATED_UUID,
"scope": "dpv:FraudPreventionAndDetection number-verification:device-phone-number:read"
}
FPNV は独自の秘密鍵を使用して JWT に署名し、携帯通信会社は対応する公開鍵を使用して JWT を検証できます。FPNV は、JWKS エンドポイントを使用して公開鍵を提供します。FPNV は定期的に(30 日に 1 回など)公開鍵をローテーションするため、携帯通信会社はこの JWKS エンドポイントを定期的にポーリングして公開鍵を取得する必要があります(1 日に 1 回など)。
FPNV のリクエスト ヘッダー
Content-Type:application/x-www-form-urlencodedAccept:application/json
FPNV のリクエスト フィールド
grant_type:urn:ietf:params:oauth:grant-type:jwt-bearerassertion: 上記で作成され、FPNV の秘密鍵で署名された JWT- この JWT には TempToken が含まれています。
POST /token.oauth2 HTTP/1.1
Host: as.example.com
Content-Type: application/x-www-form-urlencoded
Accept: application/json
grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer
&assertion=$JWT
CAMARA アクセス トークン - 携帯通信会社からのレスポンス
携帯通信会社のレスポンス ヘッダー
Content-Type: FPNV は、レスポンス タイプがリクエストの Accept ヘッダーと一致することを想定しています。- 例:
application/json
- 例:
携帯通信会社のレスポンス フィールド
access_token: CAMARA アクセス トークン。後で電話番号と交換できますtoken_type:bearerexpires_in: OAuth アクセス トークンの有効期限(秒単位)- Google は、OAuth トークンの有効期限が技術要件を満たしていることを検証します。
scope: リクエストの目的- 例:
dpv:FraudPreventionAndDetection number-verification:device-phone-number:read
- 例:
200 OK
Content-Type: application/json
{
"access_token": $CAMARA_ACCESS_TOKEN,
"token_type": "bearer",
"expires_in": $EXPIRATION_IN_SECS,
"scope": "dpv:FraudPreventionAndDetection number-verification:device-phone-number:read"
}
CAMARA NumberVerification API v2
その後、Google は、携帯通信会社の /device-phone-number エンドポイントに GET リクエストを送信して、その CAMARA アクセス トークンを交換します。
CAMARA NumberVerification - 携帯通信会社への GET リクエスト
FPNV のリクエスト ヘッダー
Authorization:Bearer $CAMARA_ACCESS_TOKENAccept:application/json
GET /device-phone-number
Authorization: Bearer $CAMARA_ACCESS_TOKEN
Accept: application/json
Content-Type: application/json
CAMARA NumberVerification - 携帯通信会社からのレスポンス
携帯通信会社のレスポンス ヘッダー
Content-Type: FPNV は、レスポンス タイプがリクエストの Accept ヘッダーと一致することを想定しています。- 例:
application/json
- 例:
携帯通信会社のレスポンス フィールド
devicePhoneNumber: 電話番号を E164 形式で返します
200 OK
Content-Type: application/json
{
"devicePhoneNumber": $PHONE_NUMBER
}