diff --git a/stats/index.php b/stats/index.php index 049792c..d394ebf 100644 --- a/stats/index.php +++ b/stats/index.php @@ -1,5 +1,14 @@ 0 && date_create($_GET['start']); + } + + $semester_start = date_create('first day of august'); + if($semester_start > date_create()) { + $semester_start = date_modify($semester_start, '-1 year'); + } + $start = is_valid_start_param() ? date_create($_GET['start']) : $semester_start; ?> @@ -7,163 +16,59 @@ Medlemsstatistikk - Det Norske Studentersamfund - - - - - - - + +
-

Salg per dag

- Fra 1. august 2015 -
-

Salg totalt

-
-
SMS:
-
App:
-
Bar:
-
Totalt:
+
+
+

Medlemskapsstatistikk for DNS

+
Disse tallene kan avvike fra faktiske salgtall.
+
-

Salg idag

- Dato: -
-
-
SMS:
-
App:
-
Bar:
-
Totalt:
+
+
+ +

Salg per dag

+ +
+ +

Salg totalt

+
+
SMS:
+
App:
+
Bar:
+
Totalt:
+
+ +
+ +

Salg idag

+ Dato: +
+
+
SMS:
+
App:
+
Bar:
+
Totalt:
+
+
+
+

Salg per dag

+ +
+
- -



Disse tallene kan avvike fra faktiske salgtall.
+ + + + + + + diff --git a/stats/stats.css b/stats/stats.css new file mode 100644 index 0000000..6353e5b --- /dev/null +++ b/stats/stats.css @@ -0,0 +1,4 @@ +.big-number { + font-weight: bold; + font-size: 1.5em; +} \ No newline at end of file diff --git a/stats/stats.js b/stats/stats.js new file mode 100644 index 0000000..308c335 --- /dev/null +++ b/stats/stats.js @@ -0,0 +1,222 @@ +/* FIXME: Make this more generic */ +var saleTypes = ['bar', 'sms', 'app']; +var salesData = {}; + +var salesChart; +var salesChartToday; + +var urls = { + cards: 'https://kassa.neuf.no/stats/card-sales/', + tekstmelding: 'https://tekstmelding.neuf.no/stats/memberships/', + snapporder: '/stats/snapporder.php' +}; + +function sumSales(memo, num) { + return memo + num.sales; +} + +function toHighchartsSeries(memberships) { + memberships = _.sortBy(memberships, 'date'); + return _.map(memberships, function (el) { + return [moment.utc(el.date).valueOf(), el.sales] + }); +} + +function getBarSales(start) { + return $.getJSON(urls.cards + '?start=' + start, function(data) { + salesData['bar'] = data.memberships; + salesChart.addSeries({name: 'Bar-salg', data: toHighchartsSeries(salesData['bar'])}); + }); +} + +function getSmsSales(start) { + return $.getJSON(urls.tekstmelding + '?start=' + start, function(data) { + salesData['sms'] = data.memberships; + salesChart.addSeries({name: 'SMS-salg', data: toHighchartsSeries(salesData['sms'])}); + }); +} + +function getAppSales(start) { + return $.getJSON(urls.snapporder + '?start=' + start, function (data) { + salesData['app'] = data.memberships; + salesChart.addSeries({name: 'App-salg', data: toHighchartsSeries(salesData['app'])}); + }); +} + +function totals() { + var sum = 0; + _.each(saleTypes, function(type) { + var total = _.reduce(salesData[type], sumSales, 0); + $('.'+ type).html(total); + sum += total; + }) ; + + $('.sum').html(sum); +} + +function today() { + var today = moment.utc().format('YYYY-MM-DD'); + $('.today-date-wrap').text(today); + var todayBarSales = _.findWhere(salesData['bar'], {date: today}) || {sales: 0}; + $('.bar-today').html(todayBarSales.sales); + var todaySmsSales = _.findWhere(salesData['sms'], {date: today}) || {sales: 0}; + $('.sms-today').html(todaySmsSales.sales); + var todayAppSales = _.findWhere(salesData['app'], {date: today}) || {sales: 0}; + $('.app-today').html(todayAppSales.sales); + + $('.sum-today').html(todayBarSales.sales + todaySmsSales.sales + todayAppSales.sales); + + salesChartToday = new Highcharts.Chart({ + chart: { + renderTo: 'sales-chart-today', + plotBackgroundColor: null, + plotBorderWidth: null, + plotShadow: false, + type: 'pie' + }, + title: { + text: false + }, + series: [{ + name: 'Salg', data: [ + {name: 'Bar-salg', y: todayBarSales.sales}, + {name: 'SMS-salg', y: todaySmsSales.sales}, + {name: 'App-salg', y: todayAppSales.sales} + ] + } + ] + }); +} + +function groupSalesByDate() { + var salesByDate = {}; + _.each(saleTypes, function (type) { + _.each(salesData[type], function (el) { + var d = {}; + d[el.date] = {}; + d[el.date][type]= el.sales; + + $.extend(true, salesByDate, d); + }); + }); + /* add zeros */ + _.each(salesByDate, function (sales, date) { + _.each(saleTypes, function (type) { + if(typeof sales[type] == 'undefined') { + salesByDate[date][type] = 0; + } + }); + }); + + var table_friendly = []; + _.each(salesByDate, function (sales, date) { + sales.date = date; + table_friendly.push(sales); + }); + table_friendly = _.sortBy(table_friendly, 'date').reverse(); + + return table_friendly; +} + +function salesTable() { + var html = 'DatoBarSMSApp'; + html += ''; + salesData = groupSalesByDate(); + + _.each(salesData, function(el) { + html += '' + el.date + ''; + _.each(saleTypes, function(type) { + html += '' + el[type] + ''; + }); + html += ''; + }); + html += ''; + $('#sales-table').html(html); +} + +function toCSV(data) { + var csvLines = data.map(function(d){ + return d.date + ',' + saleTypes.map(function(t) { return d[t]; }).join(','); + }); + var csvHeader = 'date,' +saleTypes.join(',') + '\n'; + return csvHeader + csvLines.join('\n') +} + +function downloadCSVFile(csvData, fileName) { + csvData = 'data:text/csv;charset=utf-8,' + csvData; + var encodedUri = encodeURI(csvData); + + var link = document.createElement("a"); + link.setAttribute("href", encodedUri); + link.setAttribute("download", fileName); + document.body.appendChild(link); // Required for FF + + link.click(); +} + +function recalc(start, cb) { + salesChart = new Highcharts.Chart({ + chart: { + renderTo: 'sales-chart' + }, + title: { + text: false + }, + xAxis: { + type: "datetime" + }, + yAxis: { + title: { + text: "Salg" + }, + min: 0 + }, + plotOptions: { + series: { + marker: { + radius: 4 + } + } + }, + series: [] + }); + + $.when(getSmsSales(start), getAppSales(start), getBarSales(start)).done(function() { + totals(); + salesTable(); + + if(cb) { + cb(); + } + }); +} + +$(document).ready(function() { + Highcharts.setOptions({ + credits: {enabled: false} + }); + + var $exportBtn = $('.export-data-btn'); + var $startInput = $('#start'); + + var start = $startInput.val(); + recalc(start, function() { + today(); + }); + + /* Dynamic date change */ + $startInput.on('input', function(e) { + start = $(e.target).val(); + history.replaceState(null, null, '?start=' + start); + recalc(start); + }); + + /* Export to CSV */ + $exportBtn.on('click', function (e) { + e.preventDefault(); + var fileName = 'medlemskapsstats-' + $startInput.val() + '.csv'; + var csvData = toCSV(salesData); + downloadCSVFile(csvData, fileName); + }); + +});