はじめに

Webアプリケーション(Next.js)を運用していく中で、機能の大型アップデートやデータベースの移行など、ユーザーからのアクセスを一時的に遮断して「メンテナンス画面」を表示したいケースがあります。

Amplifyを用いてアプリをHostingしている際、「WAFのIP制限は維持しつつ、ユーザーにはメンテナンス画面を出したい」という場面によく遭遇します。WAF自体でメンテナンス画面(503レスポンス等)を返す方法もありますが、WAFの設定を切り替える際やWebACLを差し替える際に、一時的に設定が外れてしまいアプリケーション自体がリスクに晒されてしまう危険があります。

本記事では、Amplifyのリライトとリダイレクト機能を使うことで、WAFの保護を維持したまま柔軟にメンテナンス画面へ切り替える方法をご紹介します。さらに、GitHub Actionsを用いてこのON/OFFをワンクリックで安全に切り替える仕組みも構築します。

前提条件

項目 内容
ホスティング AWS Amplify Gen 2
フレームワーク Next.js 15
セキュリティ AWS WAF適用済み(IP制限など)

GitHub Secrets / Variables

Settings > Secrets and variables > Actions に以下を登録します。

種別 キー名 内容
Secret OIDC_ROLE_ARN ワークフローが引き受けるIAMロールのARN
Secret OIDC_AWS_REGION Amplifyのホスティングリージョン
Variable AMPLIFY_APP_ID AmplifyのApp ID

メンテナンスページにリダイレクトさせる

1. メンテナンス用静的ファイルの準備

Next.jsプロジェクトの public ディレクトリに、メンテナンス専用のHTMLファイルを配置してデプロイします。

ディレクトリ構成のイメージ

my-nextjs-project/
├── .github/
├── app/
├── public/ # ← 静的ファイルの置き場所
│ ├── favicon.ico
│ ├── images/
│ └── maintenance.html # ここに配置する
├── package.json
└── next.config.js

public 配下のHTML であれば、Next.jsの実行環境(Node.jsランタイム)やバックエンドAPIを一切経由せず、Amplifyのエッジから直接配信されます。そのため、デプロイ中にAPI等が完全に停止していても、確実にメンテナンス画面を表示できます。

メンテナンス画面のサンプル (maintenance.html)

<!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>メンテナンス中</title>
  <style>
    body { font-family: sans-serif; background-color: #f8f9fa; color: #333; display: flex; justify-content: center; align-items: center; height: 100vh; margin: 0; }
    .card { background: white; padding: 2rem; border-radius: 10px; box-shadow: 0 4px 6px rgba(0,0,0,0.1); text-align: center; }
    h1 { color: #0070f3; }
  </style>
</head>
<body>
  <div class="card">
    <h1>メンテナンス中</h1>
    <p>現在、システムのアップデートを行っております。<br>完了までしばらくお待ちください。</p>
  </div>
</body>
</html>

2. Amplifyのリダイレクトルールを設定する

Amplifyコンソールの 「リライトとリダイレクト」 にて、以下のルールを追加します。

[
  {
    "source": "/maintenance.html",
    "status": "200",
    "target": "/maintenance.html"
  },
  {
    "source": "/<*>",
    "status": "302",
    "target": "/maintenance.html"
  }
]

この状態でアプリのURLへアクセスするとメンテナンス画面へ遷移します。

GitHub ActionsからAmplifyのメンテナンスモードを自動切り替えする

次に、GitHub ActionsのworkflowからメンテナンスページのON/OFFを切り替えるワークフローを構築します。

1. リダイレクトルールの定義(JSON)

まずは、Amplifyに適用するリダイレクトルールをファイルとして管理します。.github/scripts/ 配下に保存します。

メンテナンスON設定 (maintenance-on.json)

ユーザーがどのパスにアクセスしても、強制的にメンテナンス画面へ遷移させるために 302 (Redirect) を設定します。

[
  {
    "source": "/maintenance.html",
    "status": "200",
    "target": "/maintenance.html"
  },
  {
    "source": "/<*>",
    "status": "302",
    "target": "/maintenance.html"
  }
]

メンテナンスOFF設定 (maintenance-off.json)

通常時はメンテナンスページへ遷移した場合にTOPページに遷移するようにします。

注意: CLIでルールを更新すると既存のルールがすべて上書きされます。普段からAmplifyのカスタムルールを設定している場合は、必ずその既存ルールもこのファイルに含めてください。

[
  {
    "source": "/maintenance.html",
    "status": "302",
    "target": "/"
  }
]

2. 切り替え用シェルスクリプト

AWS CLIを使ってAmplify Appの設定をアップデートするスクリプト(switch-maintenance.sh)です。

#!/usr/bin/env bash
set -euo pipefail

# Usage: ./switch-maintenance.sh <app_id> <on|off>
APP_ID="$1"
MODE="$2"
REGION="${AWS_REGION:-ap-northeast-1}"
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"

if [ "$MODE" = "on" ]; then
  RULES_FILE="${SCRIPT_DIR}/maintenance-on.json"
  echo "Switching to MAINTENANCE mode (App: ${APP_ID})"
else
  RULES_FILE="${SCRIPT_DIR}/maintenance-off.json"
  echo "Switching to NORMAL mode (App: ${APP_ID})"
fi

# JSONファイルからルールを読み込み
RULES=$(cat "$RULES_FILE")

# Amplifyの設定を更新
aws amplify update-app \
  --app-id "$APP_ID" \
  --custom-rules "$RULES" \
  --region "$REGION"

echo "✅ Successfully updated Amplify custom rules."

3. GitHub Actions ワークフロー

GitHubの「Actions」タブから手動で実行(workflow_dispatch)できるようにワークフロー(maintenance_switch.yml)を定義します。

name: Maintenance Switch

on:
  workflow_dispatch:
    inputs:
      environment:
        description: "Environment"
        required: true
        default: dev
        type: choice
        options:
          - dev
          - stage
          - prod
      mode:
        description: "Switch to"
        required: true
        type: choice
        options:
          - maintenance
          - normal

permissions:
  id-token: write
  contents: read

jobs:
  emergency-switch:
    runs-on: ubuntu-latest
    environment:
      name: ${{ github.event.inputs.environment }}
    steps:
      - uses: actions/checkout@v5

      - name: Configure AWS credentials
        uses: aws-actions/configure-aws-credentials@v6
        with:
          role-to-assume: ${{ secrets.OIDC_ROLE_ARN }}
          aws-region: ${{ secrets.OIDC_AWS_REGION }}

      - name: Make scripts executable
        run: chmod +x .github/scripts/*.sh

      - name: Switch mode
        run: |
          if [ "${{ github.event.inputs.mode }}" = "maintenance" ]; then
            MODE="on"
          else
            MODE="off"
          fi

          .github/scripts/switch-maintenance.sh \
            "${{ vars.AMPLIFY_APP_ID }}" \
            "${MODE}"

これで、GitHubのActionsタブからプルダウンを選択して実行するだけで、ワンクリックでメンテナンスのON/OFFが切り替えられるようになります。

まとめ

Amplifyのリダイレクトルールは、メンテナンス運用においても頼りになります。同じ構成で悩んでいる方の参考になれば幸いです。