repositories / dotfiles
dotfiles
bugabingas dorkfiles
owned by admin
quickshell/nuguland/screenshots.test.mjs
Rawimport assert from "node:assert/strict";
import { readFileSync } from "node:fs";
import { test } from "node:test";
import vm from "node:vm";
// Replay the actual service functions, not a second screenshot implementation.
// This is not QML loading, native capture, input, file, or visual evidence.
const qml = readFileSync(new URL("Screenshots.qml", import.meta.url), "utf8");
const start = qml.indexOf(" function rectFromPoints(");
const end = qml.indexOf(" Connections {", start);
assert.ok(start >= 0 && end > start);
const plain = value => JSON.parse(JSON.stringify(value));
function service(available = true) {
const calls = [];
const state = {
niriService: {
available,
screenshotScreen: path => calls.push(["screenshot-screen", path]),
screenshotWindow: path => calls.push(["screenshot-window", path]),
screenshot: path => calls.push(["screenshot", path]),
pickColor: () => calls.push(["pick-color"]),
},
osdService: null, lastColor: "", recent: [], pending: [], requestSerial: 0,
lastAction: {}, lastOsd: {}, selection: { phase: "idle", completionFlash: false },
nativeActions: ["screenshot-screen", "screenshot-window", "screenshot", "pick-color"],
boundedActions: [], toolbarActions: ["copy", "save", "cancel", "color"],
};
Object.defineProperty(state, "nativeActionRoute", {
get: () => !!state.niriService?.available,
});
state.root = state;
vm.createContext(state);
vm.runInContext(qml.slice(start, end), state);
const handler = qml.slice(end).match(/function onScreenshotCaptured\(path\) \{([^}]+)\}/);
assert.ok(handler, "completion uses Connections");
assert.match(qml.slice(end), /target: root\.niriService/);
state.emit = vm.runInContext(`(function(path) { ${handler[1]} })`, state);
state.calls = calls;
return state;
}
for (const [kind, native] of [
["focused-screen", "screenshot-screen"],
["focused-window", "screenshot-window"],
["interactive", "screenshot"],
]) {
test(`${kind}: submission is pending; exact completion alone saves`, () => {
const s = service();
const path = `/captures/${kind}.png`;
const submitted = JSON.parse(s.capture(kind, path));
assert.deepEqual(s.calls, [[native, path]]);
assert.equal(submitted.recentCount, 0);
assert.equal(submitted.pendingCount, 1);
assert.equal(submitted.lastAction.status, "pending");
assert.equal(submitted.lastAction.saved, false);
assert.equal(submitted.lastAction.completed, false);
s.emit(`/unrelated/${kind}.png`);
assert.equal(s.recent.length, 0);
assert.equal(s.pending.length, 1);
s.emit(path);
assert.equal(s.pending.length, 0);
assert.deepEqual(plain(s.recent), [{
id: submitted.lastAction.id, kind, path, source: "niri-native", saved: true,
}]);
assert.equal(s.lastAction.status, "saved");
assert.equal(s.lastAction.completed, true);
s.emit(path);
assert.equal(s.recent.length, 1, "unmatched duplicate cannot add a record");
});
}
test("unavailable or absent compositor never dispatches or records", () => {
for (const kind of ["focused-screen", "focused-window", "interactive", "select-region"]) {
for (const absent of [false, true]) {
const s = service(false);
if (absent) s.niriService = null;
if (kind === "select-region") s.completeSelection("/capture.png");
else s.capture(kind, "/capture.png");
s.emit("/capture.png");
assert.equal(s.calls.length, 0);
assert.equal(s.pending.length, 0);
assert.equal(s.recent.length, 0);
assert.equal(s.lastAction.status, "unavailable");
assert.equal(s.selection.completionFlash, false);
}
}
});
test("unsupported actions and missing paths never dispatch or queue", () => {
const s = service();
s.capture("copy", "/capture.png");
assert.equal(s.lastAction.status, "unsupported");
for (const path of ["", null, undefined]) {
s.capture("interactive", path);
assert.equal(s.lastAction.status, "invalid-path");
}
assert.equal(s.calls.length, 0);
assert.equal(s.pending.length, 0);
assert.equal(s.recent.length, 0);
});
test("null completion cannot identify clipboard-only or failed-write requests", () => {
const s = service();
s.capture("interactive", "/clipboard-only.png");
s.capture("focused-screen", "/missing-parent/failure.png");
const pending = plain(s.pending);
for (const path of [null, null, undefined, "", 42, { path: "/clipboard-only.png" }]) s.emit(path);
assert.deepEqual(plain(s.pending), pending);
assert.equal(s.recent.length, 0);
assert.equal(s.lastAction.completed, false);
});
test("no event means unconfirmed, not saved or inferred cancelled/failed", () => {
const s = service();
s.capture("interactive", "/cancelled.png");
s.capture("focused-window", "/render-failure.png");
s.niriService.available = false;
const state = JSON.parse(s.stateJson());
assert.equal(state.pendingCount, 2);
assert.ok(state.pending.every(request => request.status === "pending" && !request.saved));
assert.equal(state.recentCount, 0);
s.emit("/render-failure.png");
assert.equal(s.recent.length, 1, "a late matching save still counts while disconnected");
});
test("repeated kinds retain distinct requests and out-of-order completions", () => {
const s = service();
s.capture("focused-screen", "/first.png");
s.capture("focused-screen", "/second.png");
const [first, second] = plain(s.pending);
assert.notEqual(first.id, second.id);
s.emit(second.path);
s.emit(first.path);
assert.deepEqual(plain(s.recent).map(record => record.id), [first.id, second.id]);
assert.equal(s.lastAction.id, second.id, "late completion cannot overwrite newer action");
assert.equal(s.lastAction.status, "saved");
});
test("same-path repeats consume one FIFO match per event, without pretending request identity", () => {
const s = service();
s.capture("focused-screen", "/same.png");
s.capture("focused-window", "/same.png");
const [first, second] = plain(s.pending);
s.emit("/same.png");
assert.equal(s.pending.length, 1);
assert.equal(s.recent[0].id, first.id);
assert.equal(s.lastAction.status, "pending");
s.emit("/same.png");
assert.equal(s.pending.length, 0);
assert.deepEqual(plain(s.recent).map(record => record.id), [second.id, first.id]);
s.capture("interactive", "/same.png");
s.emit("/same.png");
assert.equal(s.recent.length, 3, "sequential reuse also retains a distinct saved record");
});
test("matching is exact, not basename or normalized-path guessing", () => {
const s = service();
s.capture("focused-screen", "capture.png");
s.emit("/capture.png");
s.emit("./capture.png");
assert.equal(s.recent.length, 0);
s.emit("capture.png");
assert.equal(s.recent.length, 1);
});
test("completeSelection preserves geometry but does not flash success before matching save", () => {
const s = service();
s.beginSelection(30, 40);
s.updateSelection(-10, -20);
const submitted = JSON.parse(s.completeSelection("/region.png"));
assert.deepEqual(s.calls, [["screenshot", "/region.png"]]);
assert.deepEqual(submitted.selection.rect, { x: -10, y: -20, width: 40, height: 60 });
assert.equal(submitted.selection.phase, "pending");
assert.equal(submitted.selection.completionFlash, false);
assert.equal(submitted.selectionVisuals.dimmedMask.visible, true);
assert.equal(submitted.recentCount, 0);
assert.equal(submitted.pending[0].kind, "select-region");
s.emit(null);
s.emit("/other.png");
assert.equal(s.selection.phase, "pending");
s.emit("/region.png");
assert.equal(s.selection.phase, "completed");
assert.equal(s.selection.completionFlash, true);
assert.equal(s.recent[0].kind, "select-region");
});
test("repeated selections only complete the current preview", () => {
const s = service();
s.completeSelection("/first.png");
s.completeSelection("/second.png");
s.emit("/first.png");
assert.equal(s.selection.phase, "pending");
s.emit("/second.png");
assert.equal(s.selection.phase, "completed");
s.completeSelection("/third.png");
s.updateSelection(10, 20);
s.emit("/third.png");
assert.equal(s.selection.phase, "dragging", "new drag is not completed by an older request");
});
test("local preview cancellation does not claim native cancellation or fabricate a save", () => {
const s = service();
s.completeSelection("/region.png");
s.cancelSelection();
assert.equal(s.selection.phase, "idle");
assert.equal(s.selection.completionFlash, false);
assert.equal(s.pending.length, 1, "native outcome remains unknown");
assert.equal(s.recent.length, 0);
assert.equal(s.calls.length, 1, "no invented native cancel command");
s.emit("/region.png");
assert.equal(s.recent.length, 1, "real late save remains visible in history");
assert.equal(s.selection.phase, "idle");
assert.equal(s.lastAction.kind, "cancel");
});
test("pending is registered before native dispatch", () => {
const s = service();
s.niriService.screenshot = path => s.emit(path);
const result = JSON.parse(s.completeSelection("/immediate.png"));
assert.equal(result.recentCount, 1);
assert.equal(result.pendingCount, 0);
assert.equal(result.lastAction.status, "saved");
assert.equal(result.selection.completionFlash, true);
});
test("history stays capped at twelve successes; clear forgets pending without cancelling Niri", () => {
const s = service();
for (let i = 0; i < 14; i++) {
s.capture("focused-window", `/capture-${i}.png`);
s.emit(`/capture-${i}.png`);
}
assert.equal(s.recent.length, 12);
assert.equal(s.recent[0].path, "/capture-13.png");
assert.equal(s.recent[11].path, "/capture-2.png");
s.completeSelection("/pending.png");
const serial = s.requestSerial;
const cleared = JSON.parse(s.clear());
assert.equal(cleared.recentCount, 0);
assert.equal(cleared.pendingCount, 0);
assert.equal(cleared.lastAction.kind, "clear");
assert.equal(cleared.selection.phase, "idle");
assert.equal(s.calls.length, 15);
s.emit("/pending.png");
assert.equal(s.recent.length, 0);
s.capture("focused-screen", "/new.png");
assert.ok(s.requestSerial > serial, "clear cannot reuse local IDs");
});
test("color picking, OSD fallback and metadata-only record actions remain independent", () => {
const s = service();
s.capture("focused-screen", "/capture.png");
s.pickColor();
assert.deepEqual(s.calls.at(-1), ["pick-color"]);
s.acceptPickedColor("not a color");
assert.equal(s.lastColor, "");
s.acceptPickedColor("#ABCDEF");
assert.equal(s.lastColor, "#abcdef");
assert.deepEqual(plain(s.lastOsd), { event: "color", value: "#abcdef" });
s.osdService = { trigger: (event, value) => JSON.stringify({ event, value, delivered: true }) };
s.acceptPickedColor("#123456");
assert.equal(s.lastOsd.delivered, true);
s.osdService = { trigger() { throw Error("unavailable"); } };
s.acceptPickedColor("#654321");
assert.equal(s.lastOsd.value, "#654321");
s.emit("/capture.png");
assert.equal(s.lastAction.kind, "pick-color");
s.recordAction("copy", s.recent[0].id);
assert.equal(s.lastAction.nativeActionRoute, false);
assert.equal(s.recent.length, 1);
s.niriService = null;
s.pickColor();
assert.equal(s.calls.length, 2, "unavailable color picking does not dispatch");
});