Pourquoi mes formulaires HubSpot ne sont-ils pas suivis ?

Les soumissions manquantes reflètent souvent une déconnexion entre HubSpot, GTM/GA4 et vos intégrations. J’explique les causes principales (iframe, triggers, workflows, scripts, consentement, API) et donne un plan d’action opérationnel pour rétablir un tracking fiable.


Besoin d'aide ? Découvrez les solutions de notre agence Google Tag Manager.

Quelles sont les causes principales des soumissions non suivies

Les suivis de soumissions échouent le plus souvent parce que HubSpot, les outils d’analytics et les intégrations tierces ne sont pas alignés, ce qui empêche la propagation des événements vers GTM (Google Tag Manager) et GA4 (Google Analytics 4) et laisse des workflows incomplets.

Voici les causes principales, pourquoi elles bloquent la visibilité, l’impact sur l’attribution/pipeline et les indicateurs de diagnostic.

  • Déploiements variés (HubSpot CMS, site externe, Shopify). Les scripts et hooks ne sont pas identiques selon l’environnement. Cela empêche la collecte uniforme des événements et fausse l’attribution multi-touch. Diagnostic : Formulaires suivis sur HubSpot mais pas sur domaine externe.
  • Iframes et barrières cross-origin. Les iframes bloquent l’accès au parent pour raison de sécurité (même origine). Les événements JavaScript ne remontent pas à GTM/parent, donc pas d’enregistrement. Diagnostic : Pas de dataLayer push depuis l’iframe, erreurs CORS en console.
  • Absence de déclencheur analytics connecté à la soumission. Le formulaire déclenche un envoi côté serveur ou HubSpot sans déclencher dataLayer.push(). Attribution perdue pour les campagnes. Diagnostic : Aucune entrée d’événement « form_submit » dans dataLayer.
  • Workflows HubSpot qui fonctionnent sans événement analytics. Les workflows internes créent ou enrichissent un contact sans événement public (GTM/GA4). Impact : Pipeline interne correct mais reporting analytics neutre. Diagnostic : Contact créé dans HubSpot sans événement associé en GA4.
  • Confirmations inline sans page de remerciement. Pas de nouvelle URL = déclencheur de pageview manquant, donc difficile d’identifier les conversions. Diagnostic : Pas de hit page_view lié à une conversion.
  • GTM mal configuré pour détecter HubSpot. Balises mal filtrées ou sélecteurs DOM incorrects empêchent le firing. Diagnostic : Balises GTM non déclenchées en Preview Mode.
  • GA4 non paramétré pour marquer les événements comme conversions. Événements reçus mais non transformés en conversion, fausse KPI. Diagnostic : Événements visibles dans GA4 mais conversions à 0.
  • Conflits de scripts multiples. Plusieurs bibliothèques qui modifient DOM ou interceptent submit annulent les handlers. Diagnostic : Erreurs JS en console, ordre de chargement incorrect.
  • Contraintes de consentement. Les CMP (Consent Management Platforms) bloquent les cookies/collectes avant opt-in, réduisant l’attribution. Diagnostic : Événements côté client bloqués tant que l’utilisateur refuse.
  • Soumissions via API / formulaires custom. Envois backend qui ne déclenchent pas d’événement frontend. Impact : Contacts créés sans source marketing. Diagnostic : Entrées API dans les logs serveurs sans événement frontend correspondant.

Priorités d’investigation selon le type de site : Pour un site HubSpot, vérifier les workflows et sélecteurs intégrés. Pour un site externe, prioriser GTM, dataLayer et CORS/iframe. Pour un e‑commerce (Shopify), auditer les apps tierces, le checkout et les CMP.

CauseDiagnostic immédiat
Iframe / Cross-originPas de dataLayer push depuis iframe; erreurs CORS en console
Absence de déclencheur analyticsPas d’événement « form_submit » dans dataLayer; balise GTM non déclenchée
API / soumission backendContact créé dans HubSpot sans hit GA4 ni page_view
Consentement bloquantÉvénements client absents tant que CMP n’est pas validée

Comment gérer les iframes et les soumissions API

Je rencontre souvent deux cas quand un formulaire HubSpot n’est pas suivi : il est chargé dans une iframe ou les soumissions passent par une API serveur. Dans les deux situations, l’événement n’arrive pas naturellement dans le contexte client où tourne Google Tag Manager (GTM), donc il faut l’émettre explicitement et vérifier le mapping côté analytics.

1) Formulaires en iframe. Le navigateur isole le contexte JavaScript d’une iframe pour des raisons de sécurité (same-origin policy). Cette isolation empêche GTM sur la page parente de voir les événements internes à l’iframe. La solution consiste à faire communiquer l’iframe et la page parente via window.postMessage et à pousser ensuite dans dataLayer.

// Dans l'iframe (après soumission)
window.parent.postMessage({
  type: 'hsFormSubmit',
  formId: 'FORM_ID',
  data: { email: 'user@example.com' }
}, '*'); // Remplacer '*' par l'origine de la page parente en production
// Dans la page parente
window.addEventListener('message', event => {
  // Vérifier event.origin ici pour sécurité
  if (event.data && event.data.type === 'hsFormSubmit') {
    window.dataLayer = window.dataLayer || [];
    window.dataLayer.push({
      event: 'hubspotFormSubmit',
      formId: event.data.formId,
      hubspotData: event.data.data
    });
  }
});

Bonnes pratiques de sécurité : Toujours vérifier event.origin contre une liste d’origines connues. Éviter l’usage de ‘*’ en production. Ne pas accepter ni exécuter de payloads non attendus.

2) Soumissions via API ou formulaires custom. Un envoi serveur (Forms API ou Contacts API) ne déclenche rien côté client parce que la logique est hors navigateur. Il faut soit déclencher un événement analytics serveur (Measurement Protocol pour Google Analytics 4), soit retourner un indicateur au client pour qu’il pousse dans dataLayer.

// Exemple Node.js (fetch) : POST vers HubSpot puis vers GA4 Measurement Protocol
const hubspotRes = await fetch('https://api.hsforms.com/submissions/v3/integration/submit/PORTAL_ID/FORM_ID', {
  method: 'POST',
  headers: { 'Content-Type': 'application/json' },
  body: JSON.stringify({ fields: [{ name: 'email', value: 'user@example.com' }] })
});

if (hubspotRes.ok) {
  // Envoyer événement à GA4 (client_id récupéré côté client et transmis au serveur)
  await fetch('https://www.google-analytics.com/mp/collect?measurement_id=MEAS_ID&api_secret=API_SECRET', {
    method: 'POST',
    headers: { 'Content-Type': 'application/json' },
    body: JSON.stringify({
      client_id: 'CLIENT_ID', // doit correspondre au cookie _ga pour lier la session
      events: [{ name: 'hubspot_form_submit', params: { form_id: 'FORM_ID', email: 'user@example.com' } }]
    })
  });
}

Mapping et synchronisation. Toujours synchroniser les identifiants : formId pour retrouver la source, contactId pour le profil HubSpot, et clientId (cookie _ga ou gtag client_id) pour relier l’événement à la session analytics. Sans client_id, l’événement serveur est isolé et fausse les taux de conversion.

CasCorrectif immédiat
Formulaire en iframeAjouter postMessage dans l’iframe + listener parent qui pousse dans dataLayer (vérifier event.origin)
Soumission via APIAprès POST HubSpot, émettre event serveur (GA4 Measurement Protocol) ou transmettre client_id pour push dataLayer côté client

Comment aligner HubSpot, GTM et GA4 pour garantir les conversions

Pour garantir que vos soumissions HubSpot remontent comme conversions dans GA4, il faut déclencher un événement structuré à la soumission, le pousser dans la dataLayer, le capter via Google Tag Manager (GTM) puis le créer et le marquer comme conversion dans GA4.

Étape 1 : Nom d’événement et schéma. Définir un nom standardisé, par exemple hubspot_form_submit. Prévoir un schéma de propriétés pour tracer l’origine et dédupliquer : formId, formName, hubspotContactId (identifiant HubSpot), clientId (ID client GA4), campaign (source/utm). Le clientId correspond au cookie _ga et aide à relier session et contact.

Étape 2 : Configuration GTM. Créer un trigger de type « Événement personnalisé » qui écoute event === ‘hubspot_form_submit’. Créer une balise GA4 Event qui envoie event_name = ‘hubspot_form_submit’ et mappe les paramètres vers les variables dataLayer.

// Extrait d'exemple : push côté site
window.dataLayer.push({
  event: 'hubspot_form_submit',
  formId: 'contact-main',
  formName: 'Contact',
  hubspotContactId: '123',
  clientId: 'GA1.2.1111111111.2222222222',
  campaign: 'newsletter-apr'
});
{
  "tagType": "GA4Event",
  "eventName": "hubspot_form_submit",
  "parameters": {
    "form_id": "{{DL - formId}}",
    "form_name": "{{DL - formName}}",
    "hubspot_contact_id": "{{DL - hubspotContactId}}",
    "client_id": "{{DL - clientId}}",
    "campaign": "{{DL - campaign}}"
  },
  "trigger": "Trigger - HubSpot form submit"
}

Étape 3 : Configuration GA4. Dans GA4, aller à Configure > Events, vérifier l’événement reçu via DebugView, puis dans Configure > Conversions créer un nouvel événement nommé exactement hubspot_form_submit pour le marquer comme conversion.

Étape 4 : Tests et validation. Procéder à une checklist QA avant mise en prod :

  • Soumettre le formulaire de test et vérifier la présence de l’objet dans la dataLayer.
  • Contrôler dans DebugView de GA4 que l’événement et ses paramètres sont reçus.
  • Vérifier dans HubSpot que le contact a bien été créé avec hubspotContactId.
  • Vérifier l’absence de doublons en comparant clientId et hubspotContactId.
  • Mesurer la correspondance des conversions sur plusieurs soumissions pour détecter les faux positifs.

Étape 5 : Pourquoi GA4 désormais. Universal Analytics a cessé le traitement standard des données depuis juillet 2023, donc GA4 est la cible prioritaire pour la mesure et le marquage des conversions.

ÉtapeContrôle OK
Nom d’événement et schémaCode front / dataLayerdataLayer contient les champs attendus
Balise GTMGTM – Tags & TriggersDebugView montre l’événement envoyé
Création event GA4GA4 – Configure > EventsEvent visible en DebugView
Marquer conversionGA4 – Configure > ConversionsConversion incrémentée après soumission

Comment résoudre conflits de scripts et problèmes de consentement

Conflits de scripts et règles de consentement sont souvent la cause d’un formulaire HubSpot non suivi; auditer et rationaliser les scripts, puis aligner le CMP (Consent Management Platform) avec votre architecture de tracking règle la plupart des cas.

Audit de scripts. Utiliser Tag Assistant (outil Google) pour voir les balises qui déclenchent, ouvrir l’inspecteur Réseau (DevTools) pour repérer les requêtes vers track.hubspot.com ou endpoints GTM, et parcourir l’onglet Sources pour inventorier les scripts chargés. Identifier les doublons HubSpot/GTM/tiers en cherchant plusieurs conteneurs GTM, multiples inclusions de hbspt.forms ou appels à hubspot.js. Repérer les scripts asynchrones qui créent des conditions de course lorsque le listener (callback de HubSpot) est attaché trop tôt ou trop tard.

Rationalisation. Prioriser le chargement du dataLayer et du container GTM en en-tête, déplacer les scripts non essentiels en bas de page ou en lazy load, et centraliser les pushes d’événements vers le dataLayer au lieu d’appels dispersés. Versionner chaque script (ex: analytics-v1.2.js) et documenter l’ordre de chargement et les dépendances pour éviter regressions.

Consentement et privacy. Le CMP contrôle quelles catégories (Nécessaire, Préférences, Statistiques/Analytics, Marketing) autorisent le déclenchement des tags. Mettre en place une stratégie «consent-first»: bloquer les tags client-side si pas de consentement, mais capturer l’événement côté serveur pour éviter perte de données essentielles. Exemple d’architecture server-side: conteneur GTM Server ou endpoint personnalisé qui reçoit un événement pseudonymisé puis le relaie vers HubSpot/Google. Utiliser IAB TCF et Google Consent Mode pour harmoniser les signaux de consentement.

Tests de conformité. Simuler refus/acceptation dans la bannière, vérifier avec Tag Assistant et l’inspecteur Réseau que les tags bloqués ne s’exécutent pas et que HubSpot conserve son fonctionnement (soumission de formulaire toujours acceptée). Envisager pseudonymisation et minimisation des données pour rester compatible RGPD.

window.dataLayer = window.dataLayer || [];
// Si consentement analytics présent, pousser l'événement
if (window.__tcf && window.__tcf.gdprApplies && window.__tcf.consent.analytics) {
  dataLayer.push({event: 'hsFormSubmitted', formId: 'contact-form'});
} else {
  // Stocker localement pour envoi server-side ultérieur
  localStorage.setItem('pendingHsForm', JSON.stringify({id:'contact-form', ts:Date.now()}));
}
  • Lister tous les scripts et conteneurs (GTM, HubSpot, tiers).
  • Vérifier doublons et points de chargement asynchrones.
  • Placer dataLayer + GTM en priorité et centraliser les events.
  • Configurer CMP avec catégories claires (Analytics, Marketing) et intégrer IAB TCF/Consent Mode.
  • Mettre en place server-side tracking si données critiques sans consentement.
  • Tester en environnement isolé (incognito, Tag Assistant, logs serveur).

Quel plan d’action opérationnel pour corriger le tracking aujourd’hui

Suivre une checklist structurée en diagnostic, correction technique, tests et documentation permet souvent de rétablir le tracking des formulaires HubSpot en 48–72 heures sur la plupart des sites.

Phase 0 — Préparation : Vérifier accès et outils avant d’agir.

  • Accès HubSpot, GTM, GA4, repo git — Responsable: Produit/Analytique — Durée: 30–60 min — Priorité: Haute.
  • Installer outils: Chrome DevTools, Tag Assistant, Postman — Responsable: Dev/Analytics — Durée: 30 min — Priorité: Moyenne.

Phase 1 — Diagnostic rapide : Confirmer où ça casse.

  • Contrôle dataLayer (objet JS contenant les events) — Responsable: Analytics — Durée: 30 min — Priorité: Haute.
  • Vérifier DebugView GA4 (flux temps réel de GA4) — Responsable: Analytics — Durée: 20 min — Priorité: Haute.
  • Vérifier présence du contact dans HubSpot après soumission (API/DB) — Responsable: CRM/Dev — Durée: 30–60 min — Priorité: Haute.

Phase 2 — Corrections prioritaires : Implémentations à faire.

  • Ajouter un push d’event explicite dans dataLayer à la soumission (ex. event: ‘hsFormSubmit’) — Responsable: Dev — Durée: 1–2h — Priorité: Haute.
  • Créer trigger + tag dans GTM pour capter l’event — Responsable: Analytics — Durée: 1h — Priorité: Haute.
  • Paramétrer la conversion GA4 (événement → conversion) — Responsable: Analytics — Durée: 30 min — Priorité: Haute.
  • Sécuriser postMessage (API pour cross-origin) si formulaire en iframe — Responsable: Dev — Durée: 1–2h — Priorité: Haute.
  • Auditer scripts tiers et blocage CMP (CMP = Consent Management Platform) — Responsable: Dev/Privacy — Durée: 2h — Priorité: Haute.

Phase 3 — Tests et QA : Valider tous les scénarios.

  • Scénarios manuels et automatisés (happy path + erreurs) — Responsable: QA — Durée: 4h — Priorité: Haute.
  • Test cross-device / cross-browser — Responsable: QA — Durée: 2–4h — Priorité: Moyenne.
  • Test sans cookies / opt-out CMP pour vérifier le fallback server-side — Responsable: Dev/Analytics — Durée: 1–2h — Priorité: Haute.

Phase 4 — Industrialisation : Surveiller et alerter.

  • Créer dashboards de santé (nombre de soumissions, échecs) — Responsable: Analytics — Durée: 4h — Priorité: Moyenne.
  • Mettre alerting (ex. chute >30%/24h) — Responsable: Analytics/Ops — Durée: 2h — Priorité: Moyenne.

Phase 5 — Documentation et formation : Rendre reproductible.

  • Rédiger runbook et playbook de rétablissement — Responsable: Produit/Analytics — Durée: 3h — Priorité: Moyenne.
  • Session de 30–60 min pour équipes Marketing/Support — Responsable: Produit — Durée: 1h — Priorité: Basse.

Exemple de ticket pour développeur:

// Ticket: Implémenter push dataLayer sur soumission HubSpot
// Contexte: Les formulaires HubSpot n'envoient pas d'event JS, GA4 ne capte rien.
// Objectif: Pusher event 'hsFormSubmit' avec payload {formId, contactEmail, pagePath}
// Tâches:
// 1) Ajouter listener sur l'événement HubSpot 'onFormSubmit' ou interceptor JS.
// 2) window.dataLayer.push({event: 'hsFormSubmit', formId: 'FORM_ID', email: emailVar, pagePath: location.pathname});
// 3) Tester en DebugView GA4 et Tag Assistant.
// Critères d'acceptation: Event visible dans dataLayer et DebugView GA4.

Exemple de ticket pour analytics:

// Ticket: Créer tag GTM + conversion GA4
// Contexte: Event 'hsFormSubmit' poussé dans dataLayer.
// Objectif: Capturer event dans GTM et marquer comme conversion dans GA4.
// Tâches:
// 1) Créer trigger 'HS Form Submit' sur event 'hsFormSubmit'.
// 2) Créer tag GA4 Event mapping des variables (formId, emailHash, pagePath).
// 3) Marquer l'événement en conversion dans GA4.
// Critères d'acceptation: Evénement reçu en DebugView et comptabilisé comme conversion.
ActionResponsableDuréePriorité
Vérifier accès et outilsProduit/Analytics30–60 minHaute
Diagnostic dataLayerAnalytics30 minHaute
DebugView GA4Analytics20 minHaute
Ajouter event pushDev1–2 hHaute
Créer trigger + tag GTMAnalytics1 hHaute
Configurer conversion GA4Analytics30 minHaute
Sécuriser postMessageDev1–2 hHaute
Audit scripts & CMPDev/Privacy2 hHaute
Tests manuels et cross-deviceQA4–6 hHaute
Dashboards & alertingAnalytics4–6 hMoyenne
Documentation & formationProduit/Analytics3–4 hMoyenne

Prêt à rétablir un tracking fiable de vos formulaires HubSpot ?

Les soumissions HubSpot manquantes signalent presque toujours une rupture entre le CRM, l’analytics et les intégrations. En identifiant si le problème vient d’une iframe, d’un trigger manquant, d’un conflit de scripts, du consentement ou d’une intégration API, on peut corriger rapidement : pousser des événements structurés, configurer GTM/GA4 et valider via DebugView. En appliquant la checklist opérationnelle fournie, vous retrouverez la visibilité sur votre pipeline et l’attribution des campagnes — bénéfice direct : décisions marketing et commerciales basées sur des données fiables.

FAQ

  • Pourquoi HubSpot enregistre la soumission mais GA4 ne la voit pas ?
    Si HubSpot reçoit la soumission mais aucun événement n’est poussé vers le dataLayer ou GTM, GA4 ne pourra pas l’enregistrer. Il faut déclencher un événement client (ou server-side) et créer/marquer cet événement comme conversion dans GA4.
  • Les formulaires en iframe empêchent-ils toujours le suivi ?
    Les iframes bloquent par défaut la capture d’interactions côté parent. La solution consiste à utiliser postMessage entre l’iframe et la page parente ou à implémenter un listener dans l’iframe qui pousse un événement vers le dataLayer.
  • Faut-il configurer GTM ou GA4 en premier pour résoudre un tracking manquant ?
    Commencez par GTM : assurez-vous que l’événement est bien poussé dans le dataLayer et capté par un trigger GTM. Ensuite, vérifiez la réception dans GA4 et marquez l’événement comme conversion après tests en DebugView.
  • Le consentement des utilisateurs peut-il empêcher les soumissions d’être suivies ?
    Oui. Un CMP qui bloque les tags analytics empêchera les événements d’être envoyés. Deux options : demander le consentement avant le tracking ou implémenter une capture server-side compatible avec la réglementation.
  • Comment tester rapidement que le suivi est rétabli ?
    Testez une soumission en mode debug : inspectez le dataLayer, vérifiez le trigger GTM, utilisez DebugView GA4 pour voir l’événement en temps réel et confirmez la création/mise à jour du contact dans HubSpot.

 

 

A propos de l’auteur

Franck Scandolera — expert & formateur en tracking avancé server-side, Analytics Engineering, automatisation No/Low Code (n8n) et intégration de l’IA en entreprise. Responsable de l’agence webAnalyste et de l’organisme de formation Formations Analytics. Références : Logis Hôtel, Yelloh Village, BazarChic, Fédération Française de Football, Texdecor. Dispo pour aider les entreprises => contactez moi.

Retour en haut
Le Web Analyste