Menu

スクリプトの読み込みと最適化方法

アプリケーションスクリプト

すべてのルートに対してサードパーティスクリプトを読み込むには、next/scriptをインポートし、スクリプトをカスタム_appに直接含めます。

pages/_app.js
import Script from 'next/script'
 
export default function MyApp({ Component, pageProps }) {
  return (
    <>
      <Component {...pageProps} />
      <Script src="https://example.com/script.js" />
    </>
  )
}

このスクリプトは、アプリケーション内の任意のルートにアクセスされると読み込みと実行が行われます。Next.jsはユーザーが複数のページ間をナビゲートしても、スクリプトが1回だけ読み込まれることを保証します

推奨事項:パフォーマンスへの不要な影響を最小化するため、サードパーティスクリプトは特定のページまたはレイアウトにのみ含めることをお勧めします。

Strategy(戦略)

next/scriptのデフォルトの動作ではサードパーティスクリプトを任意のページやレイアウトに読み込めますが、strategyプロパティを使用して読み込み動作を細かく調整できます。

  • beforeInteractive:Next.jsコードの前に、かつページハイドレーション前にスクリプトを読み込みます。
  • afterInteractive:(デフォルト)ページ上である程度ハイドレーションが発生した後、早期にスクリプトを読み込みます。
  • lazyOnload:ブラウザのアイドルタイム中に後からスクリプトを読み込みます。
  • worker:(実験的)Webワーカーでスクリプトを読み込みます。

各strategyとそのユースケースについて詳しく知るには、next/script APIリファレンスドキュメントを参照してください。

スクリプトをWebワーカーにオフロードする(実験的)

警告worker strategyはまだ安定していないため、App Routerではまだ機能しません。注意して使用してください。

worker strategyを使用するスクリプトは、Partytownを使用してWebワーカーでオフロードおよび実行されます。これにより、メインスレッドをアプリケーションコードの残り部分に専念させることで、サイトのパフォーマンスを向上させることができます。

このstrategyはまだ実験的であり、next.config.jsnextScriptWorkersフラグが有効になっている場合にのみ使用できます。

next.config.js
module.exports = {
  experimental: {
    nextScriptWorkers: true,
  },
}

次に、nextを実行し(通常はnpm run devまたはyarn dev)、Next.jsがセットアップを完了するために必要なパッケージのインストールをガイドします。

Terminal
npm run dev

以下のような指示が表示されます。npm install @builder.io/partytownを実行してPartytownをインストールしてください。

セットアップが完了したら、strategy="worker"を定義するとアプリケーション内でPartytownが自動的にインスタンス化され、スクリプトがWebワーカーにオフロードされます。

pages/home.tsx
TypeScript
import Script from 'next/script'
 
export default function Home() {
  return (
    <>
      <Script src="https://example.com/script.js" strategy="worker" />
    </>
  )
}

Webワーカーでサードパーティスクリプトを読み込む場合、検討する必要があるトレードオフが多くあります。詳しくはPartytownのトレードオフドキュメントを参照してください。

カスタムPartytown設定の使用

worker strategyは追加の設定を必要としませんが、Partytownは設定オブジェクトを使用してデバッグモードの有効化やイベントおよびトリガーの転送を含む、いくつかの設定を変更することをサポートしています。

追加の設定オプションを追加する場合は、カスタム_document.jsで使用される<Head />コンポーネント内に含めることができます。

_pages/document.jsx
import { Html, Head, Main, NextScript } from 'next/document'
 
export default function Document() {
  return (
    <Html>
      <Head>
        <script
          data-partytown-config
          dangerouslySetInnerHTML={{
            __html: `
              partytown = {
                lib: "/_next/static/~partytown/",
                debug: true
              };
            `,
          }}
        />
      </Head>
      <body>
        <Main />
        <NextScript />
      </body>
    </Html>
  )
}

Partytownの設定を変更するには、以下の条件を満たす必要があります。

  1. data-partytown-config属性は、Next.jsで使用されるデフォルト設定を上書きするために使用される必要があります。
  2. Partytownのライブラリファイルを別のディレクトリに保存することに決めない限り、Partytownが必要な静的ファイルをNext.jsが保存されている場所を認識できるようにするために、lib: "/_next/static/~partytown/"プロパティと値を設定オブジェクトに含める必要があります。

補足アセットプレフィックスを使用しており、Partytownのデフォルト設定を変更する場合は、libパスの一部としてそれを含める必要があります。

Partytownの設定オプションを参照して、追加できるその他のプロパティの完全なリストを確認してください。

インラインスクリプト

外部ファイルから読み込まれないインラインスクリプトもScriptコンポーネントによってサポートされます。これらは、JavaScriptを中括弧内に配置することで記述できます。

<Script id="show-banner">
  {`document.getElementById('banner').classList.remove('hidden')`}
</Script>

またはdangerouslySetInnerHTMLプロパティを使用します。

<Script
  id="show-banner"
  dangerouslySetInnerHTML={{
    __html: `document.getElementById('banner').classList.remove('hidden')`,
  }}
/>

警告:Next.jsがスクリプトを追跡および最適化するために、インラインスクリプトにidプロパティを割り当てる必要があります。

追加コードの実行

イベントハンドラーはScriptコンポーネントで使用して、特定のイベントが発生した後に追加コードを実行できます。

  • onLoad:スクリプトの読み込みが完了した後にコードを実行します。
  • onReady:スクリプトの読み込みが完了した後、およびコンポーネントがマウントされるたびにコードを実行します。
  • onError:スクリプトの読み込みに失敗した場合にコードを実行します。

これらのハンドラーは、next/scriptクライアントコンポーネントにインポートされ使用される場合にのみ機能します。このコンポーネント内で"use client"がコードの最初の行として定義されています。

pages/index.tsx
TypeScript
import Script from 'next/script'
 
export default function Page() {
  return (
    <>
      <Script
        src="https://example.com/script.js"
        onLoad={() => {
          console.log('Script has loaded')
        }}
      />
    </>
  )
}

各イベントハンドラーの詳細と例については、next/script APIリファレンスを参照してください。

追加属性

Scriptコンポーネントで使用されていない多くのDOM属性があり、nonceカスタムデータ属性などが挙げられます。追加の属性を含めると、HTMLに含まれる最終的な最適化された<script>要素に自動的に転送されます。

pages/index.tsx
TypeScript
import Script from 'next/script'
 
export default function Page() {
  return (
    <>
      <Script
        src="https://example.com/script.js"
        id="example-script"
        nonce="XUENAJFW"
        data-test="script"
      />
    </>
  )
}