<commit_before>'use strict';
require('isomorphic-fetch');
const querystring = require('querystring');
const utils = require('./utils');
const tabulate = require('./tabulate');
const URL = require('url');
const forcedQueries = [];

const configContainer = process.browser ? window : process.env

let printers = {
	json: function (curr, prev) {
		return prev ? {curr,prev} : curr;
	},

	csv: function (curr, prev) {

	}
}

const filterShorthandMap = {
	'=': {
		operator: 'eq',
	},
	'!=': {
		operator: 'not_eq',
	},
	'>>': {
		operator: 'contains'
	},
	'>': {
		operator: 'gt',
	},
	'<': {
		operator: 'lt',
	},
	'<<': {
		operator: 'in',
		handleList: true
	}
};

const reverseFilterShorthandMap = {
	'eq': '=',
	'not_eq': '!=',
	'ne': '!=',
	'contains': '>>',
	'gt': '>',
	'lt': '<',
	'in': '<<'
};

const intervalMappings = {
	m: 'minutely',
	h: 'hourly',
	d: 'daily',
	w: 'weekly',
	mo: 'monthly',
	y: 'yearly',
}

const intervalUnitMappings = {
	m: 'minute',
	h: 'hour',
	d: 'day',
	w: 'week',
	mo: 'month',
	y: 'year',
}

const extractionMappings = {
	minimum: 'min',
	maximum: 'max',
	sum: 'sum',
	average: 'avg',
	median: 'med',
	count_unique: 'count',
	select_unique: 'select'
}

class KeenQuery {
	constructor (event) {
		if (typeof event === 'object') {
			this.query = event.query || {};
			this.extraction = event.extraction;
			this.filters = event.filters;
		} else {
			this.query = {
				event_collection: event
			};
			this.filters = [];
			this.forcedQueries = forcedQueries;
		}

	}

	// chainable extraction methods
	count (prop) {
		if (prop) {
			this.setExtraction('count_unique')
			this.query.target_property = prop;
		} else {
			this.setExtraction('count')
		}
		return this;
	}
	min (prop) {
		this.setExtraction('minimum');
		this.query.target_property = prop;
		return this;
	}

	max (prop) {
		this.setExtraction('maximum');
		this.query.target_property = prop;
		return this;
	}

	sum (prop) {
		this.setExtraction('sum');
		this.query.target_property = prop;
		return this;
	}

	avg (prop) {
		this.setExtraction('average');
		this.query.target_property = prop;
		return this;
	}

	med (prop) {
		this.setExtraction('median');
		this.query.target_property = prop;
		return this;
	}

	pct (prop, pct) {
		this.setExtraction('percentile');
		this.query.target_property = prop;
		this.query.percentile = pct;
		return this;
	}

	select (prop) {
		this.setExtraction('select_unique');
		this.query.target_property = prop;
		return this;
	}

	raw () {
		this.forcedQueries = [];
		return this;
	}

	//other chainable query methods
	time (time, interval) {
		if (time) {

			// relative timeframe
			if (parseInt(time, 10) === Number(time)) {
				time = time + '_days';
				this.timeframe = 'this_' + time;
				this.prevTimeframe = this.timeframe.replace('this_', 'previous_');

			}

			// absolute timeframe
			else if(typeof time === 'object') {
				this.timeframe = JSON.stringify({
					start: time.start.toISOString(),
					end: time.end.toISOString()
				});
			}

			else {
				throw new Error('Invalid time. Expected absolute or relative timeframe (https://keen.io/docs/api/#timeframe): ' + time);
			}

		} else {
			this.timeframe = 'this_14_days';
			this.prevTimeframe = 'prev_14_days';
		}

		if (interval) {
			this.query.interval = intervalMappings[interval] || 'daily';
			this.intervalUnit = intervalUnitMappings[interval] || 'day';
		}
		return this;<commit_msg>separate abs and rel time into seperate json-param-free methods<commit_after>'use strict';
require('isomorphic-fetch');
const querystring = require('querystring');
const utils = require('./utils');
const tabulate = require('./tabulate');
const URL = require('url');
const forcedQueries = [];

const configContainer = process.browser ? window : process.env

let printers = {
	json: function (curr, prev) {
		return prev ? {curr,prev} : curr;
	},

	csv: function (curr, prev) {

	}
}

const filterShorthandMap = {
	'=': {
		operator: 'eq',
	},
	'!=': {
		operator: 'not_eq',
	},
	'>>': {
		operator: 'contains'
	},
	'>': {
		operator: 'gt',
	},
	'<': {
		operator: 'lt',
	},
	'<<': {
		operator: 'in',
		handleList: true
	}
};

const reverseFilterShorthandMap = {
	'eq': '=',
	'not_eq': '!=',
	'ne': '!=',
	'contains': '>>',
	'gt': '>',
	'lt': '<',
	'in': '<<'
};

const intervalMappings = {
	m: 'minutely',
	h: 'hourly',
	d: 'daily',
	w: 'weekly',
	mo: 'monthly',
	y: 'yearly',
}

const intervalUnitMappings = {
	m: 'minute',
	h: 'hour',
	d: 'day',
	w: 'week',
	mo: 'month',
	y: 'year',
}

const extractionMappings = {
	minimum: 'min',
	maximum: 'max',
	sum: 'sum',
	average: 'avg',
	median: 'med',
	count_unique: 'count',
	select_unique: 'select'
}

class KeenQuery {
	constructor (event) {
		if (typeof event === 'object') {
			this.query = event.query || {};
			this.extraction = event.extraction;
			this.filters = event.filters;
		} else {
			this.query = {
				event_collection: event
			};
			this.filters = [];
			this.forcedQueries = forcedQueries;
		}

	}

	// chainable extraction methods
	count (prop) {
		if (prop) {
			this.setExtraction('count_unique')
			this.query.target_property = prop;
		} else {
			this.setExtraction('count')
		}
		return this;
	}
	min (prop) {
		this.setExtraction('minimum');
		this.query.target_property = prop;
		return this;
	}

	max (prop) {
		this.setExtraction('maximum');
		this.query.target_property = prop;
		return this;
	}

	sum (prop) {
		this.setExtraction('sum');
		this.query.target_property = prop;
		return this;
	}

	avg (prop) {
		this.setExtraction('average');
		this.query.target_property = prop;
		return this;
	}

	med (prop) {
		this.setExtraction('median');
		this.query.target_property = prop;
		return this;
	}

	pct (prop, pct) {
		this.setExtraction('percentile');
		this.query.target_property = prop;
		this.query.percentile = pct;
		return this;
	}

	select (prop) {
		this.setExtraction('select_unique');
		this.query.target_property = prop;
		return this;
	}

	raw () {
		this.forcedQueries = [];
		return this;
	}

	interval(interval) {
		this.query.interval = intervalMappings[interval] || 'daily';
		this.intervalUnit = intervalUnitMappings[interval] || 'day';
		return this;
	}

	absTime (start, end, interval) {
		this.timeframe = JSON.stringify({
			start: start.toISOString(),
			end: end.toISOString()
		});

		// todo prevTimeframe

		if (interval) {
			this.interval(interval);
		}

		return this;
	}

	relTime(time, interval) {
		if (time) {
			if (parseInt(time, 10) === Number(time)) {
				time = time + '_days';
			}
		} else {
			time = '14_days';
		}
		this.timeframe = 'this_' + time;
		this.prevTimeframe = this.timeframe.replace('this_', 'previous_');

		if (interval) {
			this.interval(interval);
		}

		return this;
	}

	time(time, interval) {
		return this.relTime(time, interval);
{'fraction_non_alphanumeric': 0.17875036840554082, 'fraction_numerical': 0.0014736221632773356, 'mean_word_length': 3.5276851234156106, 'pattern_counts': {'":': 0, '<': 15, '<?xml version=': 0, '>': 15, 'https://': 1, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2593983', 'n_tokens_mistral': 2806, 'n_tokens_neox': 2499, 'n_words': 518}