Igor Minar 41dfaf393b build(analytics): track bundle size
This will send bundle sizes (before and after gzip) to Google Analytics so that we can
track bundle size over time for every bundle we produce.

Closes 
2015-11-16 21:42:50 +00:00

177 lines
4.5 KiB
JavaScript

'use strict';
let execSync = require('child_process').execSync;
let fs = require('fs');
let minimist;
try {
minimist = require('minimist');
} catch (e) {
minimist = function(){ return {projects: ""}; };
}
let path = require('path');
let os = require('os');
let ua;
try {
ua = require('universal-analytics');
} catch(e) {
// ignore errors due to invoking analytics before the first npm install
}
const analyticsFile = path.resolve(path.join(__dirname, '..', '..', '.build-analytics'));
const analyticsId = "UA-8594346-17"; // Owned by the Angular account
const analyticsOptions = {
https: true,
debug: false
};
let cid = fs.existsSync(analyticsFile) ? fs.readFileSync(analyticsFile, 'utf-8') : null;
let visitor;
if (ua) {
if (cid) {
visitor = ua(analyticsId, cid, analyticsOptions);
} else {
visitor = ua(analyticsId, analyticsOptions);
cid = visitor.cid;
fs.writeFileSync(analyticsFile, cid, 'utf-8');
}
}
// https://developers.google.com/analytics/devguides/collection/protocol/v1/parameters
let customParams = {
// OS Platform (darwin, win32, linux)
cd1: os.platform(),
// Node.js Version (v4.1.2)
cd2: process.version,
// npm Version (2.14.7)
cd10: getNpmVersion(),
// TypeScript Version (1.6.2)
cd3: getTypeScriptVersion(),
// Dart Version
cd11: getDartVersion(),
// Dev Environment
cd4: process.env.TRAVIS ? 'Travis CI' : 'Local Dev',
// Travis - Pull Request?
cd5: process.env.TRAVIS && process.env.TRAVIS_PULL_REQUEST ? 'true' : 'false',
// Travis - Branch Name (master)
cd6: process.env.TRAVIS_BRANCH,
// Travis - Repo Slug (angular/angular)
cd7: process.env.TRAVIS_REPO_SLUG,
// Travis - Job ID (4.1)
cd12: process.env.TRAVIS_JOB_NUMBER,
// HW - CPU Info
cd8: `${os.cpus().length} x ${os.cpus()[0].model}`,
// HW - Memory Info
cd9: `${Math.round(os.totalmem()/1024/1024/1024)}GB`,
// gulp --projects (angular2,angular2_material)
cd13: minimist(process.argv.slice(2)).projects
};
function getTypeScriptVersion() {
try {
return require('typescript').version;
} catch (e) {
return 'unknown';
}
}
function getNpmVersion() {
try {
return execSync('npm -v').toString().replace(/\s/, '');
} catch (e) {
return 'unknown';
}
}
function getDartVersion() {
try {
return execSync('dart --version 2>&1').toString().replace(/.+: (\S+) [\s\S]+/, '$1')
} catch (e) {
return 'unknown';
}
}
function recordEvent(eventType, actionCategory, actionName, duration, label) {
// if universal-analytics is not yet installed, don't bother doing anything (e.g. when tracking initial npm install)
// build-analytics will however store the starting timestamp, so at least we can record the success/error event with duration
if (!ua) return;
if (duration) {
duration = Math.round(duration);
}
switch (eventType) {
case 'start':
visitor.
event(actionCategory, actionName + ' (start)', label, null, customParams).
send();
break;
case 'success':
visitor.
event(actionCategory, actionName, label, duration, customParams).
timing(actionCategory, actionName, duration, label, customParams).
send();
break;
case 'error':
visitor.
event(actionCategory, actionName + ' (errored)', label, duration, customParams).
timing(actionCategory, actionName, duration, label, customParams).
send();
break;
default:
throw new Error(`unknown event type "${eventType}"`);
}
}
module.exports = {
installStart: (actionName) => {
recordEvent('start', 'install', actionName);
},
installSuccess: (actionName, duration) => {
recordEvent('success', 'install', actionName, duration);
},
installError: (actionName, duration) => {
recordEvent('error', 'install', actionName, duration);
},
buildStart: (actionName) => {
recordEvent('start', 'build', actionName);
},
buildSuccess: (actionName, duration) => {
recordEvent('success', 'build', actionName, duration);
},
buildError: (actionName, duration) => {
recordEvent('error', 'build', actionName, duration);
},
ciStart: (actionName) => {
recordEvent('start', 'ci', actionName);
},
ciSuccess: (actionName, duration) => {
recordEvent('success', 'ci', actionName, duration);
},
ciError: (actionName, duration) => {
recordEvent('success', 'ci', actionName, duration);
},
bundleSize: (filePath, sizeInBytes, compressionLevel) => {
recordEvent('success', 'payload', compressionLevel, sizeInBytes, filePath);
}
};