Files
STSheets/tests/ref/manifest.test.ts

50 lines
2.1 KiB
TypeScript

import { test, expect, beforeEach, afterEach } from "bun:test";
import { mkdtemp, rm } from "node:fs/promises";
import { tmpdir } from "node:os";
import { join } from "node:path";
import { addSong, readManifest, songDir } from "../../src/ref/manifest.ts";
let root = "";
beforeEach(async () => { root = await mkdtemp(join(tmpdir(), "ref-")); });
afterEach(async () => { await rm(root, { recursive: true, force: true }); });
const base = { id: "s1", title: "Song", audio: "a.flac", midi: "a.mid", capo: {} };
test("readManifest on empty root returns []", async () => {
expect(await readManifest(root)).toEqual([]);
});
test("addSong writes songs.json with given roles", async () => {
const e = await addSong({ ...base, roles: { Gtr: "guitar", Crowd: null } }, root);
expect(e.roles).toEqual({ Gtr: "guitar", Crowd: null });
expect(await Bun.file(join(root, "songs.json")).exists()).toBe(true);
expect(await readManifest(root)).toEqual([e]);
});
test("addSong guesses roles from the midi, keyed by track name", async () => {
const ascii = (x: string) => [...x].map((c) => c.charCodeAt(0));
const trk = (n: string, prog: number) => {
const body = [0, 0xff, 3, n.length, ...ascii(n), 0, 0xc0, prog, 0, 0x90, 60, 90, 0x60, 0x80, 60, 0, 0, 0xff, 0x2f, 0];
return [...ascii("MTrk"), 0, 0, 0, body.length, ...body];
};
const mid = new Uint8Array([...ascii("MThd"), 0, 0, 0, 6, 0, 1, 0, 2, 0x01, 0xe0, ...trk("Acoustic Guitar ", 25), ...trk("Brass", 61)]);
const midi = join(root, "in.mid");
await Bun.write(midi, mid);
const e = await addSong({ ...base, midi }, root);
expect(e.roles).toEqual({ "Acoustic Guitar ": "guitar", Brass: null });
});
test("addSong rejects duplicate ids", async () => {
await addSong({ ...base, roles: {} }, root);
await expect(addSong({ ...base, roles: {} }, root)).rejects.toThrow(/duplicate|exists/i);
expect(await readManifest(root)).toHaveLength(1);
});
test("rejects unsafe ids", async () => {
await expect(addSong({ ...base, id: "../x", roles: {} }, root)).rejects.toThrow();
});
test("songDir", () => {
expect(songDir("s1", root)).toBe(join(root, "s1"));
});