0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Angular×Netlifyで404エラーを解決する`_redirects`の完全ガイド

Last updated at Posted at 2025-05-25

はじめに

AngularアプリをNetlifyにデプロイした際、「404 Not Found」エラーに遭遇したことはありませんか?この記事では、その原因と解決方法である_redirectsファイルについて詳しく解説します。

問題の背景:SPAとルーティングの仕組み

従来のWebサイト(MPA)とSPAの違い

従来のWebサイト(Multi-Page Application)

example.com/home     → home.html(実際のファイル)
example.com/about    → about.html(実際のファイル)
example.com/contact  → contact.html(実際のファイル)

SPA(Single Page Application)

example.com/         → index.html(実際のファイル)
example.com/todos    → index.html(ファイルは存在しない)
example.com/profile → index.html(ファイルは存在しない)

AngularのようなSPAでは、実際にはindex.htmlという1つのファイルしか存在せず、JavaScriptがブラウザ内でルーティングを処理します。

404エラーが発生するケース

1. 直接URLアクセス

ユーザーがhttps://yourapp.netlify.app/todosに直接アクセスした場合:

1. ブラウザ → Netlifyサーバー: "todos.htmlファイルをください"
2. Netlifyサーバー: "todos.htmlは存在しません" → 404エラー

2. ページリロード(F5キー)

現在/todosページにいる状態でページをリロードした場合

3. ブックマークからのアクセス

保存されたURL(例:/profile)から直接アクセスする場合

解決方法:_redirectsファイルの設定

基本的な設定

プロジェクトのpublicディレクトリに_redirectsファイルを作成します:

/*    /index.html   200

ファイル構成例

frontend-angular/
├── public/
│   └── _redirects          # ← ここに配置
├── src/
│   ├── app/
│   └── index.html
├── angular.json
└── package.json

angular.jsonでの自動コピー設定

angular.jsonassets設定で、ビルド時に自動的に_redirectsファイルがコピーされるようになっています:

{
  "assets": [
    {
      "glob": "**/*",
      "input": "public"
    }
  ]
}

_redirectsの詳細仕様

基本構文

[source] [destination] [status_code]

パラメータ説明

  • /*: すべてのパス(ワイルドカード)
  • /index.html: リダイレクト先
  • 200: HTTPステータスコード

なぜ200ステータスが重要か

301/302リダイレクトの場合(❌ 間違い)

/*    /index.html   301

# 動作:
1. ユーザーが /todos にアクセス
2. ブラウザのURLが / に変更される
3. Angularが正しいルートを認識できない

200ステータスの場合(✅ 正解)

/*    /index.html   200

# 動作:
1. ユーザーが /todos にアクセス
2. ブラウザのURLは /todos のまま
3. index.htmlの内容が返される
4. AngularがURLを見て正しいコンポーネントを表示

実装手順

1. _redirectsファイルの作成

# publicディレクトリに作成
echo "/*    /index.html   200" > public/_redirects

2. ビルドの実行

ng build

3. ビルド結果の確認

ls dist/your-app-name/browser/
# _redirects ファイルが含まれていることを確認

代替設定方法:netlify.toml

プロジェクトルートにnetlify.tomlファイルを作成する方法もあります:

[build]
  publish = "dist/your-app-name/browser"
  command = "npm run build"

[[redirects]]
  from = "/*"
  to = "/index.html"
  status = 200

高度な設定例

API呼び出しの除外

# API呼び出しは除外
/api/*  https://your-backend-api.com/api/:splat  200

# その他はSPAルーティング
/*      /index.html                              200

特定のファイルタイプの除外

# 静的ファイルは除外
/*.js   /404.html  404
/*.css  /404.html  404
/*.png  /404.html  404

# その他はSPAルーティング
/*      /index.html  200

環境別API設定の最適化

環境設定ファイルの作成

src/environments/environment.ts

export const environment = {
  production: false,
  apiUrl: 'http://localhost:8080/api'
};

src/environments/environment.prod.ts

export const environment = {
  production: true,
  apiUrl: 'https://your-backend-api.com/api'
};

サービスでの使用

import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { environment } from '../../environments/environment';

@Injectable({
  providedIn: 'root'
})
export class TodoService {
  private apiUrl = `${environment.apiUrl}/todos`;

  constructor(private http: HttpClient) { }

  getTodos() {
    return this.http.get(this.apiUrl);
  }
}

トラブルシューティング

よくある問題と解決方法

  1. _redirectsファイルが含まれない

    • publicディレクトリに配置されているか確認
    • angular.jsonassets設定を確認
  2. リダイレクトが効かない

    • ファイル名が_redirects(アンダースコア)になっているか確認
    • 構文が正しいか確認(スペース区切り)
  3. 無限リダイレクト

    • ステータスコードが200になっているか確認

まとめ

  • AngularのようなSPAをNetlifyにデプロイする際は_redirectsファイルが必須
  • /* /index.html 200の設定で直接URLアクセスとページリロードの問題を解決
  • publicディレクトリに配置することで、ビルド時に自動的に含まれる
  • 環境変数を使用してAPI設定を適切に管理する

この設定により、ユーザーがどのURLからアクセスしても、正常にAngularアプリケーションが動作するようになります。

参考リンク

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?