@dapplion/benchmark
Version:
Ensures that new code does not introduce performance regressions with CI. Tracks:
101 lines (100 loc) • 3.17 kB
JavaScript
import fs from "node:fs";
import path from "node:path";
import { HistoryProviderType } from "./provider.js";
import { fromCsv, toCsv } from "../utils/file.js";
const extension = ".csv";
const historyDir = "history";
const latestDir = "latest";
/**
* Persist results in CSV, one benchmark result per file
*
* ```
* /$dirpath/
* history/
* 52b8122daa9b7a3d0ea0ecfc1ff9eda79a201eb8.csv
* c0203c527c9a2269f1f289fad2c8e25afdc2c169.csv
* latest/
* main.csv
* dev.csv
* ```
*
* ```csv
* id,averageNs,runsDone,totalMs
* sum array with raw for loop,1348118,371,501
* sum array with reduce,16896469,128,2163
* ```
*/
export class LocalHistoryProvider {
dirpath;
type = HistoryProviderType.Local;
constructor(dirpath) {
this.dirpath = dirpath;
}
providerInfo() {
return `LocalHistoryProvider, dirpath ${this.dirpath}`;
}
async readLatestInBranch(branch) {
const filepath = this.getLatestInBranchFilepath(branch);
return this.readBenchFileIfExists(filepath);
}
async writeLatestInBranch(branch, benchmark) {
const filepath = this.getLatestInBranchFilepath(branch);
this.writeBenchFile(filepath, benchmark);
}
async readHistory() {
const historyDirpath = this.getHistoryDirpath();
let files;
try {
files = fs.readdirSync(historyDirpath);
}
catch (e) {
if (e.code === "ENOENT")
return [];
else
throw e;
}
return files.map((file) => this.readBenchFile(path.join(historyDirpath, file)));
}
async readHistoryCommit(commitSha) {
const filepath = this.getHistoryCommitPath(commitSha);
return this.readBenchFileIfExists(filepath);
}
async writeToHistory(benchmark) {
const filepath = this.getHistoryCommitPath(benchmark.commitSha);
this.writeBenchFile(filepath, benchmark);
}
readBenchFileIfExists(filepath) {
try {
return this.readBenchFile(filepath);
}
catch (e) {
if (e.code === "ENOENT")
return null;
else
throw e;
}
}
/** Read result from CSV + metadata as Embedded Metadata */
readBenchFile(filepath) {
const str = fs.readFileSync(filepath, "utf8");
const { data, metadata } = fromCsv(str);
const csvMeta = metadata;
return { commitSha: csvMeta.commit, results: data };
}
/** Write result to CSV + metadata as Embedded Metadata */
writeBenchFile(filepath, benchmark) {
const csvMeta = { commit: benchmark.commitSha };
const str = toCsv(benchmark.results, csvMeta);
fs.mkdirSync(path.dirname(filepath), { recursive: true });
fs.writeFileSync(filepath, str);
}
getLatestInBranchFilepath(branch) {
return path.join(this.dirpath, latestDir, branch) + extension;
}
getHistoryCommitPath(commitSha) {
return path.join(this.getHistoryDirpath(), commitSha) + extension;
}
getHistoryDirpath() {
return path.join(this.dirpath, historyDir);
}
}