
GA4計測用にGTMのトリガーを設定したのに、タグが発火しない。多くの場合、原因は設定ミスではなく、トリガーの条件にしているURLの変化が、実際には起きていないことにあります。サーバー側のログに記録は残っていても、ブラウザの画面自体は遷移していないケースも少なくありません。実際のURLを確認する方法や、画面が遷移しないサイトでの計測の組み方、GTM Previewだけに頼らない確認方法を実例つきで解説します。
※本記事内のGTM・DevToolsの画面名称・操作手順は2026年9月時点のものです。仕様が変更されることがあるため、実際の操作時は最新の画面もあわせてご確認ください。
GA4で、ボタンのクリックやフォームの送信といったユーザーの行動を確認するために、GTMでイベント計測を実装する場面は多くあります。ただ、条件を正しく設定したつもりでも、タグが発火しないことがあります。
多くの場合、トリガーの構文や条件の書き方そのものは間違っていません。原因は、その条件が前提としている「URLの変化」自体が、実際には起きていないことにあります。今回は、社内のアクセスログや行動ログを手がかりにGTMのトリガーを組む際に、押さえておきたいポイントを整理します。
トリガーやタグを組む前に、必ずやっておきたいのが、対象の要素をDevToolsの「Elements」タブで確認することです。
見た目は同じ「ボタン」でも、裏側の作り方は一様ではありません。実際のHTMLを見てみると、本来リンクを作るための<a>タグや、ボタンを作るための<button>タグではなく、それ自体には意味を持たない、単なる箱・囲みのための要素である<div>や<span>に対して、JavaScriptで「クリックされたら処理を実行する」という仕組みだけを、後付けで仕込んでいるケースがよくあります。
GTMには、クリックを検知するためのトリガーが用意されており、GTMの管理画面上では「クリック - リンクのみ」「クリック - すべての要素」という名前で選択肢が並んでいます。「クリック」という大分類の中に、細かい種類が2つある、という意味の名前です。「リンクのみ」は文字通り、<a>タグへのクリックしか検知しません。対象が<div>や<span>のような、リンクではない要素であれば、「すべての要素」の方を選ぶ必要があります。
ここで大事なのは、「クリックが起きたこと」を検知するのと、「どの要素が押されたか」を判断するのは、別の話だという点です。「クリック - すべての要素」を使うと、GTMはページ上のどこがクリックされても、とりあえずすべて検知します。しかしこのままでは、問い合わせボタンが押されたのか、カート追加ボタンが押されたのか区別がつきません。そこで、GTMは「今クリックされた要素のリンク先はどこか」「クラス名は何か」といった情報を自動的に調べてくれるので、それを条件にして、目的の要素が押されたときだけタグを発火させる、という絞り込みを行います。
絞り込みに使える情報は、要素の種類によって変わります。<a>タグにはリンク先を示す情報(href)が入っていますが、<div>にはこれがありません。リンクであれば、そのリンク先のURLを手がかりにでき、たとえば問い合わせページのURLが/contactだと分かっていれば、リンク先が/contactのものだけを検知するという条件を組めます。リンクでなければ、代わりにクラス名を手がかりにし、カートに追加するボタンのクラス名にbtn-add-cartが含まれることが分かっていれば、その文字列を含むものだけを検知するという条件になります。
つまり、対象のHTML構造次第で、選ぶべきトリガーの種類も、条件に使える手がかりも変わってくる、ということです。
「クリックできそうに見える」という見た目だけで判断してトリガーを組んでしまうと、後になって「なぜか発火しない」という、今回のテーマそのものにぶつかることになります。対象要素のタグ名・class・属性を確認しておくだけで、その手戻りは防げます。
社内の行動ログやアクセスログに、こういった記録が残っていることがあります。
/log/button-click?action=required-login&target_id=8821...これだけを見ると「このパスに画面が遷移した」ように読めますが、実際にはページを遷移させずに、ユーザーの行動をサーバー側へ軽量に記録するための仕組みであることが少なくありません。
大規模な改修をせずに、既存の画面構成を変えないまま行動ログだけを蓄積したい場合、「パス風の文字列を、バックエンドAPIへのリクエストに載せて送る」という設計は、実装コストを抑えられる現実的な選択肢です。フロントエンドの改修範囲を最小限に留めながら、後からログを分析できるようにする、合理的な方法のひとつといえます。
ただし、この設計を前提に知らずにGTMのトリガーを組んでしまうと、うまく計測できません。たとえばGTMの「履歴の変更(History Change)」というトリガーは、ページ全体を読み込み直さずにURLだけが裏側で書き換わる、いわゆるSPAと呼ばれる作りのサイトで、そのURLの変化を捉えるためのものです。あるいは、サーバーへ新しくリクエストが送られてページ全体が表示し直されたタイミングで発火する、通常の「ページビュー」トリガーを使うこともあります。しかしどちらも、あくまでブラウザの実際のURLが変化した、あるいはページが読み込まれたことを前提にしている仕組みなので、URL自体が変わっていなければ、いつまで待っても発火しません。
この違いに気づくための、最も確実な方法は次の1行です。ブラウザのDevTools(コンソール)で実行します。
javascript
window.location.href該当のアクションを実行した直後に、この値を確認します。もし社内ログにあったパスと、ここで返ってくる値が一致しなければ、そのパスは画面遷移ではなく、サーバーへのAPIリクエストの一部として送られているログ用のパラメータである可能性が高いということです。
実際に、ネットワークタブで該当のリクエストを確認すると、このようなケースの多くは以下のような形になっています。
Request URL: https://api.example.com/userlog/create
Request Method: POSTつまり、「見覚えのあるパス」は、POSTリクエストのボディの中身として送られたログデータであり、ブラウザの画面遷移そのものとは別物だった、ということです。GTMの「履歴の変更」トリガーは、あくまでブラウザの実際のURL変化を監視する仕組みなので、この種のサーバー直送のログは、仕組み上、検知の対象外になります。
「ブラウザの標準的な仕組み(URL変化、クリック、DOM表示)では検知できない」と分かった時点で、GTM側の対応方針は大きく2つに絞られます。
前半で説明した「クリック - すべての要素」トリガーと、リンク先URLやクラス名による絞り込みを、そのままこの用途にも使う方法です。ボタン自体のclassや属性を確認し、条件を組んで捉え直します。画面遷移の有無に関係なく、ボタンが押された事実そのものを検知できるため、既存のログ設計に一切手を加える必要がありません。
ただし注意点もあります。クリックはあくまで「押された」ことしか示さず、その後の処理が成功したかどうかまでは分かりません。また、btn-add-cartのような意味を持つクラス名ではなく、rounded-lg bg-blue-500 px-4 py-2 text-whiteのような、角丸・背景色・余白・文字色といった見た目だけを指定する、装飾目的のクラス名だけで作られたボタンの場合、他の似たデザインの要素と混同しない条件を見つけるのに手間がかかることがあります。
dataLayerとは、サイト側からGTMへ情報を直接渡すための、いわば「受け渡し場所」です。GTMを導入しているサイトであれば、この受け渡し場所自体はすでに存在しています。ただし、それは空の入れ物が用意されているだけで、そこに何が書き込まれるかは別の話です。ボタンが押された、フォームが送信されたといった出来事が起きたタイミングで、開発者がこの場所に情報を書き込んでおいて初めて、GTM側はURLの変化やクリックの検知に頼らずとも、その情報をそのまま受け取れるようになります。今回のように、既に「行動が起きたタイミングでサーバーへログを送る」処理ができあがっているのであれば、そこに dataLayer.push({event: 'xxx'}) という一行を追加してもらうだけで、同じタイミングでGTM側にも情報が届くようになります。大規模な改修は必要なく、GTM側からも正確に検知できるようになります。
依頼する際は、送る値の名前を、行動の種類ごとにきちんと分けてもらうよう伝えておくと安心です。似た行動をまとめて同じ値で送ってしまうと、後から個別に区別できなくなってしまいます。
どちらも、既存の実装方針を尊重したまま計測を成立させる方法です。サーバーログに見えているものを鵜呑みにせず、まずブラウザの実際の挙動を確認するという一手間が、遠回りな試行錯誤を大きく減らしてくれます。
原因を切り分ける過程で、GTMの「Preview(プレビュー)」モードを使う場面も多いはずです。これは、GTMの管理画面から対象のサイトに接続し、実際に操作しながら「どのタグが発火したか」「発火しなかったか」を、リアルタイムで確認できる検証用の機能です。トリガーやタグを作成したあと、公開前の動作確認として使うのが一般的です。
ただし、PreviewはあくまでGTMが検知できた範囲の情報しか表示してくれません。今回のようなサーバー直送のログはもちろん、モーダル表示だけでURLが変わらない操作や、他社ツールが独自に行う通信も、Previewの「配信されたタグ/未配信のタグ」の一覧には一切現れません。
「Previewで何も検知されていない=サイト側で何も起きていない」ではなく、「GTMの標準的な仕組みでは検知できない種類の処理が動いている」可能性がある、という前提を持っておくと安心です。判断に迷ったときは、Previewだけで完結させず、DevToolsのNetworkタブもあわせて確認する習慣をつけておきましょう。
加えて、Previewは接続のタイミング次第で、操作が記録されないことも珍しくありません。接続直後にまだセッションが確立しきっていない状態で操作してしまい、その分の記録が抜け落ちる、というケースが典型的です。検証するときは、複数の操作をまとめて行うのではなく、1つ操作するたびに、その結果がタグの一覧に反映されているかを確認してから次に進む、という進め方をおすすめします。結果が想定と違うときも、「設定が間違っている」と決めつける前に、一度Previewを接続し直して、同じ操作を再現できるか確かめると、無駄な調査を防げます。
トリガーを組む前に、DevToolsで対象要素の実体(タグ名・class・属性)を確認する。見た目は同じ「ボタン」でも、実装が異なれば適切なトリガーの種類も変わる
社内ログに「URLらしき文字列」があっても、window.location.href で実際のURLと一致するか確認する。一致しなければ、画面遷移ではなくサーバーへの裏側通信である可能性が高い
検知できないと分かったら、クリックイベントで直接捉えるか、既存のログ送信処理にdataLayerへの一行を足してもらう方法を検討する
GTMのPreviewモードも「検知できた範囲」しか表示しないため、Networkタブも併用し、1つずつ操作して結果を確認しながら検証する
GTMやGA4での計測設計は、サイトごとの実装方針を踏まえたうえで、「画面に見えているものが、そのままシステムの動きを表しているとは限らない」という前提を持つことで、精度の高い計測を無理なく実現できます。
この商品について質問がありますか?コミュニティや専門家に質問してください。