Facebook Pixel + Google Tag Manager + fbq events
Asked Answered
L

5

14

I'm using Google Tag Manager to deliver Facebook Pixel.

Then, I fire events using code like this

  <body>
...
        <script>
            fbq('track', 'ViewContent', { 
                content_type: 'product',
                content_ids: ['1234'],
                content_name: 'ABC Leather Sandal',
                content_category: 'Shoes',
                value: 0.50,
                currency: 'USD'
            });
        </script>
    </body>

But when the code is executed I got an error since Facebook Pixel is loaded asynchronously and fbq is not available yet.

Uncaught ReferenceError: fbq is not defined

What should I do?

Lenlena answered 27/10, 2017 at 10:26 Comment(0)
I
21

Couldn't get Eike's approach to work and ended up with the below "dirty workaround" (basically it just waits till the fbq is inited):

<script>
    function waitForFbq(callback){
        if(typeof fbq !== 'undefined'){
            callback()
        } else {
            setTimeout(function () {
                waitForFbq(callback)
            }, 100)
        }
    }

    waitForFbq(function () {
        fbq('track', 'Registered');
    })
</script>

Maybe it will help someone as well

Inactivate answered 5/7, 2019 at 12:48 Comment(1)
The example above works great, however I suggest to also implement a maximum-retry if for what kind of reason fbq isn't loaded at all. ```Colima
C
11

Use the tag sequencing feature. This allows to fire tags in a predefined order, where the subsequent tags wait for the previous ones before they are executed.

Create a tag that loads the FB init code. Select "Once per page" in the tag firing options (you need to load this only once, even if it used by multiple tags).

Go to your Facebook event tag. In the advanced settings look for the tag sequencing options. Set it to:

enter image description here

(where Facebook init is your tag that loads the FB library, I am asumming that you use their standard bootstrap code). With the last checkbox enabled this will not fire if your setup tag has failed.

Since the FB bootstrap code will set up a fbq object with a command queue you can now push data to fbq; even if the library is still downloading the data will enter the command queue and the calls will be executed when the library has been downloaded.

The tag sequence makes sure that the fbq object is set up before your event. If this is your only FB event you can save yourself the trouble and simply paste the loader above your event code.

Cramped answered 27/10, 2017 at 14:0 Comment(3)
Thanks for your detailed answer. I found your answer as I am also getting the 'fbq is not defined' error even when I am already sequencing my tags correctly. I have the Setup-tag set to the Facebook base pixel, but only the INIT part. I fire the PageView event separately that also is using the Base Pixel as its setup-tag. I wonder, does Facebook want the PageView event o have fired before any other event as well or is the INIT part of the pixel enough for all events to work regardless of PageView?Thermopylae
This doesn't really answer the question. Viru us solution actually solves the problem because the OP requires that the event code is on the actual template page (presumably to pull in template variables which GTM cannot do)Synesthesia
The default setup with the Meta Conversions API + Google Tag Manager needs to be modified, for those that use that setup. In the browser container you need to go into the Meta Pixel tag and add that the Meta GA4 tag setup fires before the Meta Pixel tag.Aristippus
P
0

Had the same error - in the end it was all about sequencing.

When used through tag manager on a wordpress site through the WP plugin, the pixel was loaded in the footer by default, so the fbq variable used before being declared in the footer, was not recognised in the body: Google Tag Manager for WordPress options

I tried different settings, and in the end gave up using the plugin - simply inserted it in the header section using the script section of my page builder (Thrive Architect = TA): Custom script setting in TA and it all works fine now!

Pegu answered 15/5, 2019 at 14:43 Comment(0)
R
0

Proper way to handle a problem like this

You need to check if the window reference exists, not if its value is null!

While you can't use:

if (fbq !== undefined) {
  // browser code
}
// or 
if (window.fbq !== undefined) {
  // browser code
}

Because this would try to compare a non-existent variable (window) to undefined, resulting in the mighty "ReferenceError: window is not defined". You can still use:

if (typeof window !== "undefined") {
  // browser code
}

Because typeof won't try to evaluate "window", it will only try to get its type,

Randell answered 16/8, 2021 at 10:52 Comment(1)
Yeah you got rid of the crash, but your analytics won't initialise properly and you'll screw your reports if you follow this approach. In the context of question you are literally just hiding the problem, not solving it. Don't use this code.Inactivate
C
0

As enhancement on the answer of @vir-us. I made a small improvement if for what kind of reason the fbq tag isn't populated at all. Right now the code is retrying for a maximum attempts of 20 times, with the increase of the timeout this means it'll just retry for a total of 10 seconds.

<script>
    function waitForFbq(callback, attempts = 0){
        if(typeof fbq !== 'undefined'){
            callback()
        } else if (attempts < 20) {
            setTimeout(function () {
                waitForFbq(callback, attempts + 1)
            }, 500)
        }
    }

    waitForFbq(function () {
        fbq('track', 'Registered');
    })
</script>
Colima answered 7/8, 2024 at 12:48 Comment(0)

© 2022 - 2025 — McMap. All rights reserved.