メインコンテンツにスキップ

署名検証: 2026年のアプリケーションアップデートのセキュリティ

Learn how signature verification protects Capacitor and Electron app updates, covering cryptographic principles and CI/CD integration.

あなたのアップデートパイプラインは緑色です。エッジでバンドルが利用可能で、デバイスはそれをチェックしています。すると、誰かが生成されたJavaScriptに不審な変更を発見します。テストが終了した後、ビルドランナーが妨害された、開発者資格が盗まれた、またはアーティファクトが改ざんされた可能性があります。

署名検証 signature verification、チームが作成したバンドルと、攻撃者が転送中または配信層で変更したバンドルを区別する方法がないため、クライアントには信頼できる方法がない。

署名付きの更新では、この決定が変わる。デバイスは、現在実行中の code を置き換える前に、信頼された公開鍵を使用してバンドルを検証する。署名が一致しない場合、更新は非活性のままになる。そう思えるかもしれないが、生産的な障害は通常、暗号化にではなく、その中には起きる。チームは鍵の回転を追跡できなく、誤ったアーティファクトに署名する、または未検証のキャッシュファイルを適用する、または更新を拒否したデバイスの情報を収集するのに十分なテレメトリを集めることができないため、障害が起きる。

以下のセクションでは、信頼モデルと検証フロー、CI/CD制御、インシデント対応、署名自体で解決しない制限など、実際の運用上のエッジを焦点に置く。

目次

シグネチャ検証が大規模なアップデートを防ぐ理由

人気のあるCapacitorプラグインのCI/CDパイプラインはリリースプロセスの後期に侵害されます。 攻撃者はライブアップデートパッケージを変更し、codeを追加し、データを読み取るアプリケーションを追加し、パイプラインの通常の配信パスを使用してアーティファクトを公開します。 デバイスは不明なダウンロードドメインを認識しません。 それらは、インストールを待つ有効なアップデートを認識します。

検証がクライアント側で暗号化されていない場合、アプリは更新ポリシーが許可する限り、変更されたパッケージをダウンロードして実行します。 侵害の可能性の範囲には、データの漏洩、資格情報の盗用、支払いフローの変更、ビジネスロジックの静かな操作が含まれます。 検証はもはや痛みのある調査です。 エンジニアは、どのアーティファクトが提供されたか、どのチャネルが受信したか、どのデバイスがダウンロードしたか、どのデバイスが適用したか、そしてリリースが取り消された前に、悪意のあるcodeが実行されたかどうかを判断する必要があります。

ソフトウェアアップデート配信パイプラインにおける悪意のあるcodeの注入をブロックするシグネチャ検証の図

署名検証機能が有効なチームは、異なる失敗モードを取得します。アプリは同じ汚染されたバンドルをダウンロードし、予想されるハッシュ値を計算し、信頼されたキーと比較して付属する署名を検証します。暗号検証が失敗し、アップデートャーはバンドルを有効化せず、セキュリティチームにイベントが届く前に、新しいcodeが実行される前に。

生産ルール: デバイスが両方のアイデンティティとその精確なバイトを検証するまで、更新を敵対的扱いとしてください。

検証者がデバイス上で実行され、抽出または有効化前に実行され、信頼されたキーが更新自体によって置き換えられない場合にのみ、保護が機能します。そのため、証明書とキー管理はアップデート設計の一部であり、管理上の詳細ではありません。Capacitorを使用するチームは、この境界を含む証明書管理プロセスと共にドキュメント化する必要があります。 証明書管理プロセス署名検証を扱う研究は、数十年前から測定可能なエンジニアリング分野として扱われています。1977年に最初に公開されたオフラインとオンライン署名検証の研究は、後続の研究でHMMやFFTを含む方法が拡大されました。広く引用された比較によると、専門家は約0.5%の誤認と7%の誤認を達成したのに対し、一般人は約6.5%の誤認と26%の誤認を達成したとされています。

署名検証の歴史的概要 この文脈では、この文脈では、 この文脈では、この文脈では、 この文脈では、ハンドサインの数字は、ソフトウェアのアップデートとは関係ありませんが、有用な点を強調しています:検証の品質は検証者、検証元データ、決定ポリシーに依存します。

暗号署名による信頼の構築

リリースパッケージを想像してください。ビルドシステムは、パッケージ内の精確なバイト数のダイジェストを計算し、ダイジェストに 秘密鍵 を使用して、ダイジェストにデジタル署名を作成します。アプリケーションは、対応する 公開鍵を含む、または安全に受信します。この鍵は、封筒の知られている紋章のような役割を果たします。攻撃者がパッケージの小さな部分を変更すると、アプリケーションは異なるダイジェストを計算し、署名が検証されないことを意味します。

開発者が署名を作成し、モバイルアプリケーションが検証する暗号署名プロセスの図示。

プロセスは4つの異なる部分で構成されています。

  1. ハッシュ化 はパッケージを固定長のダイジェストに変換します。SHA-256とSHA-512は、この整合性ステップの一般的な選択肢です。
  2. 鍵生成 非対称ペアを作成します。プライベートキーは署名し、パブリックキーは検証します。
  3. 署名 ハッシュ値をリリースメタデータにバインドします。バージョン、チャネル、プラットフォーム、対象者を含めることが理想的です。
  4. 検証 ダウンロードされたバイトからハッシュ値を再計算し、信頼されたプライベートキーによって生成された署名が検証されます。

検証者は、アップデーターが適用する同じペイロードに署名をバインドする必要があります。マニフェストの署名だけでは、後でバンドルをダウンロードする際にマニフェストのハッシュ値がバンドルのハッシュ値と一致することを確認しないと、十分ではありません。同様に、バンドルのハッシュ値を検証するだけでは、ハッシュ値自体が認証されていない限り、誰が承認したかを確実に知ることはできません。

モバイル配信用のアルゴリズムの選択

RSAは馴染みのあるもので広くサポートされていますが、通常は大きいキー材料と慎重なパディングの選択が必要です。新しいモバイルアップデートプロトコルでは、Ed25519はしばしば魅力的な選択肢です。キーと署名はコンパクトで、モバイルプロセッサ上の検証パスも効率的です。RSA-PSSは、互換性の要件がRSAを必要とする場合に適切な選択肢でもあります。選択肢は、プラットフォームの暗号ライブラリ、サポートされているハードウェア、相互運用性の要件、移行計画に従うべきであり、別の環境からコピーしたベンチマークではありません。

モバイル配信用のアルゴリズムの選択 署名の理解のための独立した導入としては、このガイドをご覧ください。ブロックチェーンの署名の理解のためのガイドです。

トラストチェーンと固定鍵

Aの証明書チェーンは、根から中間認可機関を経由して葉の証明書にトラストを委譲します。このモデルは、広範なPKIオペレーションを簡素化できますが、アプリケーションアップデートクライアントは、通常、より狭い要件を持っています: このアップデートを承認したパブリッシャーキーだけを信頼することです。パブリックキー、または一連の承認されたキーのEmbeddingは、パブリッシャーキーがアプリケーションバイナリにすでに信頼されている場合、外部の証明書機関への依存性を削減しますが、バイナリがすでに置き換えキーの信頼を必要とするため、ローテーション問題を生み出します。

署名されたエンベロープを完全に維持してください。リリースメタデータは、アイテム、ダイジェスト、目的のチャネル、キー識別子を識別する必要があります。Capacitorを構築するチームは、このフォーカストークン署名チェックリストを使用して、Capacitorアプリをレビューすることができます。 token-signing checklist for Capacitor apps 署名検証は、モバイル製品のいくつかの層に現れ、各層は異なる質問に答えます。アプリストア署名は、オペレーティングシステムがインストール可能なパッケージが承認されたパブリッシャーから来ているかどうかを判断するのに役立ちます。署名されたOTAバンドルは、JavaScriptとアセットのペイロードがリリース機関によって信頼されているアップデートャーが信頼しているリリース機関によって発行されたかどうかを判断するのに役立ちます。JWT署名は、__CAPGO_KEEP_0__が期待どおりのアイデンティティサービスによって発行されたトークンであることを検証するのに役立ちます。

トラストチェーンと固定鍵

署名されたエンベロープを完全に維持してください。リリースメタデータは、アイテム、ダイジェスト、目的のチャネル、キー識別子を識別する必要があります。APIを構築するチームは、このフォーカストークン署名チェックリストを使用して、APIアプリをレビューすることができます。

混乱したレイヤーはギャップを生み出す。有効なIPA署名は、後続のウェブバンドの自動認証を保証しない。有効なJWTは、更新パッケージが安全であることを証明しない。TLS接続は輸送を保護するが、CDN、プロキシ、キャッシュ、またはビルドシステムが改ざんの元になる場合にアーティファクト署名を置き換えることはない。

コンテキスト 署名機構 失敗モード防止 一般的なギャップ
アプリストアパッケージ プラットフォームcode署名とプラットフォームレビュー制御 再署名または未承認のインストール可能パッケージ チームはストア署名がポストインストールのウェブアセットをカバーすることを想定している
ウェブバンドとサービスワーカー 署名済みエクスチェンジまたはSRIスタイルの整合性参照 毒性のCDNレスポンスまたは変更されたアセット エントリーファイルのみがチェックされ、インポートされたアセットは未検証のまま
API トークン 信頼された公開鍵を使用してJWT署名を検証する 偽造または改ざんされたトークン サーバーは署名を検証するが、発行者、受信者、有効期限、またはトークンの目的を無視する
オーバー・ザ・エア更新 デタッチドまたは埋め込まれたバンドル署名がデバイス上で検証される マニン・ザ・ミッドルまたは改ざんされた更新インジェクション クライアントは、決定を強制する前に、コンテンツをダウンロード、キャッシュ、または展開する

ウェブアセットの場合、サブリソースの整合性は、参照されたリソースを受け入れるブラウザを制限できますが、ダイナミックインポート、サービスワーカーキャッシュ、または更新マニフェストが攻撃者選択したファイルに指すことは自動的に解決しません。実装は、実行するバイトを検証するために、完全なアーティファクトセットを定義する必要があります。

JWTのデプロイは、異なる方法で失敗します。エンジニアは、正しい公開鍵を公開しますが、誤った発行者または受信者を持つトークンを受け入れるか、トークンヘッダから提供された暗号化アルゴリズムを信頼します。暗号化署名は有効であるかもしれませんが、承認決定はまだ間違っている可能性があります。

頻繁なリリースと顧客向けモバイルエクスペリエンスに依存する製品の運用上のコンテキストも重要です。評価中のチーム 2026年の小売アプリケーションエンゲージメント戦略 アップデートの整合性を迅速な実験の前提条件として扱うべきである。迅速なロールアウトは、リリースチャネル、アーティファクト、受信者がすべて同じ認可決定に結びついている場合にのみ有効である。

完全な検証フローの構築

生産用アップデータは検証をゲートとして行うべきであり、インストールの近くで実行されるコールバックではありません。安全なシーケンスは決定論的です:

  1. 認証されたトランスポート上でマニフェストと署名を取得します。
  2. マニフェスト構造、バージョンポリシー、チャネル、有効期限、そしてアーティファクトのアイデンティティを検証します。
  3. マニフェストによって指定された正確なバンドルをダウンロードします。
  4. ローカルでバンドルのダイジェストを計算します。
  5. 信頼できるEd25519またはRSA-PSS公開鍵に対して署名を検証します。
  6. 検証されたアーティファクトを隔離された場所に保存します。
  7. 原子的に適用し、ロールバックパスを保持します。

ソフトウェアアップデートバンドルの取得、署名検証、検証のプロセスを示す4ステップの図

manifestは決定に影響を与えるすべての値をバインドする必要があります。少なくとも、バンドルダイジェスト、バージョン、チャネル、プラットフォーム、キー識別子が必要です。ダウンローダーが検証後、URL、ファイル名、またはチャネルを置き換えることはできません。検証者は不変のバイトと不変のメタデータを受け取り、受け入れられたり拒否されたりする単一の結果を返す必要があります。

TypeScriptの簡略化された形は次のようになります。

type UpdateManifest = {
  version: string
  channel: string
  platform: string
  sha256: string
  signature: string
  keyId: string
}

async function verifyBundle(
  bundle: Uint8Array,
  manifest: UpdateManifest,
  trustedKeys: Map<string, Uint8Array>
): Promise<boolean> {
  const publicKey = trustedKeys.get(manifest.keyId)
  if (!publicKey) return false

  const digest = await sha256(bundle)
  if (!constantTimeEqual(digest, hexToBytes(manifest.sha256))) {
    return false
  }

  try {
    return await ed25519Verify(
      base64ToBytes(manifest.signature),
      digest,
      publicKey
    )
  } catch {
    return false
  }
}

この例は意図的に厳密です。Base64が不正形、不明なキー識別子、ダイジェストの不一致、署名の失敗など、拒否を生み出す原因となるものはすべて拒否します。ダウンロード中にタイムアウトが発生した場合、前の部分ファイルを適用することはありません。インコンプリートなアーティファクトを削除し、最後の知られている良好なバージョンを保存し、制限されたポリシー下で再試行します。

競合とロールバックミスを防ぐ

一時ディレクトリにダウンロードします。ファイルを閉じてフラッシュし、その完全な内容を検証し、バージョン化された検証済みストアにファイル名を変更します。アクティベーションステップは検証済みパスを参照するのみでなければなりません。CapacitorとElectron環境では、検証プロミス独立してアクティベーションをトリガーすることなく、非同期ダウンロード完了イベントを避ける必要があります。単一のアップデート状態マシンは、例えば downloading, verified, pending, active, rejectedrolled_back.

時間計算コストの比較は、敏感なバイトシーケンスを比較する場合に適切です。特に、攻撃者が繰り返し検証行動を観察できる場合に。実際には、重要な運用上の点では、前の試行でバージョンを利用可能としてマークした場合に、ショートカットを公開してはなりません。利用可能性と正当性は別々の状態です。

Capacitor のアップデートの整合性チェック は、ハッシュ検証とアクティベーションロジックを区別する実装の参考になります。失敗分岐を意図的にテストし、短縮されたファイル、不正な署名、未知のキー、古いマニフェスト、重複バージョン、プロセス終了時のアクティベーション中に。

自動署名検証の研究は、他のドメインで閾値と参照データの重要性を示しています。1994年のオンライン研究では、 22 の特性, 最も適切なものを選択し、 10、正しい署名の正しい分類を報告し、 99.5% の偽造を拒否する 86% の方法、 の出版された統計的方法の研究。ソフトウェアアップデートの検証は決定論的ではなく、生物学的ではありませんが、教訓はまだ関連しています: 決定境界を厳密に定義する必要があります。

Key Management Challenges Most Teams Underestimate

最初の署名キーは簡単です。2番目のキーは、設計が試される場所です。

チームはキーパリスを生成し、パブリックキーをアプリに配置し、最初のバンドルを1日で署名できます。数ヶ月後、エンジニアはラップトップにアクセスし、CIシークレットがビルドログに印刷され、署名ジョブがランナーからランナーに移動する必要があります。その時点で、「キーを回転するだけ」は、チェックインしないデバイスを捨てることを意味します。

比較グラフィックが示すように、シンプルな1回限りのキー設定と複雑で継続的な生産現実の間の違いを示しています。

最初のリリース前に設計に注目すべき3つの問題があります。

  • ローテーションなしの死角: 後継キーを必要とする前に、信頼できるキーに信頼を送信してください。署名されたキートランジションレコードは、既存の信頼されたキーが次のキーを承認できるようにし、定義されたマイグレーションウィンドウ内でアプリが古いキーを受け入れることができます。
  • 無保証の削除: アプリ内にピン留めされたキーは、OCSPまたはCRLスタイルの削除を自動的に提供しません。クライアントには署名された拒否リスト、最小許容するキーバージョン、またはサーバーが制御するポリシーが必要です。このポリシーは、ネットワークが利用できない場合でも安全です。
  • 制限付き署名アクセス: CIランナーのは、vaultまたはHSMから署名操作を要求するようにし、再利用可能なプライベートキーを平文の環境変数として受け取るのではなく、ログはコマンド出力を暗号化し、信頼できないブランチからプルリクエストを受け取った場合、生産環境の署名資格情報に到達しないようにする必要があります。

実際の運用状況: キー更新は更新問題です。更新メカニズムが安全に信頼性の変更を提供できない場合、キーが侵害された場合にクリーンに回復できないためです。

キー階層は爆発半径を減らします。ルート権威はリリースキーを承認できる一方、開発、ステージング、生産チャネルを別々のキーで署名します。シグニングの閾値は、生産リリースに必要な複数の承認されたパーティーを必要とすることで、盗まれた資格情報が有効な更新を作成するのを防ぎます。これらの制御はプロセスと遅延を追加するため、チームは更新の影響とチャネルの感受性に応じて適用する必要があります。

最初の信頼の基準は、モバイル更新の場合に特に弱いです。最初のキーがバンドルと同じチャネルから到着した場合、攻撃者がそのチャネルを制御している場合、両方を置き換えることができます。初期の信頼アナーカーは、初期の信頼アナーカーがアプリバイナリ、プラットフォーム保護された構成、または独立して認証されたパスで到着する必要があります。

For Capacitor teams, Capgo’s documented approach includes public-key pinning and key rotation support. The 安全なOTA更新のためのキー管理ガイダンス 更新サイクルを計画するのではなく、キー生成を一度のセットアップとして扱うのではなく、実践的なリファレンスとして提供します。

CI/CDと監視統合のための検証統合

リリーストランザクション内に署名を含める。パイプラインは、最初にバンドルを公開し、その後別の手動ステップで署名を追加することはしない。不可変アーティファクトをビルドし、そのハッシュ値を計算し、正確なバイトを署名し、クリーンな検証ステップで署名を検証し、最後にバンドルとメタデータを一つのリリースユニットとして公開する。

実用的パイプラインは、次のアーティファクトを生成する。

  • 不可変バンドル: クライアントがダウンロードするファイルであり、CDNが再パッケージするディレクトリではない。
  • マニフェスト: バージョン、チャネル、プラットフォーム、ハッシュ値、鍵識別子、ロールアウトポリシー。
  • 分離署名: canonicalマニフェストデータまたは正確に定義されたハッシュ値表現に対する署名。
  • 検証結果: 署名が環境の公開鍵と一致するかどうかを機械的に確認する。

GitHub ActionsとGitLab CIは、シンタックスが異なるにもかかわらず同じパターンを強制できる。署名サービスが不可用の場合、署名が不正である場合、または新しくダウンロードしたテストコピーが検証されない場合、署名ジョブは失敗する。デプロイジョブは、その結果に依存する必要があり、単にビルドが成功した場合にのみ依存する必要はない。

パスを署名せずに後で変更するのを許すのはやめましょう。署名後はアーティファクトをロックし、公開前にハッシュを比較し、リリースレコードから公開可能なマニフェストを作成します。これは、CIジョブが圧縮アーカイブを署名したのに、配信層が再圧縮または再生成されたファイルを提供した場合に発生する、意外と一般的な統合ギャップを捕捉します。

デバイス上で可視性を実現しましょう。

署名ジョブが成功すると、パイプラインが有効な署名を生成したことを証明しますが、デバイスが意図したバイトを受信したことや、意図したキーを使用したことを証明するものではありません。アプリのバージョン、更新バージョン、チャネル、プラットフォーム、キーID、結果カテゴリ、プライバシー安全なリリース関連IDとともに、検証結果を記録します。バンドル、トークン、プライベートメタデータ、ユーザーコンテンツをログに記録するのを避けましょう。

便利なダッシュボードでは、次の区別が可能です。

  • 署名失敗とダウンロード失敗を区別します。
  • ハッシュ不一致と不正なマニフェストを区別します。
  • 未知のキーとポリシー拒否を区別します。
  • アプリバージョン、リージョン、チャネル、リリース年齢による失敗を区別します。

突然のハッシュ不一致の集団は、汚染されたキャッシュ、変更された配信パス、またはアーティファクトの公開エラーを示唆します。未知のキーイベントは、不完全なローテーションまたは未承認のリリース試行を示唆します。検証テレメトリは、単独では攻撃者を特定することはできませんが、タイムラインと調査対象の人口を提供します。

__CAPGO_KEEP_0__ OTA更新のCI/CDセキュリティガイド Capacitor チームは、署名、検証、デプロイゲートを1つのワークフロー内に配置するのに役立ちます。重要な設計上の選択肢は所有権です。セキュリティは、検証が実行されたかどうかをエンジニアに尋ねる必要はありません。リリースレコードとクライアントのテレメトリは、その答えを直接提供する必要があります。

セキュリティのベストプラクティスと一般的な落とし穴

Signature verification should be a hard requirement for every update path that can execute code. The updater must verify before extraction, installation, or activation, and it must fail closed when the signature, digest, key, or policy check is unavailable.

このチェックリストを即時で使用してください。

  • プライベートキーを保護する 署名材料をHSMまたはマネージドバウルティに保持し、ソースコントロールにコミットしないでください。また、モバイルバイナリに配置しないでください。CIログに許可しないでください。
  • 信頼できる公開キーを固定する 初期の信頼アナーカーをアップデートペイロード外に格納する。複数のキーをサポートする場合は、その目的と移行ルールを定義する。
  • リリースを完全にバインドする 特定のバンドル、チャネル、プラットフォーム、意図されたポリシーを識別するためのcanonicalメタデータを署名する。
  • 検証エラーをすべて拒否する タイムアウト、不正な署名、不明なキー、または欠落したマニフェストは、前の未検証の結果を続行するための招待状ではありません。
  • テストの妥協回復: ステージングでキーのローテーション、削除されたキーの処理、ロールバック、中断されたダウンロード、および古いデバイスを実行します。
  • 検証者変更のレビュー: 暗号化ライブラリ、canonicalization、パース、フォールバック動作、およびデバッグ構成のためのセキュリティに焦点を当てたcodeレビューを必要とします。
  • デバッグ動作を分離する: デフォルトのフラグまたは環境ミスによって、開発者バイパスをプロダクションビルドにパッケージ化することは不可能でなければなりません。

署名も新鮮さ、受信者への結び付け、再送信抵抗、またはプロバイダーの現在の状態と互換性のあるペイロードが残っていることを証明するものではありません。ウェブホックのセキュリティガイドラインは、この区別を明確に示しており、最近の脆弱性報告では、不正確または null の署名とcanonicality の問題は、狭い検証チェックを乗り越えることができます。ウェブホックのセキュリティギャップ分析を設計する際の周辺の承認ルールに読み込むことが推奨されます。

閾値の選択は、生物学的システムに関連する教訓を生み出します。102 人の個人の 1,232 の署名と 62 のパラメトリック特性を使用した研究は、 62 parametric features on 1,232 signatures from 102 individuals 102 人の個人の 1,232 の署名と 62 のパラメトリック特性を使用した研究は、 2.8% の誤認定1.6% の誤認定, 1 つの方法では 2.68% の誤認定1.99% の誤認定, 以下に記載されているように 閾値選択の研究. そのアプリケーションは異なるが、運用原理は同じである: 検証者の決定ポリシーは、暗号化アルゴリズムと同じくらい重要である。

Capgo は、Capacitor と Electron チームが署名されたライブアップデートパッケージ、オンデバイス検証、ロールアウト制御、ロールバック保護、配信観察性を同じシステムで提供する必要がある場合の 1 つの実装オプションとして機能することができる。 Capgo アップデートワークフローがあなたのキーマネジメント、CI/CD、監視要件に適合するかどうかを評価するために。

Capacitor アプリ用の即時更新

When a web-layer bug is live, ship the fix through Capgo instead of waiting days for app store approval. Users get the update in the background while native changes stay in the normal review path.

マーティンから人間のサポート

Capgo gives you the best insights you need to create a truly professional mobile app.