summaryrefslogtreecommitdiffstats
path: root/assets/js/ga.js
blob: 4f2ae0a376c4117ed8f8b32e8d070f2465f81156 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
import {analyticsCode, anonymizeIp} from '@params';

let dataLayer;

function isDoNotTrackEnabled() {
  if (typeof window === 'undefined') {
    return false;
  }
  const {doNotTrack, navigator} = window;

  // Do Not Track Settings across browsers
  const dnt = (doNotTrack || navigator.doNotTrack || navigator.msDoNotTrack);

  if (!dnt) {
    return false;
  }

  return dnt === true ||
    dnt === 1 ||
    dnt === 'yes' ||
    (typeof dnt === 'string' && dnt.charAt(0) === '1');
}

function gtag() {
  dataLayer.push(arguments);
}

/**
 * Function that tracks a click on an outbound link in Analytics.
 *
 * This function takes a valid URL string as an argument, optional
 * 'isBlank' argument, and uses that URL string as the event label.
 *
 * Setting the transport method to 'beacon' lets the hit be sent using
 * navigator.sendBeacon() in browser that support it. The navigator.sendBeacon()
 * method asynchronously sends an HTTP POST request containing a small amount of
 * data to a web server.
 */
function trackOutboundLink(url, isBlank = false) {
  gtag('event', 'click', {
    'event_label': url,
    'event_category': 'outbound',
    'transport_type': 'beacon',
    'event_callback': () => {
      if (!isBlank) {
        document.location = url;
      }
    }
  });
}

function trackInternalEvent(label, category) {
  gtag('event', 'click', {
    'event_label': label,
    'event_category': category
  });
}

function onClickCallback(event) {
  const element = event.target;
  const className = element.getAttribute('class');

  // Track menu show
  if (className === 'sidebar-toggle') {
    trackInternalEvent('Sidebar Toggle', 'navigation');
  }

  // Track feeds click
  if (className === 'menu-feeds-item') {
    const feedType = element.dataset.feedType;
    trackInternalEvent(`Get ${feedType}`, 'feed');
    return;
  }

  // Track only external URLs.
  if ((element.tagName !== 'A') || (element.host === window.location.host)) {
    return;
  }

  // Track outbound link click
  trackOutboundLink(
    event.target,
    event.target.getAttribute('target') !== '_blank'
  );
}

if (isDoNotTrackEnabled()) {
  // Skip analytics for users with Do Not Track enabled
  console.info('[TRACKING]: Respecting DNT with respect to analytics...'); // eslint-disable-line no-console
} else {
  // Known DNT values not set, so we will assume it's off.
  if (analyticsCode) {
    (function () {
      // New Google Site Tag (gtag.js) tagging/analytics framework
      // See: https://developers.google.com/gtagjs
      const baseUrl = 'https://www.googletagmanager.com';
      const params = new URLSearchParams({
        id: analyticsCode
      });

      let script = document.createElement('script');
      script.src = baseUrl + '/gtag/js?' + params.toString();
      script.type = 'text/javascript';
      script.async = true;

      document.getElementsByTagName('head')[0].appendChild(script);
    }());

    dataLayer = window.dataLayer = window.dataLayer || [];
    gtag('js', new Date());

    const month = 30 * 24 * 60 * 60; // 30 days, in seconds

    // Setup the project analytics code and send a pageview
    gtag('config', analyticsCode, {
      'anonymize_ip': anonymizeIp,
      'cookie_expires': month
    });

    gtag('set', {
      'cookie_flags': 'SameSite=None;Secure'
    });

    // Outbound link tracking.
    document.addEventListener('click', onClickCallback, false);
  }
}