Skip to content

Commit

Permalink
0.3.0
Browse files Browse the repository at this point in the history
- Analytics mixins for keen io analytics tracking
- Changes to pagination widgets
- Add "about" field to preprint providers model
- Fix text formatting for license text widgets
  • Loading branch information
abought committed Mar 2, 2017
2 parents 2748652 + 78f70c9 commit 8393568
Show file tree
Hide file tree
Showing 184 changed files with 2,134 additions and 275 deletions.
2 changes: 1 addition & 1 deletion addon/components/license-picker/template.hbs
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@
{{/if}}

{{#if (or showText (not toggleText))}}
<pre style='white-space: pre-wrap; border:none; width:100%; text-align:justify; max-height: 300px;'>{{nodeLicenseText}}</pre>
<pre style='white-space: pre-wrap; word-break: normal; border:none; width:100%; text-align:justify; max-height: 300px;'>{{nodeLicenseText}}</pre>
{{/if}}
{{#unless autosave}}
<button class='btn btn-success pull-right' {{action 'save'}}>Save</button>
Expand Down
10 changes: 10 additions & 0 deletions addon/components/osf-paginator/component.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,9 @@ import layout from './template';
* fetchResults=(action 'fetchResults')
* query=query}}
* ```
*
* The osf-paginator will be deprecated. Use pagination-pager instead.
*
* @class osf-paginator
* @param {integer} totalSearchResults Number of total search results to be paginated
* @param {action} fetchResults - action for fetching other pages of results
Expand All @@ -24,6 +27,13 @@ import layout from './template';
export default Ember.Component.extend({
layout,
currentPage: 1,
init() {
this._super(...arguments);
Ember.deprecate('osf-paginator will be deprecated. Use pagination-pager instead', false, {
id: 'osf-paginator',
until: '1.0.0'
});
},
pages: Ember.computed('totalSearchResults', function() {
let totalSearchResults = this.get('totalSearchResults');
return Math.ceil(totalSearchResults / 10);
Expand Down
11 changes: 11 additions & 0 deletions addon/components/pagination-control/component.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,9 @@ import layout from './template';

/**
* Display a simple pagination control that advances the page. Intended for use with PaginatedRouteMixin.
*
* The pagination-control will be deprecated. Use pagination-pager instead.
*
* @class pagination-control
*/
export default Ember.Component.extend({
Expand All @@ -21,6 +24,14 @@ export default Ember.Component.extend({
return this.get('currentPage') >= this.get('pageCount');
}),

init() {
this._super(...arguments);
Ember.deprecate('pagination-control will be deprecated. Use pagination-pager instead', false, {
id: 'pagination-control',
until: '1.0.0'
});
},

// TODO: This actions hash feels a bit kludgy
actions: {
next() {
Expand Down
298 changes: 298 additions & 0 deletions addon/metrics-adapters/keen.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,298 @@
import Ember from 'ember';
import md5 from 'npm:js-md5';
import _get from 'npm:lodash/get';
import Cookie from 'npm:js-cookie';
import config from 'ember-get-config';
import keenTracking from 'npm:keen-tracking';
import BaseAdapter from 'ember-metrics/metrics-adapters/base';

export default BaseAdapter.extend({
session: Ember.inject.service(),

toStringExtension() {
return 'Keen';
},

init() {},

trackEvent(properties, node) {
window.contextVars = {};
window.contextVars.currentUser = this.userContextVars();
window.contextVars.node = this.nodeContextVars(node);
return this.KeenTracker().getInstance().trackPrivateEvent('front-end-events', { interaction: properties }, node);
},

trackPage(properties) {
window.contextVars = {};
window.contextVars.currentUser = this.userContextVars();
return this.KeenTracker().getInstance().trackPageView({ pageViewed: properties });
},

// Use when tracking something specific, not a generic front-end-event. Usually for something we want
// to isolate and later display to the user.
trackSpecificCollection(trackingInfo) {
// Tracking info should be structured like this:
// {collection: 'keen-collection-name', eventData: eventData, node: node }
const collection = trackingInfo.collection || 'front-end-events';
const properties = trackingInfo.eventData || {};
const node = trackingInfo.node || null;
window.contextVars = {};
window.contextVars.currentUser = this.userContextVars();
window.contextVars.node = this.nodeContextVars(node);
return this.KeenTracker().getInstance().trackPrivateEvent(collection, properties, node);
},

willDestroy() {},

// Adapted from osf.io/website/static/js/keen.js
KeenTracker() {
function _nowUTC() {
var now = new Date();
return new Date(
now.getUTCFullYear(), now.getUTCMonth(), now.getUTCDate(),
now.getUTCHours(), now.getUTCMinutes(), now.getUTCSeconds()
);
}

function _createOrUpdateKeenSession() {
var expDate = new Date();
var expiresInMinutes = 25;
expDate.setTime(expDate.getTime() + (expiresInMinutes * 60 * 1000));
var currentSessionId = Cookie.get('keenSessionId') || keenTracking.helpers.getUniqueId();
Cookie.set('keenSessionId', currentSessionId, {
expires: expDate, path: '/'
});
}

function _getOrCreateKeenId() {
if (!Cookie.get('keenUserId')) {
Cookie.set('keenUserId', keenTracking.helpers.getUniqueId(), {
expires: 365, path: '/'
});
}
return Cookie.get('keenUserId');
}

function _defaultKeenPayload() {
_createOrUpdateKeenSession();

var user = window.contextVars.currentUser;
var node = window.contextVars.node;
var pageMeta = _get(window, 'contextVars.analyticsMeta.pageMeta', {}); // Do not have this information.
return {
page: {
title: document.title,
url: document.URL,
meta: pageMeta,
info: {},
},
referrer: {
url: document.referrer,
info: {},
},
time: {
local: keenTracking.helpers.getDatetimeIndex(),
utc: keenTracking.helpers.getDatetimeIndex(_nowUTC()),
},
node: {
id: _get(node, 'id'),
title: _get(node, 'title'),
type: _get(node, 'category'),
tags: _get(node, 'tags'),
},
anon: {
id: md5(Cookie.get('keenSessionId')),
continent: user.anon.continent,
country: user.anon.country,
},
meta: {
epoch: 1, // version of pageview event schema
},
keen: {
addons: [
{
name: 'keen:url_parser',
input: {
url: 'page.url',
},
output: 'page.info',
},
{
name: 'keen:url_parser',
input: {
url: 'referrer.url',
},
output: 'referrer.info',
},
{
name: 'keen:referrer_parser',
input: {
referrer_url: 'referrer.url',
page_url: 'page.url',
},
output: 'referrer.info',
},
]
},
};
} // end _defaultKeenPayload

function _trackCustomEvent(client, collection, eventData) {
if (client === null) {
return;
}
client.recordEvent(collection, eventData);
}

function _trackCustomEvents(client, events) {
if (client === null) {
return;
}
client.recordEvents(events);
}

function KeenTracker() {
if (instance) {
throw new Error('Cannot instantiate another KeenTracker instance.');
} else {
var _this = this;

_this._publicClient = null;
_this._privateClient = null;

_this.init = function _initKeentracker(params) {
var _this = this;

if (params === undefined) {
return _this;
}

_this._publicClient = keenTracking({
projectId: params.public.projectId,
writeKey: params.public.writeKey,
});
_this._publicClient.extendEvents(_defaultPublicKeenPayload);

_this._privateClient = keenTracking({
projectId: params.private.projectId,
writeKey: params.private.writeKey,
});
_this._privateClient.extendEvents(_defaultPrivateKeenPayload);

return _this;
};

var _defaultPublicKeenPayload = function() { return _defaultKeenPayload(); };
var _defaultPrivateKeenPayload = function() {
var payload = _defaultKeenPayload();
var user = window.contextVars.currentUser;
payload.visitor = {
id: _getOrCreateKeenId(),
session: Cookie.get('keenSessionId'),
returning: Boolean(Cookie.get('keenUserId')),
};
payload.tech = {
browser: keenTracking.helpers.getBrowserProfile(),
ua: '${keen.user_agent}',
ip: '${keen.ip}',
info: {},
};
payload.user = {
id: user.id,
entry_point: user.entryPoint,
institutions: user.institutions,
locale: user.locale,
timezone: user.timezone,
};
payload.keen.addons.push({
name: 'keen:ip_to_geo',
input: {
ip: 'tech.ip',
},
output: 'geo',
});
payload.keen.addons.push({
name: 'keen:ua_parser',
input: {
ua_string: 'tech.ua'
},
output: 'tech.info',
});

return payload;
};

_this.trackPageView = function (data) {
var _this = this;
if (_get(window, 'contextVars.node.isPublic', false) &&
_get(window, 'contextVars.analyticsMeta.pageMeta.public', false)) {
_this.trackPublicEvent('pageviews', data);
}
_this.trackPrivateEvent('pageviews', data);
};

_this.trackPrivateEvent = function(collection, event) {
return _trackCustomEvent(_this._privateClient, collection, event);
};
_this.trackPrivateEvents = function(events) {
return _trackCustomEvents(_this._privateClient, events);
};

_this.trackPublicEvent = function(collection, event) {
return _trackCustomEvent(_this._publicClient, collection, event);
};
_this.trackPublicEvents = function(events) {
return _trackCustomEvents(_this._publicClient, events);
};
}
}

var instance = null;
return {
getInstance() {
if (!instance) {
let configInfo = {};
config.metricsAdapters.forEach((adapter) => {
if (adapter.name === 'Keen') {
configInfo = adapter.config;
}
});
instance = new KeenTracker();
instance.init(configInfo);
}
return instance;
}
};
},
userContextVars() {
// Extract user variables from session.
const session = this.get('session');
let user = {};
if (session.get('isAuthenticated')) {
let userInfo = session.get('session.authenticated');
user = {
id: userInfo.id,
entry_point: userInfo.attributes.entry_point, // Don't have the entry point.
institutions: null, // Don't really want to make an API request to fetch user institutions.
locale: userInfo.attributes.locale,
timezone: userInfo.attributes.timezone
};
}
user.anon = {}; // Do not have this info, but most duplicated in geo.
return user;
},
nodeContextVars(node) {
// Extract node variables, if passed in.
let nodeVars = {};
if (node && node.id) {
nodeVars = {
id: node.get('id'),
title: node.get('title'),
type: node.get('category'),
tags: node.get('tags'),
isPublic: node.get('public')
};
}
return nodeVars;
},
});
Loading

0 comments on commit 8393568

Please sign in to comment.