Add telemtry

Signed-off-by: Alexandre Bodin <bodin.alex@gmail.com>
This commit is contained in:
Alexandre Bodin 2020-07-03 17:59:06 +02:00
parent 2ff0bfe75e
commit a7d8889a6a
5 changed files with 88 additions and 23 deletions

View File

@ -57,7 +57,6 @@ class Strapi {
this.config = loadConfiguration(this.dir, opts);
this.isLoaded = false;
this.EE = ee({ dir: this.dir, logger });
// internal services.
this.fs = createStrapiFs(this);
this.eventHub = createEventHub();
@ -65,6 +64,10 @@ class Strapi {
this.requireProjectBootstrap();
}
get EE() {
return ee({ dir: this.dir, logger });
}
requireProjectBootstrap() {
const bootstrapPath = path.resolve(this.dir, 'config/functions/bootstrap.js');

View File

@ -10,6 +10,7 @@ const wrapWithRateLimit = require('./rate-limiter');
const createSender = require('./sender');
const createMiddleware = require('./middleware');
const isTruthy = require('./is-truthy');
const ee = require('../../utils/ee');
const LIMITED_EVENTS = [
'didSaveMediaWithAlternativeText',
@ -30,6 +31,26 @@ const createTelemetryInstance = strapi => {
strapi.app.use(createMiddleware({ sendEvent }));
}
if (strapi.EE === true && ee.isEE === true) {
const pingDisabled =
isTruthy(process.env.STRAPI_LICENSE_PING_DISABLED) && ee.licenseInfo.type === 'enterprise';
const sendLicenseCheck = () => {
return sendEvent(
'didCheckLicense',
{ licenseInfo: ee.licenseInfo },
{
headers: { 'x-strapi-project': 'enterprise' },
}
);
};
if (!pingDisabled) {
scheduleJob('0 0 0 * * 7', () => sendLicenseCheck());
sendLicenseCheck();
}
}
return {
async send(event, payload) {
if (isDisabled) return true;

View File

@ -7,9 +7,9 @@ module.exports = (sender, { limitedEvents = [] } = {}) => {
let currentDay = new Date().getDate();
const eventCache = new Map();
return async (event, payload) => {
return async (event, ...args) => {
if (!limitedEvents.includes(event)) {
return sender(event, payload);
return sender(event, ...args);
}
if (new Date().getDate() !== currentDay) {
@ -22,6 +22,6 @@ module.exports = (sender, { limitedEvents = [] } = {}) => {
}
eventCache.set(event, true);
return sender(event, payload);
return sender(event, ...args);
};
};

View File

@ -1,12 +1,19 @@
'use strict';
const os = require('os');
const _ = require('lodash');
const isDocker = require('is-docker');
const { machineIdSync } = require('node-machine-id');
const fetch = require('node-fetch');
const ciEnv = require('ci-info');
const defaultQueryOpts = {
timeout: 1000,
headers: { 'Content-Type': 'application/json' },
};
const ANALYTICS_URI = 'http://localhost:1338'; // https://analytics.strapi.io
/**
* Create a send function for event with all the necessary metadatas
* @param {Object} strapi strapi app
@ -28,23 +35,23 @@ module.exports = strapi => {
strapiVersion: strapi.config.info.strapi,
};
return async (event, payload = {}) => {
try {
const res = await fetch('https://analytics.strapi.io/track', {
method: 'POST',
body: JSON.stringify({
event,
uuid,
deviceId,
properties: {
...payload,
...anonymous_metadata,
},
}),
timeout: 1000,
headers: { 'Content-Type': 'application/json' },
});
return async (event, payload = {}, opts = {}) => {
const reqParams = {
method: 'POST',
body: JSON.stringify({
event,
uuid,
deviceId,
properties: {
...payload,
...anonymous_metadata,
},
}),
..._.merge({}, defaultQueryOpts, opts),
};
try {
const res = await fetch(`${ANALYTICS_URI}/track`, reqParams);
return res.ok;
} catch (err) {
return false;

View File

@ -14,13 +14,19 @@ const noLog = {
info: noop,
};
const internals = {};
module.exports = ({ dir, logger = noLog }) => {
if (_.has(internals, 'isEE')) return internals.isEE;
const warnAndReturn = (msg = 'Invalid license. Starting in CE.') => {
logger.warn(msg);
internals.isEE = false;
return false;
};
if (process.env.STRAPI_DISABLE_EE === 'true') {
internals.isEE = false;
return false;
}
@ -34,6 +40,7 @@ module.exports = ({ dir, logger = noLog }) => {
}
if (_.isNil(license)) {
internals.isEE = false;
return false;
}
@ -51,14 +58,41 @@ module.exports = ({ dir, logger = noLog }) => {
const isValid = verifier.verify(publicKey, signature);
if (!isValid) return warnAndReturn();
const licenseInfo = JSON.parse(content);
internals.licenseInfo = JSON.parse(content);
if (licenseInfo.expireAt < new Date().getTime()) {
if (internals.licenseInfo.expireAt < new Date().getTime()) {
return warnAndReturn('License expired');
}
} catch (err) {
return warnAndReturn();
}
internals.isEE = true;
return true;
};
Object.defineProperty(module.exports, 'licenseInfo', {
get: () => {
mustHaveKey('licenseInfo');
return internals.licenseInfo;
},
configurable: false,
enumerable: false,
});
Object.defineProperty(module.exports, 'isEE', {
get: () => {
mustHaveKey('isEE');
return internals.isEE;
},
configurable: false,
enumerable: false,
});
const mustHaveKey = key => {
if (!_.has(internals, key)) {
const err = new Error('Tampering with license');
err.stack = null;
throw err;
}
};