chadtmiller.com/pds.js
An atproto PDS in JavaScript, for Cloudflare Workers and Node
0
0
import { describe, expect, it } from 'vitest';
import {
byPull,
fileSummary,
fixesOf,
mergedRun,
place,
pullKey,
pullRkey,
replacedTips,
runsForCopies,
subjectOf,
} from '../src/pull-requests.js';
/** @param {string} name */
const sha = (name) => name.repeat(40).slice(0, 40);
/** @param {string} name @param {string} [message] */
const commit = (name, message = '') => ({ sha: sha(name), message });
describe('pullKey', () => {
it('names a pull request by the account and the branch', () => {
expect(pullKey('did:plc:bob', 'agent/docs')).toBe('did:plc:bob agent/docs');
});
it('tells two branches of one account apart', () => {
expect(pullKey('did:plc:bob', 'a')).not.toBe(pullKey('did:plc:bob', 'b'));
});
});
describe('subjectOf', () => {
it('is the first line', () => {
expect(subjectOf('add farewell()\n\nA body.\n')).toBe('add farewell()');
});
});
describe('place', () => {
const main = [sha('d'), sha('c'), sha('b'), sha('a')];
it('counts the commits main does not have, and names the merge base', () => {
const placed = place([commit('f'), commit('e'), commit('c')], main);
expect(placed.ahead).toBe(2);
expect(placed.base).toBe(sha('c'));
expect(placed.merged).toBe(false);
expect(placed.rooted).toBe(true);
});
it('counts the commits main has that the branch does not', () => {
// Branched at b, which main has moved two commits past.
expect(place([commit('e'), commit('b')], main).behind).toBe(2);
expect(place([commit('e'), commit('d')], main).behind).toBe(0);
});
it('reports a tip main already reaches as merged', () => {
const placed = place([commit('c'), commit('b')], main);
expect(placed.merged).toBe(true);
expect(placed.ahead).toBe(0);
expect(placed.behind).toBe(0);
});
it('reports a branch sharing no commit with main as unrooted', () => {
const placed = place([commit('z'), commit('y')], main);
expect(placed.rooted).toBe(false);
expect(placed.merged).toBe(false);
// Nothing places it, so a distance would be a guess.
expect(placed.behind).toBe(0);
});
it('treats an empty branch as merged', () => {
expect(place([], main).merged).toBe(true);
});
});
describe('mergedRun', () => {
/** @param {string} name @param {string[]} parents */
const entry = (name, parents = []) => ({
sha: sha(name),
parents: parents.map(sha),
});
// main: m (merge of t and p) over p over o. The branch is t over s over p.
const branch = [entry('t', ['s']), entry('s', ['p']), entry('p', ['o'])];
const mainCommits = [entry('m', ['p', 't']), entry('p', ['o']), entry('o')];
it('takes the commits the merge brought in, and where they began', () => {
const run = mergedRun(branch, mainCommits);
expect(run.ahead).toBe(2);
expect(run.base).toBe(sha('p'));
});
it('takes the tip alone where no merge commit names it', () => {
const run = mergedRun(branch, [entry('p', ['o']), entry('o')]);
expect(run.ahead).toBe(1);
expect(run.base).toBe(sha('s'));
});
it('reports no base at the root of a history', () => {
expect(mergedRun([entry('a')], []).base).toBe(null);
});
});
describe('fileSummary', () => {
it('counts the paths per directory, most first', () => {
const summary = fileSummary([
'packages/core/src/http.js',
'packages/core/src/auth.js',
'README.md',
'packages/git/src/pack.js',
]);
expect(summary.count).toBe(4);
expect(summary.dirs).toEqual([
{ dir: 'packages/core/src', count: 2 },
{ dir: '', count: 1 },
{ dir: 'packages/git/src', count: 1 },
]);
});
it('counts nothing for no paths', () => {
expect(fileSummary([])).toEqual({ count: 0, dirs: [] });
});
});
describe('runsForCopies', () => {
// Each copy under its own holder's key, which is what a run names.
const copies = [
'at://did:plc:alice/dev.pdsjs.git.repo/project',
'at://did:plc:bob/dev.pdsjs.git.repo/project',
];
/** @param {string} did @param {string} startedAt */
const run = (did, startedAt, rkey = 'project') => ({
value: {
subject: { uri: `at://${did}/dev.pdsjs.git.repo/${rkey}` },
sha: sha('a'),
startedAt,
},
});
it('keeps the runs about any named copy, newest first', () => {
const runs = runsForCopies(
[
run('did:plc:alice', '2026-08-01T00:00:00Z'),
run('did:plc:bob', '2026-08-02T00:00:00Z'),
],
copies,
);
expect(runs.map((entry) => entry.startedAt)).toEqual([
'2026-08-02T00:00:00Z',
'2026-08-01T00:00:00Z',
]);
});
it('drops another repository, and an account nobody named', () => {
const runs = runsForCopies(
[
run('did:plc:alice', '2026-08-01T00:00:00Z', 'other'),
run('did:plc:mallory', '2026-08-01T00:00:00Z'),
{ value: { subject: { uri: 42 } } },
{},
],
copies,
);
expect(runs).toEqual([]);
});
});
describe('pullRkey', () => {
it('derives a safe record key from the repository and the full ref', () => {
expect(pullRkey('project', 'refs/heads/feature/x')).toBe(
'project:refs_heads_feature_x',
);
expect(pullRkey('pds.js', 'refs/heads/main')).toBe(
'pds.js:refs_heads_main',
);
});
});
describe('fixesOf', () => {
it('reads each Fixes trailer as an issue address', () => {
const message = [
'refuse a non-string name',
'',
'Fixes: at://did:plc:dan/dev.pdsjs.git.issue/3kissue',
].join('\n');
expect(fixesOf(message)).toEqual([
'at://did:plc:dan/dev.pdsjs.git.issue/3kissue',
]);
});
it('ignores prose mentioning a fix and messages without one', () => {
expect(fixesOf('this fixes the bug')).toEqual([]);
expect(fixesOf('Fixes: #123')).toEqual([]);
expect(fixesOf('')).toEqual([]);
});
});
describe('byPull', () => {
it('indexes a review under its pull request and its sha', () => {
const statement = {
author: 'did:plc:bob',
ref: 'refs/heads/agent/docs',
sha: sha('a'),
};
const index = byPull([statement]);
expect(index.get(pullKey('did:plc:bob', 'agent/docs'))).toEqual([
statement,
]);
expect(index.get(sha('a'))).toEqual([statement]);
});
it("reads a check's pull request off the copy it ran against", () => {
const run = {
subject: { uri: 'at://did:plc:bob/dev.pdsjs.git.repo/project' },
ref: 'refs/heads/agent/docs',
sha: sha('a'),
};
const index = byPull([run]);
expect(index.get(pullKey('did:plc:bob', 'agent/docs'))).toEqual([run]);
});
it('indexes a statement naming no branch under its sha alone', () => {
const index = byPull([{ sha: sha('a') }]);
expect([...index.keys()]).toEqual([sha('a')]);
});
});
describe('replacedTips', () => {
/** Only what replacedTips reads of a pull request. @param {string} name */
const tip = (name) => /** @type {any} */ ({ sha: sha(name) });
it('names every tip the branch has carried but the one it carries now', () => {
const replaced = replacedTips(tip('c'), [
{ sha: sha('b'), startedAt: '2026-08-02T00:00:00Z' },
{ sha: sha('a'), reviewedAt: '2026-08-01T00:00:00Z' },
{ sha: sha('c'), startedAt: '2026-08-03T00:00:00Z' },
]);
expect([...replaced].sort()).toEqual([sha('a'), sha('b')]);
// The tip is not something the branch replaced.
expect(replaced.has(sha('c'))).toBe(false);
});
it('names nothing where the branch has never been rewritten', () => {
expect(replacedTips(tip('a'), []).size).toBe(0);
expect(
replacedTips(tip('a'), [{ sha: sha('a'), reviewedAt: '' }]).size,
).toBe(0);
});
});