App Routerではフォルダ名やファイル名に基づいてアプリケーションのナビゲーションなどの挙動を設定します。この記事ではそんなフォルダ名やファイル名についてパターンを一覧で見れるようにまとめました。
ファイル
ルーティングに関するファイル
page
マッピングされたページごとのUIを記述するファイルです。ページの主要な内容はここに記述されます。
layout
マッピングされたページとそれ以降のページに対するUIを記述するファイルです。
app
は以下にある場合はhtml
タグやbody
タグを用いて記述する必要があり、App Routerでは配置することが必須となっています。
template
layout
に似たような動きをするファイルです。こちらのファイルはapp
に置くことは強制されていません。
layout
と大きく異なる部分はナビゲーション毎の動作です。template
ではナビゲーション毎にUIを作り直すので状態が初期化されてしまいます。ページ毎になんらかの動作を行うようにしてほしい場合はtemplate
を利用します。
default
マッピングされていないページに訪れたときに表示されるUIを記述します。並行ルートとの相性が良い機能となります。
loading
マッピング毎に設けられるSuspense
境界で表示されるUIを記述するファイルです。
error
マッピング毎に設けられるErrorBoundary
境界で表示されるUIを記述するファイルです。
global-error
app
全体のエラーを扱うファイルです。app/layout
の内容すら置き換える内容を記述する必要があるのでhtml
要素やbody
要素を用いて記述する必要があります。
not-found
notFound
関数がスローされたときやマッピングされていないページに訪れたときに表示されるUIを記述するファイルです。
route
マッピングされた場所でAPIを定義することができるファイルです。これまで紹介したファイルと一緒に置くことはできません。
ルーティングまとめ
これまで紹介したルーティングファイルは以下のような形で組み立てられます(routeとdefaultはここに記述されない)。
<ErrorBoundary fallback={<GlobalError />}>
<Layout>
<Template>
<ErrorBoundary fallback={<Error />}>
<Suspense fallback={<Loading />}>
<ErrorBoundary fallback={<NotFound />}>
<Page />
</ErrorBoundary>
</Suspense>
</ErrorBoundary>
</Template>
</Layout>
</ErrorBoundary>
icon
favicon
やicon
、apple-icon
はapp
ディレクトリに置くことでマッピングしたページのhead
に追加してくれます。
これらはコードを用いて生成することもできます。
manifest.json
manifest.json
やmanifest.webmanifest
をapp
は以下に置くことでアプリに関する情報を提供できます。
これらはコードを用いて生成することもできます。
opengraph-image
opengraph-image
やtwitter-image
を設定することができます。
これらはコードを用いて生成することもできます。
robots.txt
robots.txt
を設定することができます。
これらはコードを用いて生成することもできます。
sitemap.xml
sitemap.xml
を設定することができます。
これらはコードを用いて生成することもできます。
フォルダ
通常
App Routerはapp
ディレクトリ内で配置されたディレクトリ構成をもとにルーティングを行います。
app/blog
に置かれたファイルはexample.com/blog
で展開されます。app/user/profile
だとexample.com/user/profile
です。
動的ルート
example.com/accounts/123
やexample.com/accounts/987
のように動的にパスが変更されるページを表現するには[]
で囲むことで作成できます。例で出したケースはapp/accounts/[id]
のように書きます。
このようなパスはexample.com/accounts/123/edit
のようなパスにはマッチしませんが、app/accounts/[...id]
のように...
を加えることでapp/accounts/:id
に後続する全てのルートに一致するようになります。これはキャッチオールセグメントと呼ばれます。
そして、大括弧を一個増やしてapp/accounts/[[id]]
のように書くことでexample.com/accounts/987
だけではなく、example.com/accounts
もマッチするようになります。この記法はキャッチオールセグメントと重ねて利用することもできます。
動的ルートがマッピングする先に通常のルーティングがマッピングされている場合は通常のマッピングが優先されることに注意してください。app/accounts/password
でマッピングされている場合はexample.com/accounts/password
にはapp/accounts/[id]
ではなく、app/accounts/password
の内容が反映されます。
ルートグループ
ルートグループは()
を囲むことで利用できるマッピングに関する機能です。app/(royal)/accounts
の内容はexample.com/accounts
にマッピングされます。
App Routerではレイアウトなどの情報をより上位のディレクトリから引き継いで表示されますが、途中で引き継ぐ内容を分割したいことがあります。example.com/posts
やexample.com/about
より下のレベルとexample.com/accounts
より下のレベルで異なる内容を表示したいとします。それぞれのディレクトリにレイアウトなどの情報を書くだけでも良いですが、ルートグループを用いることで、app/(public)/posts
やapp/(public)/about
、app/(private)/accounts
のようにすることでposts
とabout
の共通化をしつつも異なる設定をaccounts
に対して行うことができます。
並行ルート
並行ルートは@
で始まる名前でディレクトリを作成することで利用できる機能です。app/@hello
やapp/@world
のようにディレクトリを作成するとapp
配下にあるレイアウトでそれらを用いることが可能となります。
app/@hello/accounts
のように内部でディレクトリを積み重ねこともできます。しかし、app/accounts
とapp/@hello/accounts
ディレクトリにファイルを置いて/accounts
にアクセスしてもapp/@world/accounts
にUIが宣言されていないため404ページが表示されます(ただし、Nextjsのナビゲーション機能を用いて遷移した場合はその部分に直前まで表示していたUIを表示し続けます)。
/accounts
に直接アクセスしたときであってもUIを表示させたい場合はapp/@world/accounts
にUIを宣言するか、app/@world
にdefault
ファイルを記述する必要があります。
インターセプトルート
インターセプトルートは(.)
や(..)
、(..)(..)
、(...)
などから始まる名前でディレクトリを作成することで利用できる機能です。
例えばapp/accounts
、app/blog
、app/accounts/(..)blog
のようにマッピングされているときに、example.com/accounts
からexample.com/blog
にアクセスしたときにapp/accounts
ではなく、app/accounts/(..)blog
の内容が表示されるようになります。
規則は相対パスと同じような感じで(.)
は同じレベルの内容をインターセプトします。(..)
はひとつ上のレベルの内容をインターセプトします。(..)(..)
はふたつ上のレベルの内容をインターセプトします。(...)
はapp
配下の内容をインターセプトします。
プライベートフォルダ
_
から始まるディレクト名のことをプライベートフォルダと言います。App Routerの理から外れたファイルを設置できます。_components
のようにがルーティングから除外したいが、app
内におきたいようなファイルを置くのがおすすめです。