/simple-tracker

Easy client-side tracking library to log events, metrics, errors, and messages

Primary LanguageJavaScriptMIT LicenseMIT

Simple Tracker

NPM version Build Status codecov gzip size dependencies License

Easy client-side tracking library to log events, metrics, errors, and messages. Send data to any server endpoint for log management and event tracking services like Google Analytics, Splunk, ELK/Logstash, Loggly, Open Web Analytics, etc...

You can make use of Simple Tracker one of two ways. You can install through npm and use it as a module, or you can include the uglified script file in your HTML page.

Inspiration

If you run an adblocker or a trackerblocker plugin in your browser, page requests to google analytics and other well known tracking libraries get blocked causing you to lose valuable metrics/logs from your websites. To circumvent these blockers, you'd have to write some javascript on your pages to send tracking data to an endpoint that won't be blocked and configure a server or cloud function to proxy this data to a service of your choice. Simple Tracker is the first piece to that solution. It's a light-weight client library that makes sending tracking data simple.

If you're looking to connect your tracking data sent from Simple Tracker to a cloud function, check out these example AWS Lambda functions which proxies the data to a free log management service called Loggly.

Installation through NPM as module

In command line, run:

npm install simple-tracker

In code:

import tracker from 'simple-tracker' // or const tracker = require('simple-tracker')

// initialize tracker endpoint and settings
tracker.push({
  endpoint: '/endpoint', // Endpoint to send tracking data to
  attachClientContext: true, // Attach various client context, such as useragent, platform, and page url
});

You only need to initialize endpoint and settings as above once. After initializing, simply import tracker in other modules or components:

import tracker from 'simple-tracker' // or const tracker = require('simple-tracker')

tracker.push({ event: 'pageview' })

Here is a live example page: https://codeniko.github.io/simple-tracker/examples/all-functions.html

Installation in HTML

Place the following on your page. While you can use the script at the CDN link below, I recommend you to download the script and host it yourself.

<script type="text/javascript" src="https://unpkg.com/simple-tracker@latest/dist/simple-tracker.min.js"></script>
<script>
  // initialize tracker endpoint and settings
  tracker.push({
    endpoint: '/endpoint', // Endpoint to send tracking data to
    attachClientContext: true, // Attach various client context, such as useragent, platform, and page url
  });
</script>

Here is a live example page: https://codeniko.github.io/simple-tracker/examples/all-functions.html

Quick Usage

Logging text:

tracker.push('some text to track');

Logging JSON:

tracker.push({
  message: 'my tracking string',
  values: [1, 2, 3, 'a', 'b', 'c']
});

This will send a POST request containing a sessionId, and client context if enabled (enabled by default). An example request payload:

{
  "sessionId": "11bf5b37-e0b8-42e0-8dcf-dc8c4aefc000",
  "message": "my tracking string",
  "values": [1, 2, 3, "a", "b", "c"],
  "context": {
    "url": "https://nfeld.com/",
    "userAgent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_12_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/65.0.3325.181 Safari/537.36",
    "platform": "MacIntel"
  }
}

There are also several convenience functions defined to push common tracking data such as tracker.logEvent(event), tracker.logMessage('message'), and tracker.logMetric('metric', 'value'). You can find examples of these and more below.

Session Id

Simple Tracker makes use of cookies to persist the sessionId that accompanies all tracking data. If the sessionId is not explicitly set in configuration, one will be generated as a UUIDv4 string. Regardless if explicitly set or generated, the sessionId will be stored in a cookie named trcksesh and will be destroyed when session ends (browser closes)

All configurations

tracker.push({
  endpoint: '/endpoint', // Endpoint to send tracking data to
  sessionId: 'SESSION_ID', // Explicitly set a session id
  sendCaughtExceptions: true/false, // Send exceptions caught by browser. DEFAULT: false
  attachClientContext: true/false, // Attach client context to requests. Includes: useragent, platform, and page url. DEFAULT: true
  attachSessionId: true/false, // Attach sessionId to requests. DEFAULT: true
  devMode: true/false // Toggle dev mode. If enabled, outgoing requests are blocked and logged for debugging instead. DEFAULT: false
});

Adding to client context object

You can add your own values to persist inside of the client context object, or even overwrite the object entirely. You can access the object with tracker.clientContext. Any values you add to the clientContext object will go out on every tracking request

// assign more values
tracker.clientContext.username = 'codeniko',
tracker.clientContext.location = 'San Francisco, CA'

// overwriting context entirely
tracker.clientContext = {
  username = 'codeniko',
  location = 'San Francisco, CA'
}

Tracker functions

Here is a live example page showing all of the convenience functions:
https://codeniko.github.io/simple-tracker/examples/all-functions.html

logEvent(event, additionalParams): Log an event that occurred, with optional additionalParams

tracker.logEvent('contact_form_submitted', { name: 'niko', fromEmail: 'niko@nfeld.com' });

// Request: POST /endpoint
{
  "type": "event",
  "event": "contact_form_submitted",
  "sessionId": "11bf5b37-e0b8-42e0-8dcf-dc8c4aefc000",
  "name": "niko",
  "fromEmail": "niko@nfeld.com"
}

logMessage(message, optionalLevel): Log simple message, with optional level as second argument

tracker.logMessage('some message', 'info');

// Request: POST /endpoint
{
  "type": "message",
  "message": "some message",
  "level": "info",
  "sessionId": "11bf5b37-e0b8-42e0-8dcf-dc8c4aefc000"
}

logException(exceptionObject): Log exceptional error. Can pass an exception object, or other value

tracker.logException(new Error('some exception').stack);

// Request: POST /endpoint
{
  "type": "exception",
  "level": "error",
  "exception": "Error: some exception at <anonymous>:1:1",
  "sessionId": "11bf5b37-e0b8-42e0-8dcf-dc8c4aefc000"
}

logMetric(metricKey, metricValue): Log a metric and its value

tracker.logMetric('page_load_time', 254);

// Request: POST /endpoint
{
  "type": "metric",
  "metric": "page_load_time",
  "value": 254,
  "sessionId": "11bf5b37-e0b8-42e0-8dcf-dc8c4aefc000"
}

Start/stop a timer to record a metric
startTimer(metricKey): Start a timer named by metricKey
stopTimer(metricKey, metricValue): Stop timer named metricKey and log result in millis as metric value

tracker.startTimer('page_load_time');
// wait 1 second
tracker.stopTimer('page_load_time');

// Request: POST /endpoint
{
  "type": "metric",
  "metric": "page_load_time",
  "value": 1000,
  "sessionId": "11bf5b37-e0b8-42e0-8dcf-dc8c4aefc000"
}

push(dataObject): Push any data of your choice

tracker.push({
  message: 'my tracking string',
  values: [1, 2, 3, 'a', 'b', 'c'],
  userMap: {
    codeniko: 1234,
    chance: 8888
  }
});

// Request: POST /endpoint
{
  "message": "my tracking string",
  "values": [1, 2, 3, "a", "b", "c"],
  "userMap": {
    "codeniko": 1234,
    "chance": 8888
  },
  "sessionId": "11bf5b37-e0b8-42e0-8dcf-dc8c4aefc000"
}

Examples out in production

You can find Simple Tracker used on the following websites. For some fun, ensure your adblocker is enabled, open up devtool console, refresh/navigate the pages and observe network requests to /ga for google analytics pageviews and /track for log messages.
https://jessicalchang.com
https://nfeld.com

Bugs, feature requests, & contributing

If you found a bug or want to request a feature, create a new issue. Contributions via pull requests are more than welcome :)

Running unit tests and code coverage

npm test