こんにちは、フロント周りを担当しているY.A.です。DevToolsの機能(tips編)』でいくつかtipsを紹介しました。https://techblog.gmo-ap.jp/2019/07/11/using-chromedevtools-like-pro-tips/ただ実際にこれらを「どういう場面で」「どのように使用するのか」、イメージ付いていない方もいたかもしれません。DevToolsを使用して不具合調査するときは、1つのパネル/機能だけで原因特定まで至らないことも多いです。ほとんどの場合仮説とその検証のために、複数のパネル/機能を使用しますので、そのため少し難易度高く感じている方もいるかと思います。今回は3つの具体例を通して、それらパネル/機能をどう活用できるのか説明したいと思います。事例はいずれもメディアサイト(または広告や様々なサードパーティJavaScriptが入っているサイト)を想定しています。それぞれのセクションでサンプルページも用意したので、必要に応じてご自身の手で確かめてみてください。本稿では「ブレークポイント」をよく使います。デバッグする』が詳しいので、触れたことない方は事前に目を通しておくと、よりイメージつきやすいかと思います。Listeners/Sources/Breakpoint)サイト内で3つ目のリンクの遷移がうまくいっていない(404)になるという不具合があり、調べることになりました。パネルを開いてみたところ、aタグのhrefの値(URL)は問題なさそうですが、確かにユーザーがタップするとhrefに指定してあるURLに遷移しませんでした。上からリンクをタップしていく様子(gif)↓さっそく調べます。本件はタップしたときのアクションに不具合が起きていることから、何かしらJSのイベントリスナーが関係していると考えます。Listeners』を開きます。ここでイベントリスナーを確認します。『Elements』パネル内にて、DOMノードを選択(クリック)します。するとそのノードに紐づいたイベントリスナーが表示されます。今回は問題のある3つ目のliタグのノードを選択しています。チェックが入っていると、『Elements』パネルでクリックしたDOMノードを基点に、祖先のイベントまで検知されて表示されます。チェックを外して絞ります。詳しくは前回記事をご参考ください。https://techblog.gmo-ap.jp/2019/07/11/using-chromedevtools-like-pro-tips/#section5パネルを見ると、DOMノードにクリックイベントが設定されていることが分かりました。それではイベントの横にある▼のアイコンをクリックしてイベントリスナーを展開します。すると要素と、イベントハンドラへのリンクが表示されています。リンク先へいってもよいのですが、ひとまず先にこのイベントが不具合に関係しているかどうかを見てみます。『Remove』という文字列が表示されます。『Remove』をクリックしてイベントの紐付けを解除します。解除した上で改めて3つ目のリンクをタップしてみます。イベントを解除した上でタップした動き(gif)↓すると正常に遷移しました。このイベントリスナーが何かしらの不具合を生んでいる可能性が高いようです。ここからはそのハンドラにブレークポイントを貼って処理を追っていきます。先のイベントハンドラを見るために、ページをリロードし直します。リンク(click.js)も再度表示されますので、それをクリックします。クリックすると、該当箇所が『Sources』パネルで展開されます。それではブレークポイントを貼ります。ブレークポイントは、JSの実行を一時的に止めるポイントのことです。貼ることで、そこを起点にステップ実行を行えるので、じっくり処理の流れを確認することができます。ブレークポイントの設定はソースの任意の行をクリックすることでできます。クリックした後の直後の動きを見たいので、下記箇所に貼ります。それでは改めて3つ目のリンクをタップしてみます。イベントが発火し、ブレークポイントを貼った箇所で一旦実行が止まりました。このときUIの画面はグレーアウトします。ここからはステップ実行で一つひとつ処理を追っていきます。実際に実行していくとわかると思いますが、3つめのリンクをクリックした時だけ、「href」という変数の値に「undefined」が入ります。「undefined」になる理由を調べていきましょう。コードを目で追っていっても良いですし、ブレークポイントを貼ったまま、リロード/リンクタップ/ステップ実行を何回か繰り返してみても良いでしょう。クリックした要素の先祖要素に任意のクラスがないといけないことが分かると思います。今回の場合でいうとaタグの親要素に「wrap」というクラス名があること前提の仕組みだったようです。これで対応すべきことが見えました。先祖要素にそのクラスを付与するか、あるいはこのイベントハンドラの改修をかけるかといったところです。依頼者にその旨報告して完了です。その他少しtipsです。*ブレークポイントの解除ブレークポイントを外すには、マーカーを再度クリックします。ブレークポイントを貼ったり解除したりする動き(gif)↓その他に、右ペインの『Breakoints』にてチェックボックスのon/offで任意のブレークポイントの一時的に無効にできたり、右クリックメニューからブレークポイントの一括削除などもできます。Breakpoints』があります。https://techblog.gmo-ap.jp/2019/07/11/using-chromedevtools-like-pro-tips/#section5例えば、「なんでも良いからページ内で起きたクリックイベントを捕捉したい」場合、『Mouse』>『click』にチェックを入れることでハンドラを捕捉することができます。『Mouse』>『click』にチェックを入れて今回の3つ目のリンクをタップした時の様子(gif)↓この方法でも同様に、今回の3つ目のリンクのハンドラを検出することができます。ケースによってはこちらの方が便利かもしれませんので、試してみてください。(Elements/Network)広告が1つしか出るべきでない場所に、3つ出る(2つ余計に出る)という不具合の相談を受けました。『Elements』パネルを開きます。すると広告タグが3つ展開されてしまいました。この時点で「アドサーバーに広告タグを(誤ってか)3つ入稿しているのではないか」という疑いが出てきます。依頼者にそのことを伝えて、入稿内容の確認を取っても良いかもしれませんが、しかしもう少し確信をもちたいところです。そもそも『Elements』パネルに展開されているのはあくまでJSなどが実行された後のDOMツリーのビューだからです。1つの広告タグがもう一つの広告タグを読み込んで展開、という再帰的な広告呼び出しが起こっている可能性も無くはありません。この場合でいうと、1つ目の広告タグと思しきものが内部で2つめ3つめを呼び出しているケースです。先に立てた「入稿画面で広告タグを3つ入れている」という仮説をどうやって検証するかというと、ここで『Network』タブを使用します。『Network』タブはページ内で起こったリクエスト、レスポンスを確認するのに使われます。f」のショートカットを打ってください。すると左側に検索ペインが表示されます。その検索ペインのinputに検索したい文字列を打つことで、ページ内で起こったリクエストとそのレスポンスのheaderとbody内にマッチするものをリストで出してくれます。https://developers.google.com/web/updates/2018/04/devtools#network-search今回の場合は広告タグの文字列を検索します。『Elements』パネルで見たところ「ad.js」というscriptを読み込むようなので、「ad.js」という文字列で検索します。検索結果にはリクエストURLとレスポンス内容が表示されます。いくつか検索結果に出ていますが、上の3つは中身を見ると広告タグそのもののようなので、最後の「endpoint.json」が怪しそうです。ここにリストされる検索結果はクリッカブルになっていますので、「endpoint.json」のbody部をクリックしましょう。右のペインに内容が展開されます。展開されたら該当文字列を調べます。するとレスポンスにやはり広告タグらしきものが3つ確認できました。アドサーバーから返されているJSONの中に、広告タグが3つ入っていたということなので、やはり3つ入稿されている可能性がかなり高いことが分かりました。依頼者にその旨伝えて確認してもらうようにして完了です。Breakpoints/Breakpoint)後読みコンテンツでJSのscriptが正しく実行されていないという不具合調査依頼がありました。『Elements』パネル上では存在確認できるのですが、実行されていないということです。サンプルページhttps://arasaki-yuki.github.io/techblog/example-breakpoint/調査方法それでは見てみます。インフィニティスクロールであれば、「あるところまでスクロールしたらコンテンツが追加される」仕様ではないかと考えます。確認のため一旦『Elements』パネルを開きながらスクロールして、動きを見てみます。見たところやはりある地点で、特定の要素に子要素が追加されていました。何かがインビュー(または〇px手前まで来たら)されたタイミングで起こっているようです。その追加しているscriptの処理内容を調べれば原因が分かりそうです。処理を行っているJSのscriptがどこかに存在するはずなので探します。Breakpoints』を使います。modification』を選択します。選択するとDOMノードの左に青い丸のマーカーが付きます。マーカーがあることを確認出来たら改めてリロードしてスクロールします。すると突然ブレークポイントを置いた時と同じように、UI画面がグレーアウトします。modification』が起きたため)、scriptの実行が一時停止したのです。modification』を設定し、その上でリロード、スクロールして、ブレークした様子(gif)↓そしてパネル側を見ると、『Sources』パネルに子要素を追加するハンドラが展開されています。見たところ、innerHTMLで子要素を入れていることが分かりました。代入しているのはHTMLタグの文字列で、その中に今回依頼者のいうscriptタグが入っていることが分かりました。マウスオーバーすると中身全体が表示されます。入っている文字列を見る限り問題なさそうです。『Elements』パネルにもこの文字列同様にscriptタグがDOMノードとして存在するのは最初の通りです。scriptタグが実行されないかという話ですが、調べたところHTML5の仕様上innerHTMLでscriptタグは実行できないことがわかりました。execute.こうなるとscriptタグだけinnerHTMLでなく、createElement(‘script’)などで実装を変えるなど、仕様変更が必要です。状況が分かったのでその旨依頼者に報告します。—-以上がほんの3例でしたが、実際の活用例でした。今回紹介したやり方はあくまで1つの方法です。DevToolsは触れるほど理解が深まると思いますので、みなさんそれぞれで効率的な方法を見つけていただければと思います。紹介したい強力な機能もあるのですが、それはまたどこかのタイミングでできればとは思います。おまけ(Breakpoint/Console)ブレークポイントと『Console』をうまく使うことでより手軽にデバッグができます。サンプルページhttps://arasaki-yuki.github.io/techblog/example-breakpoint_tip/上記画像は、とある即時関数内でブレークポイントを貼り、一時停止した様子です。ブレーク中に右ペインの『Scope』を見ると、ローカル/グローバル変数の値を確認することができます。『Scope』以外に、『Console』でそのローカル/グローバル変数を打っても、同様に同じ値が返ってきます。(上の画像参照)この時点でお気づきになる方もいるかと思いますが、ブレークポイントと『Console』を組み合わせて使えば、グローバル/ローカル変数の値を参照だけでなく、それらの上書きも可能となります。今回のサンプルページで見てみます。breakpoint.jsを読み込んでおり、その中で1/100の確率で、あるクリエイティブを出すというロジックが実装されています。99)」という条件を設定し、ブロック内にクリエイティブを出す処理を入れることで、実現しているようです。頑張ってリロードをし続ければ、1/100の確率でいつかクリエイティブを見ることができますが、ただ手っ取り早くこのクリエイティブを見ないといけないなどの場合(=if文を通したいと思った場合)先のテクニックを使用することで解決できます。if文の行にブレークポイントを貼り、リロードします。その後ステップ実行、あるいは再生アイコンをクリックして処理を流します。することでif文のブロックに処理が通すことができました。上の処理をやった様子(gif)↓なお『Console』以外にも『Sources』内の『Snippets』も同様にJSを実行できます。長くなる場合などはブレークポイントと『Snippets』の組み合わせでやると良いかと思います。長くなりましたが、以上です。DevToolsアカウントなどおすすめです。Devloper』も読むと良いでしょう。https://developers.google.com/web/tools/chrome-devtools/javascript/?hl=jaそして当社サービス「めるも」もどうぞよろしくお願いいたします。https://news.merumo.ne.jp/明日は、KONCEさんによる「エンジニアになってみて、難しいなって思ったコト」です。@gmoap_engineer本ブログで発信される情報は、各エンジニア個人の見解であり、弊社の公式見解ではありません。本ブログに掲載、引用等をしている商品またはサービス等の名称は、各社の商標または登録商標です。その他の事項について一切責任を負いかねます。発表する情報には注意を払っておりますが、公式発表、見解については、弊社WEBサイトおよびプレスリリースなどをご確認ください。GMOインターネットグループにおけるソーシャルメディア運用ポリシーについては次のページをご確認ください。本ブログに掲載のあるソフトウェアのダウンロードは自己責任で御願い致します。ソフトウェアのダウンロードの結果、ご利用者に何らかの損失・損害が生じたといえども、当社ではその責任を負いかねます。本ブログに掲載のあるソフトウェアを扱う際は、各ソフトウェアの公式リファレンスを参照のもとご使用下さい。ソフトウェアの実行の結果、ご利用者に何らかの損失・損害が生じたといえども、当社ではその責任を負いかねます。