ブラウザー拡大-内容スクリプトからの安全なHTTP要請


私はちょうどgithubのUIからコードツアーを実行することができますクロムとFirefoxの新しい拡張機能を公開しました.コード旅行とこのブログ柱の拡大に関する詳細情報.


私は、あなたがステップで正確に同じことをする方法についてのシリーズを書くのが楽しいと思いました.
この3番目のブログ記事は、コンテンツスクリプトからのクロス起源HTTPリクエストの送信に集中します.

問題


私はちょうど前に言及していたコードツアーの拡張を覚えていますか?最初のビットを実行しようとしましょう.私たちが望むのは、コードツアー(JSONファイル)の内容を取得できるようにすることです.あなたは右のURLで、fetchを使用するように簡単でなければならないと思いますか?さて、それはそれより少し複雑です.

奇抜なアプローチ


まず、すべてのコードツアー定義ファイルを見つける必要があります.一旦我々がいるならば、...githubのツアーディレクトリには、セレクタを使用できます.
// Wait for the page to be ready
document.addEventListener("DOMContentLoaded", function(){
  Array.from(
      // Find all links to tour files
      document.querySelectorAll('div[role=row] > div[role="rowheader"] > span > a').values(),
    ).map(
      async (parentElement) => {
        const title = parentElement.getAttribute('title')
        const href = parentElement.getAttribute('href')


        // Now we want to query the file content as a raw string.
        // In Github, this means fetching the file using “raw” instead of “blob”
        const codeTourUrl = href.replace('blob', 'raw')

        // A code tour is a json object, we can use the fetch API to receive an object
        const content = await fetch(codeTourUrl).then((response) => response.json())
        console.log(title, content)
  })
})
この投稿で作成したコンテンツスクリプトファイルにこのコードをコピーします


拡張モジュールを更新すると、ロードされたページで実行されます.the .tours folder of a projectに行き、コンソールを開きます.これらのどちらかが表示されます.
クロムの上の
  • 、コード旅行のリストと彼らの内容は、
  • を載せられます
    Firefoxの
  • にはエラーが表示され、HTTPリクエストは
  • リクエストをバックグラウンドに転送する


    このコードを使用すると、すべてのコードツアー定義ファイルを取得できます.残念ながら、Githubはこのリクエストの間、私たちをリダイレクトします.これは、クロス起源の要求であるFirefox上で動作しません.
    一般に、あなたは内容スクリプトからFETCHを使用してはいけません.これを処理する正しい方法は、バックグラウンドスクリプトに問い合わせを転送するためです.
    バックグラウンドスクリプトにリクエストを転送できるようにする関数を作りましょう.
    function forwardRequest(message) {
      return new Promise((resolve, reject) => {
        chrome.runtime.sendMessage(message, (response) => {
          if (!response) return reject(chrome.runtime.lastError)
          return resolve(response)
        })
      })
    }
    
    バックグラウンドスクリプトでは、この要求を処理する必要があります.
    chrome.runtime.onMessage.addListener(function(request, sender, sendResponse) {
        // sendResponse can be used to send back a result to the content script
        fetch(`https://github.com/${request.url}`)
             .then((response) => response.json())
             .then((codeTourContent) => sendResponse(codeTourContent))
        // As we will reply asynchronously to the request, we need to tell chrome to wait for our response
        return true
    })
    
    ⚠️ あなたのバックグラウンドスクリプトに転送する方法に注意してください.これは完全に認証されている場合は、ランダムなURLへの要求をトリガしないことを確認する必要があります.この場合、URLを確認する必要があります(安全であることを確認してください).ここではGitHubドメインの使用を強制します.可能であれば、バックグラウンドスクリプトで自分自身のURLを構築する必要がある正確なリソースをターゲットにするためにサーサーする.
    このコードを持っているので、バックグラウンドスクリプトで取得する呼び出しをforwardRequestへの呼び出しで置き換えることができます.
    Array.from(
        document.querySelectorAll('div[role=row] > div[role="rowheader"] > span > a').values(),
      ).map(
        async (parentElement) => {
            const title = parentElement.getAttribute('title')
            const href = parentElement.getAttribute('href')
            const codeTourUrl = href.replace('blob', 'raw')
    
            // Now forward request will behave like fetch
            const content = await forwardRequest({ url: codeTourUrl })
            console.log(title, content)
    })
    
    これは、バックグラウンドスクリプトがランダムなホスト名にどんな要求もするのを防ぐので、Firefoxの上で働きません.これを修正するために、あなたはバックグラウンドスクリプトからgithub.comrender.githubusercontent.com(Githubはこのドメインにリダイレクトします)に問い合わせを許可するよう要求する必要があります.
    マニフェストファイルに追加します.
    {
        "permissions": ["https://render.githubusercontent.com/*", "https://github.com/*"]
    }
    
    リロードを拡張し、それが動作する!

    結論


    私たちは深いブラウザの拡張の1つの本当に重要な側面に深く潜入:コンテンツスクリプトからデータを安全に取得します.次のポストでは、機能を構築するためにデータを使用します!次の1つをチェックアウトしたい場合はこちらをご覧ください.
    -アクションボタン
    バックグラウンドカラー:けっこうffffff!重要
    色:千円!重要
    ボーダーカラー:こっち重要


    クェンティンM


    Engineering Manager @Doctolib – Mostly writing about TypeScript / JavaScript
    Ricardo Gomez AngelUnsplashによる写真