Separate statistics functions from main.js
This commit is contained in:
parent
cc1e1fa50c
commit
a1804e6ea2
79
main.js
79
main.js
|
@ -4,6 +4,7 @@ const fs = require('fs')
|
|||
const Gitlab = require('gitlab/dist/es5').default
|
||||
const klaw = require('klaw-sync')
|
||||
const path = require('path')
|
||||
const { avgTime, freqUsers, labelsAlphabet } = require('./statistics')
|
||||
|
||||
const api = new Gitlab({
|
||||
token: config.token
|
||||
|
@ -162,84 +163,28 @@ function createStatistics() {
|
|||
statistics += `${opened.length} issues were opened and `
|
||||
statistics += `${closed.length} issues were closed.\n\n`
|
||||
|
||||
const averageOpenPerDay = (opened.length / 30).toFixed(2)
|
||||
const averageClosePerDay = (closed.length / 30).toFixed(2)
|
||||
statistics += `An average of ${averageOpenPerDay} issues were opened `
|
||||
statistics += `and ${averageClosePerDay} issues were closed each day.\n\n`
|
||||
statistics += `An average of ${(opened.length / 30).toFixed(2)} issues were opened `
|
||||
statistics += `and ${(closed.length / 30).toFixed(2)} issues were closed each day.\n\n`
|
||||
|
||||
let averageClosedDays
|
||||
let averageClosedHours
|
||||
for (const file of closed) {
|
||||
const issue = require(file.path)
|
||||
const openedAt = new Date(issue.created_at)
|
||||
const closedAt = new Date(issue.closed_at)
|
||||
const diffDays = (closedAt - openedAt) / (1000 * 60 * 60 * 24)
|
||||
const diffHours = (closedAt - openedAt) / (1000 * 60 * 60)
|
||||
|
||||
averageClosedDays = (typeof averageClosedDays === 'undefined')
|
||||
? averageClosedDays = diffDays
|
||||
: averageClosedDays += diffDays
|
||||
averageClosedHours = (typeof averageClosedHours === 'undefined')
|
||||
? averageClosedHours = diffHours
|
||||
: averageClosedHours += diffHours
|
||||
}
|
||||
averageClosedDays = (averageClosedDays / closed.length).toFixed(2)
|
||||
averageClosedHours = (averageClosedHours / closed.length).toFixed(2)
|
||||
|
||||
statistics += `The average time to close issues was ${averageClosedDays} days `
|
||||
statistics += `or ${averageClosedHours} hours.\n\n`
|
||||
|
||||
let _mostFrequent = {}
|
||||
for (const file of opened) {
|
||||
const issue = require(file.path)
|
||||
if (typeof _mostFrequent[issue.author.username] === 'undefined') _mostFrequent[issue.author.username] = 1
|
||||
else _mostFrequent[issue.author.username]++
|
||||
}
|
||||
|
||||
let mostFrequent = Object.keys(_mostFrequent)
|
||||
mostFrequent.sort((a, b) => _mostFrequent[b] - _mostFrequent[a])
|
||||
mostFrequent = mostFrequent.slice(0, 3)
|
||||
statistics += `The average time to close issues was ${avgTime(closed, 'days')} days `
|
||||
statistics += `or ${avgTime(closed, 'hours')} hours.\n\n`
|
||||
|
||||
const topUsers = freqUsers(opened, 3)
|
||||
statistics += 'Top 3 issue creators:\n\n'
|
||||
for (const user of mostFrequent) {
|
||||
for (const user in topUsers) {
|
||||
statistics += `* [${user}](https://gitlab.com/${user}) `
|
||||
statistics += `with [${_mostFrequent[user]} issues created](https://gitlab.com/tildes/tildes/issues?state=all&author_username=${user}).\n`
|
||||
statistics += `with [${topUsers[user]} issues created](https://gitlab.com/tildes/tildes/issues?state=all&author_username=${user}).\n`
|
||||
}
|
||||
|
||||
let labels = {}
|
||||
for (const file of opened) {
|
||||
const issue = require(file.path)
|
||||
if (issue.closed_at !== null) continue
|
||||
for (const label of issue.labels) {
|
||||
if (typeof labels[label] === 'undefined') labels[label] = 1
|
||||
else labels[label]++
|
||||
}
|
||||
}
|
||||
|
||||
let labelsOrdered = {}
|
||||
Object.keys(labels).sort().forEach(label => labelsOrdered[label] = labels[label])
|
||||
|
||||
let labels = labelsAlphabet(opened, true)
|
||||
statistics += '\nAmount of labels assigned to currently open issues:\n\n'
|
||||
|
||||
for (const label in labelsOrdered) {
|
||||
for (const label in labels) {
|
||||
statistics += `* [${label}](https://gitlab.com/tildes/tildes/issues?state=opened&label_name%5B%5D=${label.replace(' ', '+')}): ${labels[label]} times.\n`
|
||||
}
|
||||
|
||||
labels = {}
|
||||
for (const file of closed) {
|
||||
const issue = require(file.path)
|
||||
for (const label of issue.labels) {
|
||||
if (typeof labels[label] === 'undefined') labels[label] = 1
|
||||
else labels[label]++
|
||||
}
|
||||
}
|
||||
|
||||
labelsOrdered = {}
|
||||
Object.keys(labels).sort().forEach(label => labelsOrdered[label] = labels[label])
|
||||
|
||||
labels = labelsAlphabet(closed, false)
|
||||
statistics += '\nAmount of labels assigned to closed issues:\n\n'
|
||||
|
||||
for (const label in labelsOrdered) {
|
||||
for (const label in labels) {
|
||||
statistics += `* [${label}](https://gitlab.com/tildes/tildes/issues?state=closed&label_name%5B%5D=${label.replace(' ', '+')}): ${labels[label]} times.\n`
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,76 @@
|
|||
/**
|
||||
* @function avgTime
|
||||
* @description Returns the average time it takes to close an issue in hours or days.
|
||||
* @param {Array} data Array with paths leading to GitLab Issue .json files
|
||||
* @param {string} time 'hours' or 'days'
|
||||
*/
|
||||
|
||||
function avgTime(data, time) {
|
||||
if (time !== 'hours' && time !== 'days') return Error('avgTime(data, time): time should be "hours" or "days"')
|
||||
let avg
|
||||
for (const file of data) {
|
||||
const issue = require(file.path)
|
||||
const openDate = new Date(issue.created_at)
|
||||
const closeDate = new Date(issue.closed_at)
|
||||
let diff
|
||||
if (time === 'days') diff = (closeDate - openDate) / (1000 * 60 * 60 * 24)
|
||||
else if (time === 'hours') diff = (closeDate - openDate) / (1000 * 60 * 60)
|
||||
avg = (typeof avg === 'undefined')
|
||||
? avg = diff
|
||||
: avg += diff
|
||||
}
|
||||
return (avg / data.length).toFixed(2)
|
||||
}
|
||||
|
||||
/**
|
||||
* @function freqUsers
|
||||
* @description Returns the top X issue creators.
|
||||
* @param {Array} data Array with paths leading to GitLab Issue .json files
|
||||
* @param {number} maxUsers Maximum amount of users to return, defaults to 3
|
||||
* @returns {Object}
|
||||
*/
|
||||
|
||||
function freqUsers(data, maxUsers) {
|
||||
if (typeof maxUsers === 'undefined') maxUsers = 3
|
||||
let userCounts = {}
|
||||
for (const file of data) {
|
||||
const issue = require(file.path)
|
||||
if (typeof userCounts[issue.author.username] === 'undefined') userCounts[issue.author.username] = 1
|
||||
else userCounts[issue.author.username]++
|
||||
}
|
||||
const sortedArray = Object.keys(userCounts).sort((a, b) => userCounts[b] - userCounts[a])
|
||||
const sortedObject = {}
|
||||
for (let i = 0; i < maxUsers; i++) {
|
||||
if (typeof sortedArray[i] === 'undefined') break
|
||||
sortedObject[sortedArray[i]] = userCounts[sortedArray[i]]
|
||||
}
|
||||
return sortedObject
|
||||
}
|
||||
|
||||
/**
|
||||
* @function labelsAlphabet
|
||||
* @description Returns all labels found in alphabetical order with their amount.
|
||||
* @param {Array} data Array with paths leading to GitLab Issue .json files
|
||||
* @param {boolean} checkNull Boolean whether or not to check if closed_at is null (for currently open issues)
|
||||
* @returns {Object}
|
||||
*/
|
||||
|
||||
function labelsAlphabet(data, checkNull) {
|
||||
if (typeof checkNull === 'undefined') checkNull = false
|
||||
const labels = {}
|
||||
for (const file of data) {
|
||||
const issue = require(file.path)
|
||||
if (checkNull && issue.closed_at !== null) continue
|
||||
for (const label of issue.labels) {
|
||||
if (typeof labels[label] === 'undefined') labels[label] = 1
|
||||
else labels[label]++
|
||||
}
|
||||
}
|
||||
const labelsOrdered = {}
|
||||
Object.keys(labels).sort().forEach(label => labelsOrdered[label] = labels[label])
|
||||
return labelsOrdered
|
||||
}
|
||||
|
||||
exports.avgTime = avgTime
|
||||
exports.freqUsers = freqUsers
|
||||
exports.labelsAlphabet = labelsAlphabet
|
Reference in New Issue