【2026年版】Next.js テンプレートの作り方 — TypeScript 7.0・Oxlint・pnpm でセキュリティファーストな開発環境を構築する

約40分で読めます by ぽんたぬき
【2026年版】Next.js テンプレートの作り方 — TypeScript 7.0・Oxlint・pnpm でセキュリティファーストな開発環境を構築する

【2026年版】Next.js テンプレートの作り方 — TypeScript 7.0・Oxlint・pnpm でセキュリティファーストな開発環境を構築する

2026年のフロントエンド開発は、「速度」と「サプライチェーンセキュリティ」という2つの軸で大きく変化しました。TypeScript 7.0 の Go 言語実装による約10倍の高速化、Rust 製リンター Oxlint の台頭、pnpm v11 のセキュリティデフォルト強化——これらの変化は「便利だから乗り換える」という次元を超え、「安全側のデフォルトが業界水準として定着した」ことを意味します。

この記事では、2026年基準の Next.js テンプレートをゼロから構築する手順を、コピペ可能な設定ファイル付きで解説します。所要時間は約60分。読み終えたとき、あなたの手元にはセキュアで高速な開発環境の雛形が完成しています。


検証環境・バージョン一覧

ツール バージョン
Node.js 22.x LTS
pnpm v11.x
Next.js 16.x
React 19.x
TypeScript 7.0.2
Oxlint v1.x
Oxfmt v0.36.x
Tailwind CSS v4.x

この記事で作るテンプレートの全体像

完成する技術スタック

my-next-app/
├── .github/
│   ├── workflows/ci.yml       # SHA固定済みCI
│   └── dependabot.yml         # 週次更新 + クールダウン設定
├── .vscode/
│   └── settings.json          # 保存時自動フォーマット
├── src/
│   └── app/                   # App Router
├── .oxlintrc.json             # Oxlint設定
├── .npmrc                     # pnpmセキュリティ設定
├── pnpm-workspace.yaml
├── tsconfig.json              # TypeScript 7.0設定
└── package.json

なぜ「2026年版」を作り直す必要があるのか

2025年から2026年にかけて、OSSのサプライチェーン攻撃は質・量ともに深刻化しました。公開直後の悪意あるバージョンを npm install で踏んでしまう事例や、postinstall スクリプトを悪用した任意コード実行が相次いで報告されています。

その結果、主要パッケージマネージャーやツールチェーンが「安全側のデフォルト」への舵を切りました。pnpm v11 のセキュリティ設定標準化、GitHub Actions の SHA 固定が事実上の最低水準となったことがその証左です。「昔のやり方のままで動いている」テンプレートは、機能的には問題なくても、セキュリティ的には時代遅れになっているのです。


STEP 1|pnpm でプロジェクトを初期化する

このステップでやること

pnpm v11 をインストールし、Next.js 16 プロジェクトを作成します。

pnpm v11 をインストールする(Corepack 経由)

Node.js 22 には Corepack が同梱されています。以下のコマンドで pnpm を有効化します。

npm install -g pnpm@latest

package.jsondevEngines フィールドを追加すると、チームメンバーの Node.js バージョンを宣言的に管理できます。

{
  "devEngines": {
    "runtime": {
      "name": "node",
      "version": ">=22.0.0",
      "onFail": "error"
    },
    "packageManager": {
      "name": "pnpm",
      "version": ">=11.0.0",
      "onFail": "error"
    }
  }
}

onFail: "error" を指定することで、要件外の環境での pnpm run を失敗させることができます。バージョン不一致による「自分の環境でしか動かない」問題を未然に防ぐ、地味ながら重要な設定です。

Next.js 16 プロジェクトを作成する

pnpm create next-app@latest my-next-app

対話式プロンプトでは以下を選択します。

質問 選択
TypeScript Yes
ESLint No(後で Oxlint に差し替えるため)
Tailwind CSS Yes
App Router Yes
Turbopack Yes
src/ directory Yes

既存プロジェクトを pnpm へ移行する場合

npm / Yarn から移行する際は、まず旧来のファイルを削除します。

rm -rf node_modules package-lock.json yarn.lock
pnpm install

pnpm はハードリンク方式で依存関係を管理するため、インストール後のディレクトリ構造が npm と異なります。プロジェクト内の node_modules/.pnpm 以下に全パッケージが格納され、各パッケージのルートにはシンボリックリンクが張られます。これにより、幽霊依存(phantom dependencies)が防止されます。


STEP 2|pnpm のセキュリティ設定を固める

このステップでやること

.npmrcpnpm-workspace.yaml にセキュリティ設定を追記し、サプライチェーン攻撃への耐性を高めます。

なぜ npm install が危険になったのか

2025〜2026年のサプライチェーン攻撃の典型的なパターンは2つです。

パターン1:タイポスクワッティング+即時公開 攻撃者は有名パッケージに酷似した名前でマルウェアを公開します。開発者が npm install した瞬間、公開から数分以内の「出たて」バージョンを踏んでしまうリスクがあります。

パターン2:postinstall スクリプトの悪用 npm install は既定でインストール後スクリプトを実行します。正規パッケージのアカウントが乗っ取られた場合、悪意あるビルドスクリプトが仕込まれる恐れがあります。

minimumReleaseAge で「出たての依存」を採用しない

pnpm v11 では minimumReleaseAge がデフォルト 1440 分(1日)に設定されています。これを7日に引き上げることで、タイポスクワッティング攻撃への耐性が大幅に向上します。

# .npmrc
minimumReleaseAge=7 days
minimumReleaseAgeExcludePrune=true

minimumReleaseAgeExcludePrune=true を設定すると、猶予期間中のパッケージを除外リストから自動的に整理してくれます。

allowBuilds でビルドスクリプトを許可制にする

pnpm v11 では onlyBuiltDependencies の後継として allowBuilds が導入されました。ビルドスクリプトの実行を明示的に許可したパッケージのみに限定できます。

# .npmrc
allowBuilds[]=sharp
allowBuilds[]=esbuild
allowBuilds[]=@next/swc
allowBuilds[]=lightningcss

ここに列挙していないパッケージのビルドスクリプトは実行されません。万が一悪意あるパッケージが混入しても、任意コード実行を防ぐ重要な防衛ラインです。

完成版 .npmrc

# .npmrc

# --- サプライチェーンセキュリティ ---
# 公開から7日未満のパッケージを採用しない(タイポスクワッティング対策)
minimumReleaseAge=7 days
minimumReleaseAgeExcludePrune=true

# ビルドスクリプトの実行を許可するパッケージを明示
allowBuilds[]=sharp
allowBuilds[]=esbuild
allowBuilds[]=@next/swc
allowBuilds[]=lightningcss

# 異常な依存パスをブロック(v11デフォルトON、明示的に記載)
blockExoticSubdeps=true

# バージョンを ^ なしで固定する(lockfileと合わせて完全固定)
save-exact=true

# --- パフォーマンス ---
# ストアの共有を有効化(ディスク節約)
shamefully-hoist=false

完成版 pnpm-workspace.yaml

# pnpm-workspace.yaml
packages:
  - "."

# カタログ機能でバージョンを一元管理(モノレポ対応)
catalog:
  react: "19.1.0"
  react-dom: "19.1.0"
  next: "16.0.0"
  typescript: "7.0.2"

STEP 3|TypeScript 7.0 を導入する

このステップでやること

TypeScript 7.0 をインストールし、2026年推奨の tsconfig.json に書き換えます。

TypeScript 7.0 とは — Go 言語による完全書き直し(Project Corsa)

2026年7月8日、TypeScript 7.0(v7.0.2)が正式リリースされました。最大のトピックは、コンパイラの実装言語を JavaScript から Go 言語へ完全に書き直した「Project Corsa」の成果です。

重要なのは、型システムや構文はまったく変わっていないという点です。既存の TypeScript コードはそのまま動きます。変わったのはコンパイラの内部実装のみです。

ベンチマークで見る速度向上

Microsoft の公式ブログで公開された計測結果(対象:VS Code リポジトリ):

計測項目 TypeScript 6.x TypeScript 7.0 改善率
完全ビルド 125.7秒 10.6秒 約12倍高速
メモリ使用量 ベースライン 6〜26%削減

この高速化は、Go のマルチスレッドモデルを活かした並列処理によるものです。--checkers フラグで型チェッカーのワーカー数、--builders フラグで並列ビルド数を指定できます。

インストールと動作確認

pnpm add -D typescript@7

インストール後、型エラーがないかを確認します。

pnpm tsc --noEmit

完成版 tsconfig.json

{
  "compilerOptions": {
    // --- 基本設定 ---
    "target": "ES2022",
    "lib": ["ES2022", "DOM", "DOM.Iterable"],
    "module": "ESNext",
    "moduleResolution": "bundler",
    "jsx": "preserve",

    // --- 厳格モード(TS 7.0 でデフォルト化) ---
    "strict": true,

    // --- 追加の型安全設定 ---
    // サイドエフェクトインポートの未チェックを防ぐ(TS 7.0 デフォルト化)
    "noUncheckedSideEffectImports": true,
    // 未使用の変数・パラメータをエラーにする
    "noUnusedLocals": true,
    "noUnusedParameters": true,
    // import type を明示的に書くことを強制する
    "verbatimModuleSyntax": true,

    // --- Node.js ネイティブ TypeScript 実行に備える ---
    // enum・名前空間など「コードを生成する構文」をエラーにする
    // Node.js が --experimental-strip-types で直接実行する際に必要
    "erasableSyntaxOnly": true,

    // --- 並列型チェックの高速化 ---
    // 宣言ファイル生成をコンパイラに任せず並列で行う
    "isolatedDeclarations": true,

    // --- パス解決 ---
    "baseUrl": ".",
    "paths": {
      "@/*": ["./src/*"]
    },

    // --- 出力設定 ---
    "outDir": ".next",
    "noEmit": true,
    "incremental": true,
    "skipLibCheck": true,
    "esModuleInterop": true,
    "allowSyntheticDefaultImports": true,
    "resolveJsonModule": true
  },
  "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"],
  "exclude": ["node_modules"]
}

移行前に必ず確認すべき注意点

TS 7.0 には重要な制限があります。Compiler API を提供していないという点です。webpack や ts-jest など、内部で TypeScript の Compiler API を使用しているツールは、現時点では TS 7.0 に対応できません。

実際の開発現場では「TS 7.0 でビルドしつつ、webpack との連携部分は TS 6.x を並走させる」デュアル運用という選択肢もあります。TS 7.1 で Compiler API の対応が予定されているため、新規プロジェクトであれば Turbopack(Next.js 標準)との組み合わせで TS 7.0 を単体利用するのがベストプラクティスです。


STEP 4|Oxlint で ESLint を置き換える

このステップでやること

ESLint を Oxlint に移行し、高速なリンティング環境を構築します。

Oxlint とは — VoidZero / OXC 製の Rust リンター

Oxlint は、Evan You(Vue.js 作者)が率いる VoidZero が支援する OXC プロジェクトの一部です。2025年8月に v1.0 安定版がリリースされ、2026年3月には JavaScript プラグインのアルファ版も公開されました。

内蔵ルール数は 819 以上(TypeScript・React・Next.js・アクセシビリティ・import を網羅)。ESLint と比較した速度向上の事例では、81秒 → 2.5秒(約32倍)という数字が報告されています。

この高速化の理由は3つです。① Rust 実装による低レベルの高速処理、② 並列処理によるファイル単位の並行解析、③ AST の共有による再計算コストの削減。

自動マイグレーションツールを使う

既存の ESLint 設定がある場合、自動変換ツールを利用できます。

npx @oxlint/migrate

このコマンドが ESLint の flat config(eslint.config.mjs など)を読み込み、.oxlintrc.json を自動生成します。

ESLint を「フォールバック」として残すハイブリッド構成

現時点では Oxlint が対応していないルールも存在します。実際の開発現場でのベストプラクティスは、Oxlint で対応できるルールは Oxlint に任せ、非対応のルールだけを ESLint でカバーするハイブリッド構成です。

pnpm add -D eslint-plugin-oxlint

eslint.config.mjs に以下を追記することで、Oxlint がカバー済みのルールを ESLint 側で重複実行しなくなります。

// eslint.config.mjs
import oxlint from "eslint-plugin-oxlint";

export default [
  // ... 他の設定
  ...oxlint.buildFromOxlintConfigFile("./.oxlintrc.json"),
];

実行順序は「Oxlint → ESLint」が推奨です。Oxlint で高速に大半のルールをチェックし、ESLint は補完的に動かします。

完成版 .oxlintrc.json

{
  "$schema": "https://raw.githubusercontent.com/oxc-project/oxc/main/npm/oxlint/configuration_schema.json",
  "plugins": ["react", "react-hooks", "next", "typescript", "jsx-a11y", "import"],
  "env": {
    "browser": true,
    "es2022": true,
    "node": true
  },
  "rules": {
    // TypeScript
    "typescript/no-explicit-any": "warn",
    "typescript/consistent-type-imports": "error",

    // React
    "react/react-in-jsx-scope": "off",
    "react-hooks/rules-of-hooks": "error",
    "react-hooks/exhaustive-deps": "warn",

    // Next.js
    "next/no-html-link-for-pages": "error",

    // アクセシビリティ
    "jsx-a11y/alt-text": "error",

    // import
    "import/no-duplicates": "error"
  },
  "overrides": [
    {
      "files": ["**/*.test.ts", "**/*.test.tsx"],
      "rules": {
        "typescript/no-explicit-any": "off"
      }
    }
  ]
}

STEP 5|Oxfmt で Prettier を置き換える

このステップでやること

Prettier を Oxfmt に置き換え、フォーマットと Lint の自動修正を一元管理します。

Oxfmt の現在地(v0.36.0 は実用段階)

Oxfmt は OXC プロジェクトのフォーマッターです。v0.36.0 時点で Prettier との出力互換性はほぼ達成されており、新規プロジェクトでは Prettier の代替として実用段階にあります。

pnpm add -D @oxc-project/oxfmt

Prettier 設定を自動変換する

npx oxfmt --migrate=prettier

既存の .prettierrc を読み込み、Oxfmt の設定ファイルを自動生成します。Biome からの移行も --migrate=biome フラグで対応しています。

Oxfmt に内蔵された「地味に嬉しい」機能

Oxfmt は単なるフォーマッターにとどまらず、以下の機能を標準で内蔵しています。

1. import 文の自動整序 eslint-plugin-simple-import-sort@trivago/prettier-plugin-sort-imports が不要になります。

2. Tailwind CSS クラスの並び順整形 prettier-plugin-tailwindcss が不要になります。Tailwind の公式推奨順に自動でクラスを並べ替えます。

3. package.json フィールド順序の正規化 nameversionscripts といったフィールドを慣習的な順序に自動整列します。

VS Code で保存時に自動整形・自動修正する

OXC の VS Code 拡張をインストールします(拡張 ID: oxc.oxc-vscode)。

// .vscode/settings.json
{
  // デフォルトフォーマッターを Oxfmt に設定
  "editor.defaultFormatter": "oxc.oxc-vscode",
  // 保存時に自動フォーマット
  "editor.formatOnSave": true,
  // 保存時に Oxlint の自動修正も実行
  "editor.codeActionsOnSave": {
    "source.fixAll.oxc": "explicit"
  },
  // TypeScript / TSX ファイルで Oxfmt を使用
  "[typescript]": {
    "editor.defaultFormatter": "oxc.oxc-vscode"
  },
  "[typescriptreact]": {
    "editor.defaultFormatter": "oxc.oxc-vscode"
  },
  "[javascript]": {
    "editor.defaultFormatter": "oxc.oxc-vscode"
  },
  "[json]": {
    "editor.defaultFormatter": "oxc.oxc-vscode"
  }
}

STEP 6|Tailwind CSS とスタイリング環境を整える

このステップでやること

Tailwind CSS v4 のセットアップと、Oxfmt のクラス順ソートとの共存を確認します。

Tailwind CSS v4 のセットアップ

pnpm create next-app で Tailwind を選択した場合、基本設定はすでに完了しています。v4 では設定ファイルが大幅に簡略化され、tailwind.config.ts の代わりに CSS ファイル内で設定を完結できます。

/* src/app/globals.css */
@import "tailwindcss";

/* カスタムテーマ設定(v4 スタイル) */
@theme {
  --color-primary: oklch(0.5 0.2 250);
  --font-sans: "Inter", sans-serif;
}

動作確認用のサンプルコンポーネント

// src/components/Button.tsx
type ButtonProps = {
  children: React.ReactNode;
  variant?: "primary" | "secondary";
  onClick?: () => void;
};

export function Button({
  children,
  variant = "primary",
  onClick,
}: ButtonProps) {
  return (
    <button
      type="button"
      onClick={onClick}
      // Oxfmt が Tailwind クラスを自動整序します
      className={
        variant === "primary"
          ? "rounded-md bg-blue-600 px-4 py-2 text-sm font-medium text-white hover:bg-blue-700 focus:outline-none focus:ring-2 focus:ring-blue-500 focus:ring-offset-2"
          : "rounded-md border border-gray-300 bg-white px-4 py-2 text-sm font-medium text-gray-700 hover:bg-gray-50"
      }
    >
      {children}
    </button>
  );
}

STEP 7|GitHub Actions で CI を組む

このステップでやること

型チェック・Lint・フォーマット・ビルドの4ジョブを持つ CI ワークフローを構築します。Actions の SHA 固定も実施します。

Actions の SHA 固定は「新たな最低水準」

2026年現在、GitHub Actions のステップで uses: actions/checkout@v4 のようにバージョンタグを指定することはセキュリティ的に不十分とみなされるようになりました。

理由はタグの移動可能性です。@v4 というタグは、リポジトリ管理者が任意のコミットに付け替えることができます。アカウントが乗っ取られた場合、@v4 が悪意あるコードを指すよう書き換えられても、CI のワークフローファイルには変更が現れません。

対策は40文字のコミット SHA で固定することです。

# ❌ タグ指定(セキュリティ的に不十分)
uses: actions/checkout@v4

# ✅ SHA 固定(2026年の最低水準)
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2

pinact で SHA 固定を自動化する

手動で SHA を調べて記述するのは非現実的です。pinact を使うと一括で SHA 固定できます。

# pinact のインストールと実行
go install github.com/suzuki-shunsuke/pinact/cmd/pinact@latest
pinact run

完成版 .github/workflows/ci.yml

name: CI

on:
  push:
    branches: [main]
  pull_request:
    branches: [main]

# 最小権限の原則:デフォルトで読み取り専用
permissions:
  contents: read

jobs:
  ci:
    name: Type Check / Lint / Format / Build
    runs-on: ubuntu-latest
    timeout-minutes: 15

    steps:
      # SHA固定(v4.2.2)
      - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683

      # pnpm のセットアップ(SHA固定済み)
      - uses: pnpm/action-setup@a3252b7d380b931fa2ef01cb1a3bc9ad3b3b94ae # v4.1.0
        with:
          version: 11

      # Node.js のセットアップ(pnpm キャッシュ込み)
      - uses: actions/setup-node@39370e3970a6d050c480ffad4ff0ed4d3fdee5af # v4.1.0
        with:
          node-version: "22"
          cache: "pnpm"

      - name: Install dependencies
        run: pnpm install --frozen-lockfile

      - name: Type check
        run: pnpm tsc --noEmit

      - name: Lint (Oxlint)
        run: pnpm oxlint .

      - name: Lint (ESLint fallback)
        run: pnpm eslint .

      - name: Format check (Oxfmt)
        run: pnpm oxfmt --check .

      - name: Build
        run: pnpm build

actionlint でワークフローの記述ミスを検出する

# actionlint のインストール
go install github.com/rhysd/actionlint/cmd/actionlint@latest

# ワークフローの静的解析
actionlint

actionlintpermissions ブロックの欠落、無効な式の記述、シェルスクリプトのミスなどを検出します。CI に組み込むことで、ワークフロー自体の品質を保証できます。

zizmor でワークフローをセキュリティ静的解析する

pip install zizmor
zizmor .github/workflows/

zizmor は GitHub Actions ワークフロー専用のセキュリティ静的解析ツールです。2026年に特に注目されている理由は、script injection${{ github.event.pull_request.title }} のような信頼できない入力を run: 内で展開するパターン)や、過剰な権限設定を自動検出できる点です。


STEP 8|Dependabot で依存更新を自動化する

このステップでやること

Dependabot を設定し、STEP 2 の pnpm セキュリティ設定と連携した自動更新を構築します。

cooldown を pnpm の minimumReleaseAge と同期させる

STEP 2 で pnpm の minimumReleaseAge を7日に設定しました。Dependabot 側の cooldown(更新 PR を作成するまでの待機期間)も7日に合わせることで、「pnpm が採用しない期間中に Dependabot が PR を作る」という矛盾を防げます。

セキュリティアップデートだけは grouping 対象外にする

通常の依存更新は週1回まとめて PR を作るよう groups 設定します。しかしセキュリティ修正は即時対応が必要なため、grouping の対象外にします。

完成版 .github/dependabot.yml

version: 2

updates:
  # npm(pnpm)の依存更新
  - package-ecosystem: "npm"
    directory: "/"
    schedule:
      interval: "weekly"
      day: "monday"
      time: "09:00"
      timezone: "Asia/Tokyo"

    # pnpm の minimumReleaseAge=7 days と同期
    cooldown:
      default-days: 7
      # セキュリティアップデートは待機なし
      security-days: 0

    # 更新 PR を種類別にまとめて週1回(レビュー負荷を下げる)
    groups:
      dependencies:
        patterns:
          - "*"
        # セキュリティアップデートは grouping 対象外
        exclude-patterns:
          - "!"
        update-types:
          - "minor"
          - "patch"

    # PR の上限数
    open-pull-requests-limit: 10

    # ラベルの自動付与
    labels:
      - "dependencies"

  # GitHub Actions の更新(SHA固定済み Actions の更新)
  - package-ecosystem: "github-actions"
    directory: "/"
    schedule:
      interval: "weekly"
      day: "monday"
      time: "09:00"
      timezone: "Asia/Tokyo"

    # SHA固定済み Actions を更新するために必要
    enable-beta-ecosystems: true

    cooldown:
      default-days: 7
      security-days: 0

    groups:
      github-actions:
        patterns:
          - "*"

    labels:
      - "github-actions"
      - "dependencies"

完成したテンプレートの動作確認

ローカルでの検証コマンド一覧

# 依存関係のインストール
pnpm install

# 型チェック
pnpm tsc --noEmit

# Lint(Oxlint → ESLint の順)
pnpm oxlint .
pnpm eslint .

# フォーマットチェック(差分がなければ OK)
pnpm oxfmt --check .

# フォーマットの適用(初回移行時など)
pnpm oxfmt .

# ビルド
pnpm build

# 開発サーバー起動
pnpm dev

わざとエラーを入れて CI が落ちることを確認する

設定が正しく機能しているか確認するため、意図的にエラーを混入してみましょう。

// src/app/page.tsx に追記
const unusedVariable = "これは使われません"; // noUnusedLocals でエラー

pnpm tsc --noEmit を実行すると、以下のエラーが出るはずです。

error TS6133: 'unusedVariable' is declared but its value is never read.

確認できたら元に戻してコミットします。

完成後のディレクトリ構成

my-next-app/
├── .github/
│   ├── workflows/
│   │   └── ci.yml             # SHA固定済み CI(型チェック/Lint/Format/Build)
│   └── dependabot.yml         # 週次更新 + cooldown 7日設定
├── .vscode/
│   └── settings.json          # 保存時 Oxfmt 自動フォーマット
├── src/
│   ├── app/
│   │   ├── globals.css        # Tailwind CSS v4 設定
│   │   ├── layout.tsx
│   │   └── page.tsx
│   └── components/
│       └── Button.tsx         # サンプルコンポーネント
├── .npmrc                     # pnpm セキュリティ設定
├── .oxlintrc.json             # Oxlint 設定
├── eslint.config.mjs          # ESLint フォールバック(oxlint-plugin 込み)
├── next.config.ts
├── package.json               # devEngines 設定込み
├── pnpm-workspace.yaml        # catalog でバージョン一元管理
└── tsconfig.json              # TypeScript 7.0 推奨設定

よくある質問(FAQ)

TypeScript 7.0 に今すぐ移行して大丈夫?

型システムに変更はないため、段階的な移行が可能です。ただし Compiler API を必要とする webpack・ts-jest などは TS 7.1 の対応を待つ必要があります。Next.js の Turbopack を使用する新規プロジェクトであれば、現時点でも TS 7.0 を問題なく使えます。

Oxlint は ESLint を完全に置き換えられる?

現時点では非対応のルールが残るため、ハイブリッド構成が現実的な解答です。この記事で解説した「Oxlint → ESLint フォールバック」の構成を採用することで、速度の恩恵を最大限受けながら、カバレッジの欠落を防げます。

Prettier をやめて Oxfmt にすると大量の差分が出ない?

初回移行時は全ファイルに差分が出ます。移行作業は単独の PRとして行い、機能変更と混在させないことをお勧めします。PR のタイトルに「chore: migrate formatter from Prettier to Oxfmt」と明記しておけば、コードレビュー時の混乱を防げます。

minimumReleaseAge を長くすると脆弱性修正が遅れないか?

この懸念は設計上カバーされています。pnpm の minimumReleaseAge はセキュリティアドバイザリが登録されたパッケージを対象外とする仕組みがあります。加えて、Dependabot の security-days: 0 設定により、セキュリティアップデートの PR は待機なしで即日作成されます。通常の依存更新とセキュリティ修正を分けた運用こそが、このテンプレートの核心です。

モノレポや React Router / TanStack Router でも使える?

はい。pnpm-workspace.yamlpackages にサブパッケージのパスを追記するだけでモノレポに対応できます。Oxlint・Oxfmt・CI の設定はルートに1つ置けば全パッケージに適用されます。Next.js 以外のフレームワーク(React Router、TanStack Router)でも、この記事の設定のうちフレームワーク固有の部分(allowBuilds@next/swc など)を差し替えるだけで流用できます。

既存プロジェクトに部分導入する場合、どこから始めるべき?

リスクの低い順に以下の順序を推奨します。

  1. pnpm セキュリティ設定.npmrc の追記のみ、既存コードに影響なし)
  2. Oxlint の導入(ESLint と並走させてから段階的に移行)
  3. Oxfmt の導入(単独 PR で全ファイル差分を出す)
  4. TypeScript 7.0(型エラーがないことを確認してから)
  5. CI の SHA 固定pinact で一括変換)

まとめ — 2026年のテンプレートは「速度」より「デフォルトの安全性」

この記事で導入した設定の振り返りチェックリスト

  • pnpmminimumReleaseAge を7日に設定した
  • allowBuilds で許可パッケージを明示した
  • blockExoticSubdeps=true を確認した
  • TypeScript 7.0 をインストールし tsconfig.json を更新した
  • erasableSyntaxOnlyisolatedDeclarations を有効化した
  • Oxlint を導入し ESLint フォールバックを設定した
  • Oxfmt を導入し保存時自動フォーマットを設定した
  • CI の全ステップを SHA 固定した
  • pinact で SHA 固定を検証した
  • Dependabot の cooldown を7日に設定した
  • セキュリティアップデートは security-days: 0 で即時対応にした

次のステップ

このテンプレートはあくまで「土台」です。実際のプロダクト開発では以下の追加が考えられます。

  • テスト環境:Vitest + Testing Library(Oxlint の vitest プラグインと相性良好)
  • E2E テスト:Playwright(GitHub Actions との連携)
  • デプロイ:Vercel / Cloudflare Workers の環境変数管理
  • 認証:Better Auth / NextAuth v5 の導入パターン

2026年のフロントエンド開発において、セキュリティファーストな設計は「やる気のある人だけが頑張ること」から「デフォルトで備わっていること」へと変わりました。今回構築したテンプレートを起点に、段階的に理解を深めていきましょう。

参考リンク

関連記事

Next.js 16徹底解説:React 19.2時代のフルスタック開発完全ガイド

Next.js 16徹底解説:React 19.2時代のフルスタック開発完全ガイド

Next.js 16とReact 19.2の全変更点を徹底解説。Turbopackのデフォルト化、"use cache"による明示的キャッシュ戦略、破壊的変更の移行手順まで、実務に役立つフルスタック開発の完全ガイドです。

コメント

0/2000