SHOEISHA iD

※旧SEメンバーシップ会員の方は、同じ登録情報(メールアドレス&パスワード)でログインいただけます

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

LINEフロントエンドレンジャーのWeb開発術

SEO検証! GoogleはAngularJSを正しくクロールするのか?(2015年2月版)

LINEフロントエンドレンジャーのWeb開発術 第3回


  • X ポスト
  • このエントリーをはてなブックマークに追加

検証の履歴(2)

2015/01/30 インデックス確認

概要

項目 内容
結果 変化なし
問題 Endがインデックスされていない
考察 クローラーがアクセスしていないのでは?
対応 LPページに各LISTのEND-1へのリンクを設置し、インデックスを送信

詳細

 インデックス状況に変化はありませんでした。「sitemap.xml」も「Fetch as Google」を使用したインデックス送信も失敗してしまいました。

 この頃から、「クロールはされているが別の要因でインデックスされないのでは?」という疑問が湧きました。今回は、最後のクロール対策としてLPページに各LISTのEND-1へのリンクを設置し、LPに対してインデックス送信を行いました。

2015/02/05 インデックス確認

概要

項目 内容
結果 変化なし
問題 Endがインデックスされていない
考察 クローラーは正常に動いているのでは?
調査 クローラーは正常に動いていた
対応 HTMLやJavaScriptに問題がないかを調査

詳細

 インデックス状況に変化はありませんでした。

 検証開始から3か月経過しましたが、インデックス状況に変化は見られません。ここまで来ると「クロールはされているが別の要因でインデックスされないのでは?」という、思いが強くなりました。

 クロール状況を確認するため、サーバーのアクセスログを集計してGoogleクローラーのアクセス状況を確認しました。当初は簡単な検証を行おうと思っていたため、アクセスログの目視チェックは検証項目に含めていませんでした。

アクセスログ解析結果
 

 結果、クローラーは1か月に2~3回ほどEndページにアクセスしていたという事実が判明しました。

 実は最初にListがインデックスされた2014/11/06には、List-5,List-6のENDページをクロールしていました。もちろん、「/list6/end/{{item.id}}」の形式のURLにもクローラーは度々アクセスしていましたが、List-5,List-6のENDに関してはすべてクロールされていました。

 List-4のENDに関しては上記と異なり、2015/01/08に初めて正常にクロールされました。つまり、2014/01/07に、List-4_End-1をインデックス送信したことがきっかけで、はじめてEndページのURLが認識されたと言えます。

 となると、インデクサの処理が失敗していることになります。そのため、HTMLやJavaScriptコードに問題がないか、という調査を行うことにしました。

2015/02/13 インデックス確認

概要

項目 内容
結果 変化なし
問題 Endがインデックスされていない
考察 コンテンツが重複と認識されると検索結果に表示されないのでは?
対応 重複していたOGPを削除し、LPに対してインデックス送信

詳細

 インデックス状況に変化はありませんでした。

 クロールされているのにインデックスが行われない状況に疑問を感じたので、試しに「site:」コマンドではなく、各ENDのURLをGoogleで検索してみました。

sitemap送信ページサンプル
sitemap送信ページサンプル

 すると、インデックス確認できなかったENDページが検索結果に表示されました。

 上記のタイトルやスニペットの内容を確認すると、LISTページと同様の物が出ていました。最初は重複コンテンツ扱いになり検索結果画面に表示されていないだけかと思いましたが、ウェブマスターツールで確認してもインデックス数は0件でした。

 そのため、URLは判明しているがインデクサが止まっている特殊な状態だと判断しました。

 その結果を基に、重複と判断されるようなコードを確認したところ、OGPの設定内容がLIST、ENDで同一物になっていたことが判明しました。

<meta property="og:locale" content="ja_JP">
<meta property="og:type" content="website">
<meta property="og:site_name" content="sample site">
<meta property="og:title" content="サンプル一覧 No5">
<meta property="og:description" content="サンプル一覧 No5のアイテム一覧ページです。">
<meta property="og:url" content="http://example.com/list05/">
<meta property="og:image" content="http://example.com/img/img01.jpg">

 OGPに関しては、2014年の5月に「Webmasters Stack Exchange」に投稿されたOGPの質問で、GoogleのJohn Mueller氏が「Web検索ではOGPを使用していない」とコメントしていたため、軽視していました。

 ですが、念のため、OGP削除後にLPに対してインデックス送信を行いました。

 予想としては、List-6のENDは引き続き重複コンテンツとみなされ表示されない可能性があります。しかし、List-4、List-5のENDはOGPを除外したことにより、コンテンツの重複判定が軽減され、正常にインデックスされる可能性があると判断しました。

2015/02/13 インデックス確認

概要

項目 内容
結果 List-4_End1がインデックス
問題 List-4_End1のみなぜインデックスされたのか?
考察 「Fetch as Google」を使い直接インデックス送信しなければならないのでは?
対応 List-4_End2、List-5_End2、List-6_End2をインデックス送信

詳細

 ついにインデックス状況に変化がありました。

 List-4_End1のみインデックスに反映されました。

No router Default Content List Index End Index
List-1 hash(#) none ×
List-2 hash(#) Angular Template ×
List-3 hash(#) Publish HTML ×
List-4 html5Mode none
List-5 html5Mode Angular Template ×
List-6 html5Mode Publish HTML ×

 OGP削除の影響なのか、は定かではありませんが、コンテンツの重複解消が影響していると前提におき考察を進めました。

 この結果を見て私が疑問に思ったのは、なぜList-4_End1のみインデックスされ、他のページはインデックスされていないのか?

 今までの対応を振り返ると、List-4_End1に関してはウェブマスターツールの「Fetch as Google」を使い直接インデックス送信を行っていました。「Fetch as Google」を使いインデックス送信を行わなければ、インデックスに反映されない可能性があると判断しました。

 この考察を基に最後の対策を行うことにしました。まだクロール施策を行っていないEndページである、List-4_End2、List-5_End2、List-6_End2を直接インデックス送信しました。

 以後、送信したページがインデックスに表示されるのであれば、「Fetch as Google」によるインデックス送信をしなければ検索結果に反映されないという結論がでます。

2015/02/17 インデックス最終確認

概要

項目 内容
結果 List-4_End2、List-5_End2がインデックス
問題 List-6_End-2はなぜインデックスされなかったのか?
考察 重複コンテンツと認識されたのでは?
対応 検証終了

詳細

 前回送信した、List-4_End2、List-5_End2がインデックスに反映されました。

No router Default Content List Index End Index
List-1 hash(#) none ×
List-2 hash(#) Angular Template ×
List-3 hash(#) Publish HTML ×
List-4 html5Mode none
List-5 html5Mode Angular Template
List-6 html5Mode Publish HTML ×

 しかし、前回インデックス送信を行ったList-6_End-2はインデックスに反映されませんでした。

 List-6_End-2に関しては、リストと同様のコンテンツをHTML内に入れているため、コンテンツ重複と判断されていると予測しました。

 今回、List-4_End2、List-5_End2がインデックスされたことによって、私の中で1つの結論がでました。

最終結果

 今回の検証の最終結果は、下記のようになりました。

施策を行わない場合

No router Default Content List Index End Index
List-1 hash(#) none ×
List-2 hash(#) Angular Template ×
List-3 hash(#) Publish HTML ×
List-4 html5Mode none ×
List-5 html5Mode Angular Template ×
List-6 html5Mode Publish HTML ×

施策を行った場合

No router Default Content List Index End Index
List-1 hash(#) none ×
List-2 hash(#) Angular Template ×
List-3 hash(#) Publish HTML ×
List-4 html5Mode none
List-5 html5Mode Angular Template
List-6 html5Mode Publish HTML ×

考察のまとめ

日時 事象 考察 結果
2014/11/06 一部ページのTitleにAngular変数が入っている 時間が経過すれば改善されるのでは? 改善
2014/11/27 Endがインデックスされない クローラーがアクセスしていないのでは? クローラーはアクセスしていた。
2015/02/06 Endがインデックスされない コンテンツが重複と認識されると検索結果に表示されないのでは? 影響あり
2015/02/06 一部ページのみインデックス 「Fetch as Google」を使い直接インデックス送信しなけばならないのでは? コンテンツ重複の影響がない、インデックス送信したページのみ検索結果に反映

今回実施したENDページインデックス施策

日時 対応 詳細 結果
2014/11/27 「Fetch as Google」 LPに対してインデックス送信 ×
2014/12/16 サイトマップ EndのURLを記載し送信 ×
2014/01/07 「Fetch as Google」 List-4_End1のみインデックスの送信 × (後に影響)
2015/01/30 「Fetch as Google」 LPページに各LISTのEND-1へのリンクを設置しインデックスの送信 ×
2015/02/06 HTML OGPを削除 List-4_End1がインデックス
2015/02/13 「Fetch as Google」 List-4_End2、List-5_End2、List-6_End2をインデックス送信 List-4_End2、List-5_End2がインデックス

結論

 普通にAngularJSを使いシングルページアプリを作成しても、一部ページはインデックスされません。ただし、下記の条件を満たせばHTMLSnapShotを使わなくても検索結果に反映できる可能性があります。今回の私のケースでは成功しました。

  • html5Mode(pushState)。
  • ウェブマスターツールの「Fetch as Google」を使い、画面レンダリング後インデックスを送信。
  • OGPやHTMLなどが重複しないようにする。

 しかし、シングルページアプリケーションで仮想的に作っているパスを「Fetch as Google」を使い、手動でインデックス送信するのは現実的ではありません。小規模サイトであればともかく、動的にページが増える大規模サイトだと不可能と言えるでしょう。

 JavaScriptのインデックス処理に関しては現在成長中の段階と言えます。1か月足らずで状況が変わる可能性もあれば、1年後も状況が変わらない可能性もあります。その状況を考えると、確実と言われており導入事例の多い「Html Snapshot」を使うほうがよいでしょう。

 もしくは、JavaScriptを活用したシングルページアプリではなく、純粋にサーバー側でHTMLを生成したアプリケーションを作ることをおすすめします。

最後に

 今回のAngularJSを利用したSEO検証ではこのような結果がでました。

 しかし、SEOは環境によって大きく結果が左右されます。今回は単純なシングルページアプリケーションで試したため、このような結果が出ました。そのため、複雑なシングルページアプリケーションの場合、APIのセキュリティ対応でクローラーがAPIの結果を取得できず失敗してしまう可能性もあるでしょう。

 また、AngularJSに関しては「Dirty checking」やAPIのパフォーマンスの影響でレンダリングが失敗してしまう可能性もあります。

 今回の方法を使用しても環境によっては失敗してしまう方や、中には特に施策を行わなくてもインデックスされたという方もいると思われます。今回の話も一つの検証事例として参考程度に頭に入れていただければと思います。

追記(2015年3月18日)

 2015年2月26日に発表された、スマートフォン向け検索でのランキングの変更についてがきっかけで、3月に入りインデクサの精度が変わった模様です。「Fetch as Google」を利用しなくても検索結果に表示されるようになりはじめてきました。 シングルページアプリケーションのインデックスで苦労をせずに済む日も近いかもしれません。

修正履歴

この記事は参考になりましたか?

  • X ポスト
  • このエントリーをはてなブックマークに追加
LINEフロントエンドレンジャーのWeb開発術連載記事一覧

もっと読む

この記事の著者

姜 勝陽(LINE株式会社)(キョウ ショウヨウ)

LINE株式会社に在籍しているフロントエンドエンジニア。LINE内Webアプリを担当。2002年からSEOの情報を趣味の一環として収集している。最近はサーバーサイドレンダリング無しで、Single Page ApplicationをGoogleに認識させる為の検証を進めている。

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

この記事は参考になりましたか?

この記事をシェア

  • X ポスト
  • このエントリーをはてなブックマークに追加
CodeZine(コードジン)
https://codezine.jp/article/detail/8543 2016/07/19 11:09

おすすめ

アクセスランキング

アクセスランキング

イベント

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

新規会員登録無料のご案内

  • ・全ての過去記事が閲覧できます
  • ・会員限定メルマガを受信できます

メールバックナンバー

アクセスランキング

アクセスランキング