libyear
Version:
A simple measure of software dependency freshness
50 lines (49 loc) • 2.2 kB
JavaScript
import { metrics } from "./constants.js";
const isExcused = (dependency, overrides) => Object.entries(overrides).some(([pattern, { defer }]) => RegExp(pattern).test(dependency) && Date.now() < Date.parse(defer));
const isBreach = (value, limit, dependency, overrides) => limit != null && value > limit && !isExcused(dependency, overrides ?? {});
const getMatchingPattern = (dependency, overrides) => Object.keys(overrides).find((pattern) => RegExp(pattern).test(dependency));
export const getTotals = (dependencies) => {
const totals = new Map();
dependencies.forEach((dependency) => {
metrics.forEach((metric) => {
if (!Number.isNaN(dependency[metric])) {
const acc = totals.has(metric) ? totals.get(metric) : 0;
const cur = dependency[metric];
totals.set(metric, acc + cur);
}
});
});
return totals;
};
const getCollectiveViolations = (totals, threshold) => {
const violations = new Map();
metrics.forEach((metric) => {
const value = totals.get(metric);
const limit = threshold?.[`${metric}Collective`];
if (isBreach(value, limit)) {
violations.set(metric, value);
}
});
return violations;
};
const getIndividualViolations = (dependencies, threshold, overrides) => {
const violations = new Map();
dependencies.forEach(({ dependency, ...rest }) => {
metrics.forEach((metric) => {
const value = rest[metric];
const limit = overrides?.[getMatchingPattern(dependency, overrides)]?.[metric] ??
threshold?.[`${metric}Individual`];
if (isBreach(value, limit, dependency, overrides)) {
if (!violations.has(metric)) {
violations.set(metric, new Map());
}
violations.get(metric).set(dependency, { threshold: limit, value });
}
});
});
return violations;
};
export const getViolations = (dependencies, totals, threshold, overrides) => ({
collective: getCollectiveViolations(totals, threshold),
individual: getIndividualViolations(dependencies, threshold, overrides),
});