• #SEO
  • #Google Search Console
  • #Cloudflare Pages
  • #trailing slash
  • #canonical
  • #sitemap
開発完了

Google Search Console「リダイレクト」「インデックス未登録」の原因:canonical/サイトマップの末尾スラッシュ不一致

結論

Google Search Consoleで報告される以下2つの問題は、canonical/サイトマップの末尾スラッシュ不一致が有力な原因と考えられる。

報告内容件数原因
ページにリダイレクトがあります31件canonical/サイトマップの末尾スラッシュ不一致
検出 - インデックス未登録209件上記が有力な原因(※他にも品質・重複・クロール優先度など複数要因の可能性あり)

現状の設定(不一致)

項目URL形式設定場所
Cloudflare Pages/path/ (スラッシュ付き)変更不可の仕様
サイトマップ/path/ (スラッシュ付き)generate-sitemap.mjs:64
canonicalタグ/path (スラッシュなし)app/plugins/canonical.ts(自作プラグイン)

対応状況(2026-01-06実施)

app/plugins/canonical.tsnuxt.config.tsを修正し、canonicalタグを末尾スラッシュ付きに統一した。

反映見込み

報告内容反映見込み備考
ページにリダイレクトがあります1〜2週間次回クロール時に解消される見込み
検出 - インデックス未登録2〜4週間複数要因が絡む可能性があり、canonical修正だけで全て解消するかは不明

※GSCの「URL検査」から主要ページの再クロールをリクエストすると早まる可能性あり


問題の状況

1. 「ページにリダイレクトがあります」31件

Google Search Consoleの「ページのインデックス登録」レポートで、31件のURLが「ページにリダイレクトがあります」として報告された。

Google Search Console「ページにリダイレクトがあります」レポート

  • 該当ページ数: 31件
  • 期間: 2025/12/23頃から急増
  • 前回のクロール日: 2026/01/01〜2026/01/02

報告されたURLの例(すべて末尾スラッシュなし):

URL前回のクロール
https://log.eurekapu.com/desktop-extensions2026/01/02
https://log.eurekapu.com/contextual-retrieval2026/01/02
https://log.eurekapu.com/think-tool2026/01/01

2. 「検出 - インデックス未登録」209件

同じく「ページのインデックス登録」で、209ページが「検出 - インデックス未登録」として報告された。

Google Search Console - 検出・インデックス未登録

  • /about - 該当なし(前回のクロール日なし)
  • /blog - 該当なし
  • /blog/ai-native-future-scenarios - 該当なし
  • その他多数...

「該当なし」は「前回のクロール」日付がないことを意味する。Googleがこれらのページをクロール後、インデックスを保留している状態。


原因の分析

Cloudflare Pagesの仕様

Cloudflare Pagesは「末尾スラッシュを強制的に追加する」仕様を持つ。無効化できない

curl -I -s "https://log.eurekapu.com/desktop-extensions"
# HTTP/1.1 308 Permanent Redirect
# Location: /desktop-extensions/

Cloudflare Pages is "an opinionated system that thinks trailing slashes should be there." — Cloudflare Community

現在の実装

// app/plugins/canonical.ts(自作プラグイン)
// このサイトのcanonicalタグはこのプラグインで生成される
const getCanonicalUrl = (path: string) => {
  const cleanPath = path.replace(/\/$/, '') || '/'
  return `${siteUrl}${cleanPath}`  // 末尾スラッシュなし
}
// generate-sitemap.mjs:64
const canonicalUrl = route === '/' ? route : `${route}/`  // 末尾スラッシュ付き

不一致: サイトマップは/path/、canonicalは/path

Googleの視点

「リダイレクト」が報告される流れ

  1. ページをクロール → canonicalタグで /desktop-extensions を発見
  2. /desktop-extensions をクロールしようとする
  3. 308リダイレクト → /desktop-extensions/
  4. 「ページにリダイレクトがあります」として報告

「インデックス未登録」が報告される流れ(推測)

  1. サイトマップで /blog/ を発見
  2. /blog/ にアクセス → 200 OK
  3. ページ内のcanonicalタグを確認 → /blog を指している
  4. /blog/ は正規URLではないと判断
  5. インデックスを保留(「検出 - インデックス未登録」)

※「検出 - インデックス未登録」はcanonical不一致以外にも、ページ品質・重複コンテンツ・クロール優先度など複数の要因で発生する可能性がある。ただし、サイトマップとcanonicalの不一致は有力な原因の一つ。

「リダイレクト」は末尾スラッシュ不一致が原因(Cloudflare Pagesの308強制リダイレクトが有効な限り)。「インデックス未登録」も同じ原因である可能性が高い。


修正方針

方針:canonicalタグを末尾スラッシュ付きに統一

Cloudflare Pagesの仕様に合わせ、末尾スラッシュ付きに統一する。

修正対象ファイル

app/plugins/canonical.ts(メイン修正箇所)

このサイトのcanonicalタグは自作プラグインで生成されており、nuxt.config.tssite.trailingSlashは参照していない。そのため、修正の本体はcanonical.tsである。

// 修正前
const getCanonicalUrl = (path: string) => {
  const cleanPath = path.replace(/\/$/, '') || '/'
  return `${siteUrl}${cleanPath}`
}

// 修正後
const getCanonicalUrl = (path: string) => {
  const cleanPath = path.replace(/\/$/, '') || '/'
  // 全URLを末尾スラッシュ付きに統一(ルートは / 1つ)
  return cleanPath === '/' ? `${siteUrl}/` : `${siteUrl}${cleanPath}/`
}

ルートURLについて

ルートURLも末尾スラッシュ付き(https://log.eurekapu.com/)に統一する。

  • ルート: https://log.eurekapu.com/(スラッシュ1つ)
  • その他: https://log.eurekapu.com/path/
  • コード上は分岐が必要だが、出力は全URL末尾スラッシュ付きで一貫

nuxt.config.ts(参考)

site.trailingSlash@nuxtjs/seoなどのモジュールが参照するが、自作のcanonicalプラグインは参照していない。整合性のためtrueにしておくことを推奨。

site: {
  trailingSlash: true  // Cloudflare Pagesの仕様に合わせる(参考設定)
}

修正後の期待される状態

項目URL形式
Cloudflare Pages/path/
サイトマップ/path/
canonicalタグ/path/

全て一致するため、Googleへの混乱がなくなる。

注意事項

  • 修正後、「ページにリダイレクトがあります」「インデックス未登録」の件数は減少する見込み
  • 既存のインデックスが新しいcanonical URLに統合されるまで数週間かかる可能性がある
  • 内部リンクは末尾スラッシュなしでも機能するが、毎回308リダイレクトが発生する。SEO評価やページ表示速度の観点から、内部リンクも末尾スラッシュ付きに統一することを推奨

対応履歴

2026-01-06: 修正実装

以下の修正を実施:

1. app/plugins/canonical.ts

// 修正前
const getCanonicalUrl = (path: string) => {
  const cleanPath = path.replace(/\/$/, '') || '/'
  return `${siteUrl}${cleanPath}`  // 末尾スラッシュなし
}

// 修正後
const getCanonicalUrl = (path: string) => {
  const cleanPath = path.replace(/\/$/, '') || '/'
  // ルートは / 1つ、その他は末尾スラッシュ付き
  return cleanPath === '/' ? `${siteUrl}/` : `${siteUrl}${cleanPath}/`
}

2. nuxt.config.ts

// 修正前
trailingSlash: false

// 修正後
trailingSlash: true  // Cloudflare Pagesの仕様に合わせて末尾スラッシュ付きに統一

今後の対応

  1. trailingSlash 設定変更の影響範囲を調査
  2. 修正を実装
  3. デプロイ
  4. Google Search Consoleで再クロールをリクエスト(任意)
  5. 1-2週間後にインデックス状況を確認

関連ドキュメント

  • trailing-slash-duplicate-index - trailing slash重複問題の経緯と対策
    • 注意: このドキュメントではtrailingSlash: falseを採用した経緯が記載されているが、本ドキュメントではCloudflare Pagesの仕様に合わせてtrailingSlash: true(末尾スラッシュ付き)に方針転換することを提案している
  • google-index-improvement - インデックス率改善の調査
  • url-structure-improvement - URL構造改善計画

参考リンク