Luigit
repositories / dotfiles

dotfiles

bugabingas dorkfiles

owned by admin

niri/theme.test.mjs

Raw
import assert from "node:assert/strict";
import { cpSync, existsSync, mkdirSync, mkdtempSync, readFileSync, rmSync, writeFileSync } from "node:fs";
import { tmpdir } from "node:os";
import { dirname, join, resolve } from "node:path";
import { spawnSync } from "node:child_process";
import { fileURLToPath } from "node:url";
import test from "node:test";

const niriDir = dirname(fileURLToPath(import.meta.url));
const root = resolve(niriDir, "..");
const justArgs = ["--shell", "nu", "--clear-shell-args", "--shell-arg=--no-config-file", "--shell-arg=--commands", "niri"];

function run(command, args, cwd) {
    const result = spawnSync(command, args, { cwd, encoding: "utf8" });
    assert.equal(result.status, 0, `${command}: ${result.error ?? ""}\n${result.stdout}\n${result.stderr}`);
    return result.stdout;
}

test("Nugu installs both Niri themes; config alone selects the active variant", () => {
    const workspace = mkdtempSync(join(tmpdir(), "niri-theme-test-"));
    try {
        const nugu = join(workspace, "nugu");
        const config = join(workspace, "niri");
        mkdirSync(nugu);
        // Only source inputs: no pre-generated palettes or compositor intermediaries.
        for (const file of ["base.toml", "nugu.nu", "niri.nu", "justfile"])
            cpSync(join(root, "nugu", file), join(nugu, file));
        run("just", justArgs, nugu);
        assert.equal(existsSync(join(config, "config.kdl")), false, "generation must not select an active theme");
        cpSync(join(niriDir, "cfg"), join(config, "cfg"), { recursive: true });
        const originalConfig = readFileSync(join(niriDir, "config.kdl"), "utf8");
        const include = /^include "themes\/nugu-(?:dark|light)\.kdl"$/gm;
        assert.equal([...originalConfig.matchAll(include)].length, 1, "config must select exactly one theme");
        const originalLayout = readFileSync(join(config, "cfg/layout.kdl"), "utf8");
        const originalRules = readFileSync(join(config, "cfg/rules.kdl"), "utf8");
        const generated = new Set();

        for (const mode of ["dark", "light"]) {
            const p = JSON.parse(run("nu", ["--no-config-file", "-c", `use nugu.nu; nugu ${mode} | get palette | to json`], nugu));
            const filename = `nugu-${mode}.kdl`;
            const kdl = readFileSync(join(nugu, "output/niri", filename), "utf8");
            assert.equal(readFileSync(join(config, "themes", filename), "utf8"), kdl);
            assert.equal(readFileSync(join(niriDir, "themes", filename), "utf8"), kdl, "repo theme must match generator output");
            for (const block of ["focus-ring", "tab-indicator", "highlight"]) {
                const body = kdl.match(new RegExp(`${block} \\{([^}]+)\\}`))?.[1];
                assert.ok(body, block);
                assert.ok(body.includes(`active-color "${p.ui.focus}"`), block);
                assert.ok(body.includes(`urgent-color "${p.error}"`), block);
                if (block !== "highlight")
                    assert.ok(body.includes(`inactive-color "${p.ui.unfocus}"`), block);
            }
            assert.match(kdl, new RegExp(`insert-hint \\{\\s*color "${p.ui.focus}80"\\s*\\}`));
            assert.match(kdl, new RegExp(`overview \\{\\s*backdrop-color "${p.ui.backdrop}"\\s*\\}`));
            assert.doesNotMatch(kdl, /\b(?:background-color|shadow|border|on|off|width|gap|binds)\b/);
            const selectedConfig = originalConfig.replace(include, `include "themes/${filename}"`);
            writeFileSync(join(config, "config.kdl"), selectedConfig);
            run("just", justArgs, nugu);
            assert.equal(readFileSync(join(config, "config.kdl"), "utf8"), selectedConfig, "regeneration must preserve theme selection");
            assert.equal(readFileSync(join(config, "cfg/layout.kdl"), "utf8"), originalLayout);
            assert.equal(readFileSync(join(config, "cfg/rules.kdl"), "utf8"), originalRules);
            assert.equal(existsSync(join(config, "themes", `${filename}.tmp`)), false);
            run("niri", ["validate", "-c", join(config, "config.kdl")], workspace);
            generated.add(kdl);
        }
        assert.equal(generated.size, 2, "dark and light must differ");
        const invalid = spawnSync("nu", ["--no-config-file", "-c", "use niri.nu; niri theme invalid"], { cwd: nugu, encoding: "utf8" });
        assert.notEqual(invalid.status, 0);
        assert.match(invalid.stderr, /Expected dark or light/);
        assert.equal(existsSync(join(config, "cfg/nugu.kdl")), false, "no copied active-theme intermediary");
        assert.equal(existsSync(join(nugu, "output/dark.toml")), false);
        assert.equal(existsSync(join(nugu, "output/light.toml")), false);
        assert.equal(existsSync(join(workspace, "hypr")), false);
    } finally {
        rmSync(workspace, { recursive: true, force: true });
    }
});