ページとレイアウト

Nuxt 2 から Nuxt 3 のページとレイアウトへの移行方法を学びましょう。

app.vue

Nuxt 3 は、~/app.vue を介してアプリへの中心的なエントリポイントを提供します。

ソースディレクトリに app.vue ファイルがない場合、Nuxt は独自のデフォルトバージョンを使用します。

このファイルは、アプリの起動時に一度実行する必要があるカスタムコードや、アプリのすべてのページに存在するコンポーネントを配置するのに最適な場所です。たとえば、レイアウトが1つしかない場合は、代わりに app.vue に移動できます。

Docs > 4 X > Guide > Directory Structure > App でさらに詳しく読みましょう。
Docs > 4 X > Examples > Hello World でライブ例を読み、編集しましょう。

移行

app.vue ファイルを作成し、アプリの最上位で一度実行する必要があるロジックを含めることを検討してください。ここにある例を確認できます。

レイアウト

複数のページでアプリにレイアウトを使用している場合、わずかな変更のみが必要です。

Nuxt 2 では、<Nuxt> コンポーネントがレイアウト内で現在のページをレンダリングするために使用されます。Nuxt 3 では、レイアウトは代わりにスロットを使用するため、そのコンポーネントを <slot /> に置き換える必要があります。これにより、名前付きスロットやスコープ付きスロットなどの高度なユースケースも可能になります。レイアウトについて詳しく読む

また、definePageMeta コンパイラマクロを使用して、ページで使用されるレイアウトを定義する方法も変更する必要があります。レイアウトはケバブケースになります。そのため、app/layouts/customLayout.vue は、ページで参照されるときに custom-layout になります。

移行

  1. <Nuxt /><slot /> に置き換えます
    app/layouts/custom.vue
      <template>
        <div id="app-layout">
          <main>
    -       <Nuxt />
    +       <slot />
          </main>
        </div>
      </template>
    
  2. definePageMeta を使用して、ページで使用されるレイアウトを選択します。
    app/pages/index.vue
    + <script setup>
    + definePageMeta({
    +   layout: 'custom'
    + })
    - <script>
    - export default {
    -   layout: 'custom'
    - }
      </script>
    
  3. ~/layouts/_error.vue~/error.vue に移動します。エラー処理のドキュメントを参照してください。このページでレイアウトを使用したい場合は、error.vue 内で直接 <NuxtLayout> を使用できます。
    error.vue
    <template>
      <div>
        <NuxtLayout name="default">
          <!-- -->
        </NuxtLayout>
      </div>
    </template>
    

ページ

Nuxt 3 には、ソースディレクトリに app/pages/ ディレクトリが存在することでトリガーされる、オプションの vue-router 統合が付属しています。単一のページしかない場合は、より軽量なビルドのために app.vue に移動することを検討してください。

動的ルート

Nuxt 3 で動的ルートを定義する形式は Nuxt 2 とは若干異なるため、app/pages/ 内のいくつかのファイルの名前を変更する必要がある場合があります。

  1. 以前は動的ルートパラメータを定義するために _id を使用していましたが、現在は [id] を使用します。
  2. 以前はキャッチオールルートを定義するために _.vue を使用していましたが、現在は [...slug].vue を使用します。

ネストされたルート

Nuxt 2 では、ネストされたルート(親コンポーネントと子コンポーネントを持つ)を <Nuxt><NuxtChild> を使用して定義していました。Nuxt 3 では、これらは単一の <NuxtPage> コンポーネントに置き換えられています。

ページキーとKeep-aliveプロパティ

以前 <Nuxt> にカスタムページキーまたはkeep-aliveプロパティを渡していた場合は、definePageMeta を使用してこれらのオプションを設定する必要があります。

Docs > 4 X > Guide > Directory Structure > App > Pages#special Metadata でさらに詳しく読みましょう。

ページとレイアウトのトランジション

コンポーネントオプションで直接ページまたはレイアウトのトランジションを定義していた場合は、definePageMeta を使用してトランジションを設定する必要があります。Vue 3 以降、-enter と -leave の CSS クラスが名前変更されました。<Nuxt>style プロパティは、<slot> で使用される場合、トランジションには適用されなくなりました。そのため、スタイルを -active クラスに移動してください。

Docs > 4 X > Getting Started > Transitions で詳細をご覧ください。

移行

  1. 動的パラメータを持つページは、新しい形式に合わせて名前を変更してください。
  2. <Nuxt><NuxtChild><NuxtPage> に更新してください。
  3. コンポジション API を使用している場合、this.$routethis.$routeruseRouteuseRouter コンポーザブルを使用するように移行することもできます。

例:動的ルート

- URL: /users
- Page: /pages/users/index.vue

- URL: /users/some-user-name
- Page: /pages/users/_user.vue
- Usage: params.user

- URL: /users/some-user-name/edit
- Page: /pages/users/_user/edit.vue
- Usage: params.user

- URL: /users/anything-else
- Page: /pages/users/_.vue
- Usage: params.pathMatch

例:ネストされたルートと definePageMeta

<template>
  <div>
    <NuxtChild
      keep-alive
      :keep-alive-props="{ exclude: ['modal'] }"
      :nuxt-child-key="$route.slug"
    />
  </div>
</template>

<script>
export default {
  transition: 'page', // or { name: 'page' }
}
</script>

グローバルな NuxtLink コンポーネントの構文と機能のほとんどは同じです。以前にショートカット <NLink> 形式を使用していた場合は、<NuxtLink> を使用するように更新する必要があります。

<NuxtLink> は、外部リンクを含むすべてのリンクのドロップイン代替になりました。これについて、および独自のリンクコンポーネントを提供するためにこれを拡張する方法について詳しく読むことができます。

Docs > 4 X > API > Components > Nuxt Linkで詳細をご覧ください。

プログラムによるナビゲーション

Nuxt 2 から Nuxt 3 に移行する際、プログラムによるユーザーナビゲーション方法を更新する必要があります。Nuxt 2 では、this.$router を使用して基盤となる Vue Router にアクセスできました。Nuxt 3 では、ルートとパラメータを Vue Router に渡すことができる navigateTo() ユーティリティメソッドを使用できます。

navigateTo は常に await するか、関数から戻り値を返すことでその結果を連鎖させてください。
<script>
export default {
  methods: {
    navigate () {
      this.$router.push({
        path: '/search',
        query: {
          name: 'first name',
          type: '1',
        },
      })
    },
  },
}
</script>