リモートホスト型コード違反に対処する

リモートでホストされるコード(RHC)とは、拡張機能自身のファイル以外の場所から読み込まれたブラウザで実行されるものを Chrome ウェブストアが呼び出したものです。JavaScript や WASM などです。JSON や CSS などのデータや要素は含まれません。

RHC が利用できなくなったのはなぜですか?

Manifest V3 拡張機能では、使用するすべてのコードを拡張機能自体にバンドルする必要があります。これまでは、ウェブ上の任意の URL からスクリプトタグを動的に挿入できました。

拡張機能に RHC が含まれていると言われました。どうしましたか?

審査で拡張機能が Blue Argon エラーで拒否された場合、Google の審査担当者は拡張機能がリモートでホストされているコードを使用していると判断します。これは通常、拡張機能がリモート リソース(拡張機能に含まれるファイルではなくオープンウェブ)を含むスクリプトタグを追加しようとしたか、リソースを直接取得して実行した結果です。

RHC の特定方法

何を調べればよいかわかれば、RHC の発見は特に難しくない。まず、プロジェクト内に文字列「http://」または「https://」があるかどうかを確認します。RHC 違反がある場合は、それを見つけることで見つけることができます。完全なビルドシステムがある場合、または npm や他のサードパーティ ソースの依存関係を使用している場合は、コンパイル済みのコードを検索してください。これは、ストアで評価されるコードです。それでも問題を見つけられない場合は、次のステップとして One Stop サポートに連絡します。具体的な違反と、拡張機能をできるだけ早く公開するために必要な要件について説明してもらいます。

ライブラリがコードをリクエストしている場合

コードの出所にかかわらず、RHC は使用できません。これには、自分で作成していないにもかかわらず、たまたまプロジェクトの依存関係として使用されていたコードも含まれます。Firebase を使用する一部のデベロッパーでは、Firebase Auth で使用するリモートコードが含まれていた場合に、この問題が発生していました。これはファースト パーティ(Google 所有)のライブラリですが、RHC の例外は認められません。RHC を削除するか、最初のコードが含まれないように Pod を更新するようにコードを構成する必要があります。RHC を読み込む自分のコードではなく、使用しているライブラリという問題が発生した場合は、ライブラリの作成者に問い合わせることをおすすめします。このエラーの発生を通知し、回避策またはコードの更新を依頼してこの問題を解消してください。

ライブラリの更新を待てない場合

通知後ほぼすぐにアップデートがリリースされるライブラリもありますが、中止したり、問題に対処するために時間を取ったりするライブラリもあります。特定の違反の内容によっては、ブロックが解除されて審査が完了するまで待つ必要はありません。迅速に復旧して稼働させるためのオプションがいくつかあります。

コードを監査する

リクエストの原因となっているコードが必要であると確信していますか?コードを削除できる場合、または原因となっているライブラリを削除できる場合は、そのコードを削除すればジョブは完了です。

または、同じ機能を提供する別のライブラリはありますか?npmjs.com、GitHub などのサイトで、同じユースケースを満たすその他のオプションを確認してください。

ツリー シェイキング

RHC 違反の原因となっているコードが実際に使用されていない場合は、ツールによって自動的に削除される可能性があります。webpackRollupVite などの最新のビルドツールには、ツリー シェイキングと呼ばれる機能があります。ビルドシステムで有効にすると、ツリー シェイキングによって未使用のコードパスがすべて削除されます。つまり、より準拠したバージョンのコードを利用できるだけでなく、より効率的で高速なコードを利用できるということです。すべてのライブラリがツリー シェイキングできるわけではありませんが、多くのライブラリがツリー シェイクに対応していることに注意することが重要です。Rollup や Vite などの一部のツールでは、ツリー シェイキングがデフォルトで有効になっています。有効にするには、webpack を構成する必要があります。拡張機能の一部としてビルドシステムを使用していないが、コード ライブラリを使用している場合は、ワークフローにビルドツールを追加することをおすすめします。ビルドツールは、より安全で信頼性が高く、メンテナンスしやすいプロジェクトの作成に役立ちます。

ツリーシェイキングの実装方法の詳細は、プロジェクトによって異なります。ただし、Rollup の簡単な例では、プロジェクト コードをコンパイルするだけでツリーシェイキングを追加できます。たとえば、Firebase Auth へのログインのみを行う main.js というファイルがあるとします。

import { GoogleAuthProvider, initializeAuth } from "firebase/auth";

chrome.identity.getAuthToken({ 'interactive': true }, async (token) => {
  const credential = GoogleAuthProvider.credential(null, token);
  try {
    const app = initializeApp({ ... });
    const auth = initializeAuth(app, { popupRedirectResolver: undefined, persistence: indexDBLocalPersistence });
    const { user } = await auth.signInWithCredential(credential)
    console.log(user)
  } catch (e) {
    console.error(error);
  }
});

次に、入力ファイル、ノードファイルの読み込みに必要なプラグイン、@rollup/plugin-node-resolve、生成する出力ファイルの名前を Rollup に指示するだけです。

npx rollup --input main.js --plugin '@rollup/plugin-node-resolve' --file compiled.js

ターミナル ウィンドウでこのコマンドを実行すると、生成されたバージョンの main.js ファイルを受け取ります。このファイルはすべて、compiled.js という名前の 1 つのファイルにコンパイルされます。

傘下参入はシンプルですが、非常に構成もできます。あらゆる種類の複雑なロジックや構成を追加できます。詳しくは、こちらのドキュメントをご覧ください。このようなビルドツールを追加すると、コードが小さく効率的なものになります。このケースでは、リモートでホストされるコードの問題が解決します。

ファイルの自動編集

リモートでホストされたコードがコードベースに入ることは、ますます一般的になっています。それは、含めるライブラリのサブ依存関係として行われることです。ライブラリ X が CDN からライブラリ Yimport する場合、ローカルソースから読み込まれるようにライブラリを更新する必要があります。最新のビルドシステムでは、リモート参照を抽出するプラグインを簡単に作成して、コードに直接インライン化できます。

つまり、次のようなコードがあるとします。

import moment from "https://unpkg.com/moment@2.29.4/moment.js"
console.log(moment())

小さなロールアップ プラグインを作成できます。

import { existsSync } from 'fs';
import fetch from 'node-fetch';

export default {
  plugins: [{
    load: async function transform(id, options, outputOptions) {
      // this code runs over all of out javascript, so we check every import
      // to see if it resolves as a local file, if that fails, we grab it from
      // the network using fetch, and return the contents of that file directly inline
      if (!existsSync(id)) {
        const response = await fetch(id);
        const code = await response.text();

        return code
      }
      return null
    }
  }]
};

新しいプラグインでビルドを実行すると、Google のコード、下位依存関係、下位依存関係などであっても、リモートの import URL はすべて検出されます。

npx rollup --input main.js --config ./rollup.config.mjs --file compiled.js

ファイルを手動で編集する

最も簡単な方法は、RHC の原因となっているコードを削除することです。任意のテキスト エディタで開き、違反している行を削除します。これは脆弱で忘れられる可能性があるため、一般的にはおすすめしません。「library.min.js」というファイルが実際は library.min.js ではない場合、プロジェクトのメンテナンスが難しくなります。未加工ファイルを編集する代わりに、patch-package などのツールを使用する方が管理しやすくなります。これは、ファイル自体ではなくファイルに変更を保存できる非常に強力なオプションです。これはパッチファイル上に構築されます。これは、GitSubversion などのバージョン管理システムを動かすのと同じものです。違反しているコードを手動で変更し、差分ファイルを保存して、適用したい変更をパッチパッケージに設定するだけです。完全なチュートリアルについては、プロジェクトの README をご覧ください。プロジェクトにパッチを適用する場合は、そのプロジェクトに連絡してアップストリームで変更をリクエストすることを強くおすすめします。パッチパッケージを使用するとパッチの管理がはるかに簡単になりますが、パッチを一切適用しない方がはるかに便利です。

コードが使用されていない場合の対処方法

コードベースのが大きくなると、依存関係(または依存関係の依存関係、または ... の依存関係)によって、使用されなくなったコードパスが保持される可能性があります。これらのセクションのいずれかに、RHC を読み込みまたは実行するコードが含まれている場合は、削除する必要があります。停止していても、使用されていないかどうかは問題ではありません。使用されていない場合は、ツリーシェイキングまたはライブラリにパッチを適用して削除する必要があります。

回避策は何かあるか。

原則として認められません。RHC は許可されません。ただし、一部のケースでは許可されません。他のどのオプションも使用できないケースがほとんどです。

User Scripts API

ユーザー スクリプトは、通常はユーザーが提供する小さなコード スニペットで、TamperMonkeyViolentmonkey などのユーザー スクリプト マネージャーを対象としています。これらのマネージャーは、ユーザーが作成したコードをバンドルできないため、User Script API はユーザーが提供したコードを実行する方法を公開しています。これは、chrome.scripting.executeScript や他のコード実行環境に代わるものではありません。実行する場合は、デベロッパー モードを有効にする必要があります。ユーザーから提供されたコードなど、意図された以外の方法で使用されていると Chrome ウェブストアの審査チームが判断した場合、そのアプリは拒否されるか、ストアから削除される可能性があります。

chrome.debugger

chrome.debugger API を使用すると、拡張機能が Chrome Devtools プロトコルとやり取りできるようになります。これは、Chrome の DevTools やその他多数のツールで使用されているプロトコルと同じです。これにより、拡張機能はリモートコードをリクエストして実行できます。ユーザー スクリプトと同様に、chrome.scripting に代わるものではなく、はるかに優れたユーザー エクスペリエンスを実現します。使用中は、ウィンドウの上部に警告バーが表示されます。バナーが閉じるか閉じられると、デバッグ セッションは終了します。

「Debugger 拡張機能がこのブラウザのデバッグを開始しました」というメッセージが表示された Chrome のアドレスバーのスクリーンショット
「Debugger 拡張機能により、このブラウザのデバッグが開始されました」というメッセージが表示された Chrome のアドレスバーのスクリーンショット

サンドボックス化された iframe

DOM 環境(拡張機能 Service Worker ではなくコンテンツ スクリプトなど)で文字列をコードとして評価する必要がある場合は、サンドボックス化された iframe を使用することもできます。拡張機能は、安全上の対策として、デフォルトでは eval() などをサポートしていません。悪意のあるコードはユーザーの安全や セキュリティを危険にさらすおそれがありますしかし、ウェブの他の部分からサンドボックス化された iframe など、既知の安全な環境でのみコードを実行すれば、こうしたリスクは大幅に軽減されます。このコンテキスト内で、eval の使用をブロックするコンテンツ セキュリティ ポリシーを解除し、有効な JavaScript コードを実行できるようにします。

対象外のユースケースがある場合は、chromium-extensions のメーリング リストを使用してチームにご連絡いただき、フィードバックをお求めください。または、新しいチケットを作成して、ワンストップ サポートのガイダンスをリクエストしてください。

判定に同意できない場合の対応

ポリシーの適用には細かな差異が伴うことがあり、審査には手動での入力が必要となります。そのため、Chrome ウェブストア チームが審査の決定の変更に同意する場合があります。審査に誤りがあると思われる場合は、ワンストップ サポートを使用して不承認に対する再審査を請求できます。