クモのようにコツコツと

フロントエンドエンジニア イイダリョウの技術ブログ。略称「クモコツ」

【React】Nextスターターキットを作った-3. ページファイル編(Next + TypeScript + CSS in JS)

Nextの続きです。前回はNextスターターキットのコンポーネント&モジュールについてまとめました。今回は最終回、ページファイル編になります。Next.jsの複数ページ設定(/pagesフォルダ)を使った内容になります。それではいきましょう!

【目次】

※参考:前回記事
【React】Nextスターターキットを作った-2. コンポーネント編(Next + TypeScript + CSS in JS) - クモのようにコツコツと

※参考:ReactでWebアプリを作るシリーズまとめ
qiita.com

前回のおさらい

Nextスターターキットで作ったコンポーネントやモジュールをまとめた。async/awaitのエラーハンドリングなども。 https://cdn-ak.f.st-hatena.com/images/fotolife/i/idr_zz/20210502/20210502084809.jpg

※参考:前回記事
【React】Nextスターターキットを作った-2. コンポーネント編(Next + TypeScript + CSS in JS) - クモのようにコツコツと

今回は各ページのファイルについてまとめる。Next.jsの/pagesフォルダの中に作っていく。

作ったもの

ソースコード

※参考:GitHub - ryo-i/next-app-started

プレビュー

※参考:Nextアプリスターターキット


トップページ
f:id:idr_zz:20210501124640j:plain

/pages/index.tsxに当たる部分 next-app-started.vercel.app

トップページ固有のOGPも表示される!


Aboutページ
f:id:idr_zz:20210501124656j:plain

/pages/about.tsxに当たる部分

※参考:next-app-started.vercel.app

Aboutページ固有のOGPも表示される!


404ページ
f:id:idr_zz:20210502153951j:plain

/pages/404.tsxに当たる部分。存在しないURLを開くと表示される。

※参考:https://next-app-started.vercel.app/abc123456

トップページ

/pagesフォルダにindex.tsxを追加。

HeadHeaderInnerFooterコンポーネントをインポート

import Head from 'next/head';
import Header from '../components/Header';
import Inner from '../components/Inner';
import Footer from '../components/Footer';

HeadはNext.jsが用意しているheadタグをカスタマイズするコンポーネント

※参考:【React】Next.jsのリンク設定(Link)、共通コンポーネント化、headタグ設定(Head) - クモのようにコツコツと

HeaderInnerFooterは前回作成したコンポーネント(Innerはトップページ固有)

※参考:【React】Nextスターターキットを作った-2. コンポーネント編(Next + TypeScript + CSS in JS) - クモのようにコツコツと


次にトップページのテキスト設定

変数Datadata.jsonを取得

import Data from '../data/data.json';

変数headerTitleheaderTextpageTitlepageTextでテキスト設定

const headerTitle = Data.header.title;
const headerText = Data.header.text;
const pageTitle = Data.main.title;
const pageText = Data.main.text;

Homeコンポーネント作成

function Home() {
  return (
    <>
      <Head>
        <title>{ headerTitle }</title>
        <meta name="description" content={ headerText } />
        <meta property="og:title" content={ headerTitle } />
        <meta property="og:description" content={ headerText } />
      </Head>
      <Header />
      <main>
        <h1>{ pageTitle }</h1>
        <p dangerouslySetInnerHTML={{ __html: pageText }}></p>
        <Inner />
      </main>
      <Footer />
    </>
  )
}
  • Headコンポーネントでheadタグ設定
    titleタグ&og:titleheaderTitleを読み込む
    description&og:descriptionheaderTextを読み込む
  • Headerコンポーネントを読み込み
  • mainタグの設定
    h1タグでpageTitle、pタグでpageTextを読み込む
    Innerコンポーネントを読み込む
  • Footerコンポーネントを読み込む

最後にHomeをエクスポート

export default Home;

これでトップページが表示される!
f:id:idr_zz:20210501124640j:plain

※参考:Nextアプリスターターキット

Aboutページ

/pagesフォルダにabout.tsxを追加。

HeadHeaderProfileFooterコンポーネントをインポート

import Head from 'next/head';
import Header from '../components/Header';
import Profile from '../components/Profile';
import Footer from '../components/Footer';

Profileは前回作成したコンポーネントで、Aboutページ固有の内容

※参考:【React】Nextスターターキットを作った-2. コンポーネント編(Next + TypeScript + CSS in JS) - クモのようにコツコツと


次にAboutページのテキスト設定

変数Datadata.jsonを取得

import Data from '../data/data.json';

変数headerTitlepageTitlepageTextheadTitleでテキスト設定

const headerTitle = Data.header.title;
const pageTitle = 'このアプリについて';
const pageText = 'アプリの概要をここに書く。';
const headTitle = pageTitle + ' | ' + headerTitle;

pageTitlepageTextはベタガキ、headTitlepageTitleheaderTitleの組み合わせ


Aboutコンポーネント作成

// Component
function About() {
    return (
        <>
        <Head>
            <title>{ headTitle }</title>
            <meta name="description" content={ pageText } />
            <meta property="og:title" content={ headTitle } />
            <meta property="og:description" content={ pageText } />
        </Head>

        <Header />
        <main>
            <h1>{ pageTitle }</h1>
            <p dangerouslySetInnerHTML={{ __html: pageText }}></p>
            <section>
                <h2>使い方</h2>
                <p>アプリの説明説明説明説明説明説明説明説明</p>
            </section>
            <Profile />
        </main>
        <Footer />
        </>
    );
}
  • トップページと違いsectionタグの中がベタガキ
  • トップページと違いProfileコンポーネントを読み込んでいる

最後にAboutコンポーネントをエクスポート

export default About;

これでAboutページが表示される!
f:id:idr_zz:20210501124656j:plain

※参考:このアプリについて | Nextアプリスターターキット

404ページ

もう一つ、404ページも作成した。

Next.jsでは/pagesに存在しないURLを開くとデフォルトで用意された404ページが表示される。
f:id:idr_zz:20210502162139j:plain

この404ページをカスタマイズするには/pages404.tsxを追加すればいいようだ。

※参考:Advanced Features: エラーページのカスタマイズ | Next.js


これまで作ったトップページ、Aboutページと同じ構成の404ページを作ってみた。

HeadLinkHeaderProfileFooterコンポーネントをインポート

import Head from 'next/head';
import Link from 'next/link';
import Header from '../components/Header';
import Profile from '../components/Profile';
import Footer from '../components/Footer';

Aboutページで表示したProfileをここでも表示することにする。


404ページのテキスト設定

変数Datadata.jsonを取得

import Data from '../data/data.json';

変数headerTitlepageTitlepageTextheadTitleでテキスト設定

const headerTitle = Data.header.title;
const pageTitle = '404ページ';
const pageText = 'お探しのページは見つかりませんでした。';
const headTitle = pageTitle + ' | ' + headerTitle;

Aboutページと同じくpageTitlepageTextはベタガキ


notFoundコンポーネント作成

// Component
function notFound() {
    return (
        <>
        <Head>
            <title>{ headTitle }</title>
            <meta name="description" content={ pageText } />
            <meta property="og:title" content={ headTitle } />
            <meta property="og:description" content={ pageText } />
        </Head>

        <Header />
        <main>
            <h1>{ pageTitle }</h1>
            <p dangerouslySetInnerHTML={{ __html: pageText }}></p>
            <section>
                <h2>Homeに戻る</h2>
                <p>こちらからお戻りください→ <Link href="/"><a>Home</a></Link></p>
            </section>
            <Profile />
        </main>
        <Footer />
        </>
    );
}
  • Aboutページと同じくsectionタグの中がベタガキ
  • pタグの中でNext.jsのLinkでトップページへのリンクを設定
  • Aboutページと同じくProfileコンポーネントを読み込んでいる

最後にnotFoundコンポーネントをエクスポート

export default notFound;

これで存在しないURLを開くと404ページ が表示される! f:id:idr_zz:20210502153951j:plain

※参考:https://next-app-started.vercel.app/abc123456

最後に

ということでReactスターターキットをNext.jsで作り替えてNextスターターキットが完成しました!

今回の経験で得られた知見

  • コンポーネントの作り方、使い方はNext.jsとReactは違いを感じない
  • ReactのSPAではreact-routerやhelmet使ってた実現していた複数ページ構成がNext.jsでは最初から用意されている
  • SPAではheadタグがブラウザ側で動的に変更されるために悩み所だったOGP設定の問題がNext.jsで解決した!

ということでReactアプリとNextアプリではアプリの主要構成に本質的な違いはなく、SPAで苦心した周辺要素(ルーティングやOGP)はNext.jsの方が楽に感じました。

※参考:【React】OGPはつらいよ ーSPAでの動的OGP・失敗編ー(Reactアプリスターターキット) - クモのようにコツコツと

今後もこのNext.js + TypeScript + CSS in JS環境でWebアプリを作っていきたく思います♪


CSSに関してはNext.jsはCSS Modules推しのようで、またTailwind CSSを公式サポートする流れもあるようです。

※参考:Next.js が CSS Modules を推奨する真相に迫りたい

個人的にはReactのCSS設定はいろいろ試した上でStyled-componentsが一番使いやすく感じています。

※参考:ReactのCSS設定方法について調べたこと(className属性、style属性、CSS Modules、CSS in JS、CSSフレームワーク) - クモのようにコツコツと

今後もReact 、Next.js、フロントエンド界隈の動向の様子を見つつ本スターターキットをブラッシュアップしていきます。それではまた!


※参考:ReactでWebアプリを作るシリーズまとめ
qiita.com