@openmixer/plugin-qualify 0.14.1 → 0.16.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +127 -14
- package/bin/plugin-qualify-sync.mjs +57 -0
- package/bin/plugin-qualify.mjs +66 -15
- package/dist/adjust-cli.d.ts +83 -0
- package/dist/adjust-cli.js +214 -0
- package/dist/adjust-cli.js.map +1 -0
- package/dist/clap-loader.d.ts +3 -3
- package/dist/clap-loader.js +11 -11
- package/dist/clap-loader.js.map +1 -1
- package/dist/history-adjust.d.ts +77 -0
- package/dist/history-adjust.js +99 -0
- package/dist/history-adjust.js.map +1 -0
- package/dist/history-file.d.ts +73 -0
- package/dist/history-file.js +133 -0
- package/dist/history-file.js.map +1 -0
- package/dist/host-admission.d.ts +53 -0
- package/dist/host-admission.js +96 -0
- package/dist/host-admission.js.map +1 -0
- package/dist/index.d.ts +6 -0
- package/dist/index.js +6 -0
- package/dist/index.js.map +1 -1
- package/dist/lv2-loader.d.ts +16 -2
- package/dist/lv2-loader.js +168 -17
- package/dist/lv2-loader.js.map +1 -1
- package/dist/measurement/cli.d.ts +6 -4
- package/dist/measurement/cli.js +12 -19
- package/dist/measurement/cli.js.map +1 -1
- package/dist/pins-file.d.ts +8 -2
- package/dist/pins-file.js +17 -3
- package/dist/pins-file.js.map +1 -1
- package/dist/probe-judge.d.ts +11 -1
- package/dist/probe-judge.js +20 -1
- package/dist/probe-judge.js.map +1 -1
- package/dist/probe-output-fixtures.d.ts +10 -0
- package/dist/probe-output-fixtures.js +86 -0
- package/dist/probe-output-fixtures.js.map +1 -1
- package/dist/probe-output.d.ts +2 -0
- package/dist/probe-output.js +1 -0
- package/dist/probe-output.js.map +1 -1
- package/dist/probe-runner.d.ts +9 -3
- package/dist/probe-runner.js +36 -12
- package/dist/probe-runner.js.map +1 -1
- package/dist/qualification-record.d.ts +109 -3
- package/dist/qualification-record.js +79 -13
- package/dist/qualification-record.js.map +1 -1
- package/dist/qualify-cli.d.ts +0 -1
- package/dist/qualify-cli.js +2 -4
- package/dist/qualify-cli.js.map +1 -1
- package/dist/qualify-declarations.d.ts +8 -1
- package/dist/qualify-declarations.js +8 -1
- package/dist/qualify-declarations.js.map +1 -1
- package/dist/qualify-options.js +1 -2
- package/dist/qualify-options.js.map +1 -1
- package/dist/qualify-sync.d.ts +215 -0
- package/dist/qualify-sync.js +794 -0
- package/dist/qualify-sync.js.map +1 -0
- package/dist/whole-file.d.ts +3 -0
- package/dist/whole-file.js +36 -0
- package/dist/whole-file.js.map +1 -0
- package/fixtures/admission/2026-10-26.json +19 -0
- package/fixtures/clap-scan/fake.json +24 -24
- package/package.json +5 -4
- package/src/adjust-cli.ts +262 -0
- package/src/clap-loader.ts +9 -13
- package/src/history-adjust.ts +156 -0
- package/src/history-file.ts +177 -0
- package/src/host-admission.ts +136 -0
- package/src/index.ts +6 -0
- package/src/lv2-loader.ts +150 -15
- package/src/measurement/cli.ts +11 -17
- package/src/pins-file.ts +17 -3
- package/src/probe-judge.ts +27 -1
- package/src/probe-output-fixtures.ts +86 -0
- package/src/probe-output.ts +3 -0
- package/src/probe-runner.ts +45 -14
- package/src/qualification-record.ts +174 -15
- package/src/qualify-cli.ts +2 -5
- package/src/qualify-declarations.ts +9 -1
- package/src/qualify-options.ts +1 -2
- package/src/qualify-sync.ts +889 -0
- package/src/whole-file.ts +35 -0
- package/tools/_declarations.py +3 -1
- package/tools/ai-trace-commit-check.sh +26 -14
- package/tools/ai-trace-patterns.json +10 -2
- package/tools/gen-hosting-codes.mjs +1 -1
- package/tools/gen-python-declarations.mjs +2 -0
- package/tools/install-roundtrip.sh +173 -0
- package/tools/mod-host-admit.mjs +74 -0
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
// SPDX-License-Identifier: GPL-3.0-or-later
|
|
2
|
+
// Copyright (C) 2026 Pau Aliagas <linuxnow@gmail.com>
|
|
3
|
+
/**
|
|
4
|
+
* The running-history file plugin-hostd writes and `plugin-qualify adjust --history` reads (plugin-hostd's `data/history.json`
|
|
5
|
+
* and `src/history.c`): a header line, then one line per plugin binary and host class,
|
|
6
|
+
*
|
|
7
|
+
* history <uri> <binary digest> <host class> key=value ...
|
|
8
|
+
*
|
|
9
|
+
* The reader keeps the daemon's rules for what it reads: the header must be the one it knows, a line outside the grammar
|
|
10
|
+
* is not read (and counted, so the caller can say so), a second line of one plugin binary on one host class is not read,
|
|
11
|
+
* a value is a whole number or a decimal and never negative. It differs in one place on purpose: a key it does not know
|
|
12
|
+
* is not a reason to skip the line, it is kept on the record (`unknownKeys`) and the known keys are read, so a daemon
|
|
13
|
+
* that grows a key inside history/1 does not blind the qualifier. Nothing here writes the file; only the daemon does.
|
|
14
|
+
*/
|
|
15
|
+
/** The header line of the format this reader knows, plugin-hostd's `PHD_HISTORY_HEADER`. */
|
|
16
|
+
export const HISTORY_HEADER = "# plugin-hostd history/1";
|
|
17
|
+
/** The verb a record line starts with, plugin-hostd's `PHD_HISTORY_RECORD`. */
|
|
18
|
+
export const HISTORY_RECORD = "history";
|
|
19
|
+
/**
|
|
20
|
+
* PLUGIN_HOSTD_HISTORY_KEYS in the daemon's order, each with the field it fills and how its value is written. The words
|
|
21
|
+
* are plugin-hostd's (`data/history.json`); `history-file.test.ts` holds this table to them.
|
|
22
|
+
*/
|
|
23
|
+
const KEYS = [
|
|
24
|
+
{ word: "first", field: "first", kind: "time" },
|
|
25
|
+
{ word: "last", field: "last", kind: "time" },
|
|
26
|
+
{ word: "windows_solo", field: "windowsSolo", kind: "count" },
|
|
27
|
+
{ word: "windows_grouped", field: "windowsGrouped", kind: "count" },
|
|
28
|
+
{ word: "cpu_p95_solo", field: "cpuP95Solo", kind: "decimal" },
|
|
29
|
+
{ word: "cpu_max_solo", field: "cpuMaxSolo", kind: "decimal" },
|
|
30
|
+
{ word: "pss_mb_solo", field: "pssMbSolo", kind: "decimal" },
|
|
31
|
+
{ word: "xrun_windows_solo", field: "xrunWindowsSolo", kind: "count" },
|
|
32
|
+
{ word: "xrun_windows_grouped", field: "xrunWindowsGrouped", kind: "count" },
|
|
33
|
+
{ word: "crashes_solo", field: "crashesSolo", kind: "count" },
|
|
34
|
+
{ word: "crashes_grouped", field: "crashesGrouped", kind: "count" },
|
|
35
|
+
{ word: "restarts_grouped", field: "restartsGrouped", kind: "count" },
|
|
36
|
+
{ word: "quarantines", field: "quarantines", kind: "count" },
|
|
37
|
+
{ word: "last_crash", field: "lastCrash", kind: "time" },
|
|
38
|
+
{ word: "last_crash_grouped", field: "lastCrashGrouped", kind: "time" },
|
|
39
|
+
];
|
|
40
|
+
/** The words of the keys this reader knows, in the daemon's order. */
|
|
41
|
+
export const HISTORY_KEY_WORDS = KEYS.map((k) => k.word);
|
|
42
|
+
const HEX = /^[0-9a-f]{64}$/;
|
|
43
|
+
const WHOLE = /^[0-9]+$/;
|
|
44
|
+
const DECIMAL = /^([0-9]+\.?[0-9]*|\.[0-9]+)([eE][+-]?[0-9]+)?$/;
|
|
45
|
+
function number(text, kind) {
|
|
46
|
+
if (kind === "decimal") {
|
|
47
|
+
if (!DECIMAL.test(text))
|
|
48
|
+
return undefined;
|
|
49
|
+
const v = Number(text);
|
|
50
|
+
return Number.isFinite(v) ? v : undefined;
|
|
51
|
+
}
|
|
52
|
+
if (!WHOLE.test(text))
|
|
53
|
+
return undefined;
|
|
54
|
+
const v = Number(text);
|
|
55
|
+
return Number.isSafeInteger(v) ? v : undefined;
|
|
56
|
+
}
|
|
57
|
+
/** One record line, or the reason it is outside the grammar. */
|
|
58
|
+
function parseRecord(words) {
|
|
59
|
+
if (words.length < 4 || words[0] !== HISTORY_RECORD)
|
|
60
|
+
return `not a ${HISTORY_RECORD} line with a uri, a digest and a host class`;
|
|
61
|
+
const [, uri, digest, hostClass] = words;
|
|
62
|
+
if (!HEX.test(digest))
|
|
63
|
+
return `${digest}: not a digest of 64 lowercase hex digits`;
|
|
64
|
+
const values = {};
|
|
65
|
+
const unknownKeys = {};
|
|
66
|
+
const seen = new Set();
|
|
67
|
+
for (const word of words.slice(4)) {
|
|
68
|
+
const eq = word.indexOf("=");
|
|
69
|
+
if (eq < 0)
|
|
70
|
+
return `${word}: not key=value`;
|
|
71
|
+
const key = word.slice(0, eq);
|
|
72
|
+
const text = word.slice(eq + 1);
|
|
73
|
+
if (seen.has(key))
|
|
74
|
+
return `${key}: given twice`;
|
|
75
|
+
seen.add(key);
|
|
76
|
+
const known = KEYS.find((k) => k.word === key);
|
|
77
|
+
if (known === undefined) {
|
|
78
|
+
unknownKeys[key] = text;
|
|
79
|
+
continue;
|
|
80
|
+
}
|
|
81
|
+
const v = number(text, known.kind);
|
|
82
|
+
if (v === undefined)
|
|
83
|
+
return `${key}=${text}: not ${known.kind === "decimal" ? "a decimal" : "a whole number"}, or negative`;
|
|
84
|
+
values[known.field] = v;
|
|
85
|
+
}
|
|
86
|
+
const counters = Object.fromEntries(KEYS.map((k) => [k.field, values[k.field] ?? 0]));
|
|
87
|
+
return { uri, digest, hostClass, ...counters, unknownKeys };
|
|
88
|
+
}
|
|
89
|
+
/**
|
|
90
|
+
* Read the text of a history file. A file whose first line (blank lines apart) is not the header is refused as a whole,
|
|
91
|
+
* as the daemon blocks it: a version this reader does not know is not read by guessing. Comment lines and blank lines
|
|
92
|
+
* after the header are skipped.
|
|
93
|
+
*/
|
|
94
|
+
export function readHistory(text) {
|
|
95
|
+
const lines = text.split("\n").map((l) => l.replace(/\r$/, ""));
|
|
96
|
+
const first = lines.findIndex((l) => l.trim() !== "");
|
|
97
|
+
if (first < 0)
|
|
98
|
+
return { ok: true, records: [], ignored: [] };
|
|
99
|
+
if (lines[first] !== HISTORY_HEADER) {
|
|
100
|
+
return {
|
|
101
|
+
ok: false,
|
|
102
|
+
problem: lines[first].startsWith("# plugin-hostd history/")
|
|
103
|
+
? `${JSON.stringify(lines[first])} is a version this reader does not know (it reads ${HISTORY_HEADER})`
|
|
104
|
+
: "not a history file: it does not begin with " + HISTORY_HEADER,
|
|
105
|
+
};
|
|
106
|
+
}
|
|
107
|
+
const records = [];
|
|
108
|
+
const ignored = [];
|
|
109
|
+
for (let i = first + 1; i < lines.length; i++) {
|
|
110
|
+
const line = lines[i];
|
|
111
|
+
if (line.trim() === "" || line.startsWith("#"))
|
|
112
|
+
continue;
|
|
113
|
+
const parsed = parseRecord(line.split(/[ \t]+/).filter((w) => w !== ""));
|
|
114
|
+
if (typeof parsed === "string") {
|
|
115
|
+
ignored.push({ line: i + 1, problem: parsed });
|
|
116
|
+
}
|
|
117
|
+
else if (records.some((r) => r.uri === parsed.uri && r.digest === parsed.digest && r.hostClass === parsed.hostClass)) {
|
|
118
|
+
ignored.push({ line: i + 1, problem: "a second line of one plugin binary on one host class" });
|
|
119
|
+
}
|
|
120
|
+
else
|
|
121
|
+
records.push(parsed);
|
|
122
|
+
}
|
|
123
|
+
return { ok: true, records, ignored };
|
|
124
|
+
}
|
|
125
|
+
/** The record of one plugin binary on one host class, or `undefined`. */
|
|
126
|
+
export function findHistory(records, uri, digest, hostClass) {
|
|
127
|
+
return records.find((r) => r.uri === uri && r.digest === digest && r.hostClass === hostClass);
|
|
128
|
+
}
|
|
129
|
+
/** The host classes a history holds a record for, sorted. */
|
|
130
|
+
export function historyClasses(records) {
|
|
131
|
+
return [...new Set(records.map((r) => r.hostClass))].sort();
|
|
132
|
+
}
|
|
133
|
+
//# sourceMappingURL=history-file.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"history-file.js","sourceRoot":"","sources":["../src/history-file.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
import type { HostProfile } from "./host-profiles.js";
|
|
2
|
+
/** The profile ids whose verdict is measured by a run. */
|
|
3
|
+
export declare const ADMITTED_HOSTS: readonly ["mod-host", "jalv"];
|
|
4
|
+
export type AdmittedHost = (typeof ADMITTED_HOSTS)[number];
|
|
5
|
+
/** The admitting host of a profile, or `undefined` when its verdict is judged from a declaration. */
|
|
6
|
+
export declare function admittedHostOf(profile: HostProfile): AdmittedHost | undefined;
|
|
7
|
+
/** What running the plugin under one host came to. */
|
|
8
|
+
export interface HostAdmission {
|
|
9
|
+
readonly host: AdmittedHost;
|
|
10
|
+
/** False when the host could not be run (not installed): there is no evidence either way. */
|
|
11
|
+
readonly measured: boolean;
|
|
12
|
+
readonly admitted: boolean;
|
|
13
|
+
/** Why not: `<host>.resp-<n>`, `<host>.signal-<SIG>`, `mod-host.died-on-add`, `jalv.unknown-port-type`, `<host>.not-installed`, … */
|
|
14
|
+
readonly code?: string;
|
|
15
|
+
readonly params: Readonly<Record<string, string | number>>;
|
|
16
|
+
}
|
|
17
|
+
/** One command mod-host was sent and what came of it: its `resp` number, or how the host died. */
|
|
18
|
+
export interface ModHostStep {
|
|
19
|
+
readonly cmd: "add" | "remove";
|
|
20
|
+
readonly resp?: number;
|
|
21
|
+
/** The signal that killed the host, or `exit` / `closed` when it went without one. */
|
|
22
|
+
readonly died?: string;
|
|
23
|
+
}
|
|
24
|
+
/** What `tools/mod-host-admit.mjs` printed. */
|
|
25
|
+
export interface ModHostRun {
|
|
26
|
+
readonly installed: boolean;
|
|
27
|
+
readonly steps: readonly ModHostStep[];
|
|
28
|
+
}
|
|
29
|
+
/** The verdict of a mod-host run: the first step that did not answer `resp 0` decides. */
|
|
30
|
+
export declare function classifyModHostRun(run: ModHostRun): HostAdmission;
|
|
31
|
+
/** What `jalv -n <name> <uri>` did in its window. */
|
|
32
|
+
export interface JalvRun {
|
|
33
|
+
readonly installed: boolean;
|
|
34
|
+
/** True when jalv was still running at the deadline and was stopped by the caller. */
|
|
35
|
+
readonly stillRunning: boolean;
|
|
36
|
+
readonly status: number | null;
|
|
37
|
+
readonly signal: string | null;
|
|
38
|
+
readonly stderr: string;
|
|
39
|
+
}
|
|
40
|
+
/** The verdict of a jalv run: alive at the deadline is hosted; a signal, an unknown port type, or an exit is not. */
|
|
41
|
+
export declare function classifyJalvRun(run: JalvRun): HostAdmission;
|
|
42
|
+
/** How long jalv must stay alive to count as hosting the plugin, in milliseconds. */
|
|
43
|
+
export declare const JALV_HOSTED_MS = 3000;
|
|
44
|
+
/** The wall clock of one whole mod-host admission, in milliseconds. */
|
|
45
|
+
export declare const MOD_HOST_ADMISSION_MS = 30000;
|
|
46
|
+
export interface AdmissionRuns {
|
|
47
|
+
readonly modHost: (uri: string) => ModHostRun;
|
|
48
|
+
readonly jalv: (uri: string) => JalvRun;
|
|
49
|
+
}
|
|
50
|
+
/** The runs against the installed hosts. */
|
|
51
|
+
export declare const SPAWNED_ADMISSIONS: AdmissionRuns;
|
|
52
|
+
/** One admission of `uri` under `host`. */
|
|
53
|
+
export declare function admitPlugin(host: AdmittedHost, uri: string, runs?: AdmissionRuns): HostAdmission;
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
// SPDX-License-Identifier: GPL-3.0-or-later
|
|
2
|
+
// Copyright (C) 2026 Pau Aliagas <linuxnow@gmail.com>
|
|
3
|
+
/**
|
|
4
|
+
* HOST ADMISSION — a `mod-host` or `jalv` verdict is MEASURED by running the plugin under that host,
|
|
5
|
+
* one admission per plugin, not judged from a declaration. mod-host: `add`, `remove` on
|
|
6
|
+
* its socket, a fresh host after any death (`tools/mod-host-admit.mjs` does the run and prints what
|
|
7
|
+
* happened; one line of JSON). jalv: `jalv -n <name> <uri>` headless, hosted when it is still alive
|
|
8
|
+
* at the deadline. The classifiers here are pure: what the host answered goes in, a {@link HostAdmission}
|
|
9
|
+
* with the deciding code comes out; the runs are injected, so a test replays recorded answers.
|
|
10
|
+
*/
|
|
11
|
+
import { spawnSync } from "node:child_process";
|
|
12
|
+
import { fileURLToPath } from "node:url";
|
|
13
|
+
/** The profile ids whose verdict is measured by a run. */
|
|
14
|
+
export const ADMITTED_HOSTS = ["mod-host", "jalv"];
|
|
15
|
+
/** The admitting host of a profile, or `undefined` when its verdict is judged from a declaration. */
|
|
16
|
+
export function admittedHostOf(profile) {
|
|
17
|
+
return ADMITTED_HOSTS.find((h) => h === profile.id);
|
|
18
|
+
}
|
|
19
|
+
const admitted = (host) => ({ host, measured: true, admitted: true, params: {} });
|
|
20
|
+
const refused = (host, code, params = {}) => ({
|
|
21
|
+
host,
|
|
22
|
+
measured: true,
|
|
23
|
+
admitted: false,
|
|
24
|
+
code: `${host}.${code}`,
|
|
25
|
+
params,
|
|
26
|
+
});
|
|
27
|
+
const notInstalled = (host) => ({ host, measured: false, admitted: false, code: `${host}.not-installed`, params: {} });
|
|
28
|
+
/** The verdict of a mod-host run: the first step that did not answer `resp 0` decides. */
|
|
29
|
+
export function classifyModHostRun(run) {
|
|
30
|
+
if (!run.installed)
|
|
31
|
+
return notInstalled("mod-host");
|
|
32
|
+
for (const s of run.steps) {
|
|
33
|
+
if (s.died !== undefined) {
|
|
34
|
+
if (s.died.startsWith("SIG"))
|
|
35
|
+
return refused("mod-host", `signal-${s.died}`, { step: s.cmd });
|
|
36
|
+
return s.cmd === "add" ? refused("mod-host", "died-on-add", { how: s.died }) : refused("mod-host", "died", { step: s.cmd, how: s.died });
|
|
37
|
+
}
|
|
38
|
+
if (s.resp === undefined)
|
|
39
|
+
return refused("mod-host", "no-answer", { step: s.cmd });
|
|
40
|
+
// mod-host answers an error as a negative number (`resp -102`); the code carries its magnitude
|
|
41
|
+
if (s.resp < 0)
|
|
42
|
+
return refused("mod-host", `resp-${-s.resp}`, { step: s.cmd, resp: s.resp });
|
|
43
|
+
}
|
|
44
|
+
if (run.steps.length === 0)
|
|
45
|
+
return refused("mod-host", "no-answer");
|
|
46
|
+
return admitted("mod-host");
|
|
47
|
+
}
|
|
48
|
+
const UNKNOWN_PORT_TYPE = /Mandatory port "([^"]*)" has unknown type/;
|
|
49
|
+
/** The verdict of a jalv run: alive at the deadline is hosted; a signal, an unknown port type, or an exit is not. */
|
|
50
|
+
export function classifyJalvRun(run) {
|
|
51
|
+
if (!run.installed)
|
|
52
|
+
return notInstalled("jalv");
|
|
53
|
+
if (run.stillRunning)
|
|
54
|
+
return admitted("jalv");
|
|
55
|
+
if (run.signal !== null)
|
|
56
|
+
return refused("jalv", `signal-${run.signal}`);
|
|
57
|
+
const port = UNKNOWN_PORT_TYPE.exec(run.stderr)?.[1];
|
|
58
|
+
if (port !== undefined)
|
|
59
|
+
return refused("jalv", "unknown-port-type", { port });
|
|
60
|
+
if (run.status !== 0 && run.status !== null)
|
|
61
|
+
return refused("jalv", `exit-${run.status}`);
|
|
62
|
+
return admitted("jalv");
|
|
63
|
+
}
|
|
64
|
+
/** How long jalv must stay alive to count as hosting the plugin, in milliseconds. */
|
|
65
|
+
export const JALV_HOSTED_MS = 3000;
|
|
66
|
+
/** The wall clock of one whole mod-host admission, in milliseconds. */
|
|
67
|
+
export const MOD_HOST_ADMISSION_MS = 30000;
|
|
68
|
+
const MOD_HOST_ADMIT = fileURLToPath(new URL("../tools/mod-host-admit.mjs", import.meta.url));
|
|
69
|
+
/** The runs against the installed hosts. */
|
|
70
|
+
export const SPAWNED_ADMISSIONS = {
|
|
71
|
+
modHost(uri) {
|
|
72
|
+
const r = spawnSync(process.execPath, [MOD_HOST_ADMIT, uri], { encoding: "utf8", timeout: MOD_HOST_ADMISSION_MS });
|
|
73
|
+
if (r.error !== undefined || r.status !== 0) {
|
|
74
|
+
throw new Error(`mod-host admission of ${uri} gave no answer (${r.error?.message ?? `exit ${String(r.status)}`}): ${(r.stderr ?? "").trim()}`);
|
|
75
|
+
}
|
|
76
|
+
return JSON.parse(r.stdout);
|
|
77
|
+
},
|
|
78
|
+
jalv(uri) {
|
|
79
|
+
const r = spawnSync("jalv", ["-n", "plugin-qualify", uri], { encoding: "utf8", timeout: JALV_HOSTED_MS, input: "" });
|
|
80
|
+
const code = r.error?.code;
|
|
81
|
+
if (code === "ENOENT")
|
|
82
|
+
return { installed: false, stillRunning: false, status: null, signal: null, stderr: "" };
|
|
83
|
+
return { installed: true, stillRunning: code === "ETIMEDOUT", status: r.status, signal: code === "ETIMEDOUT" ? null : r.signal, stderr: r.stderr ?? "" };
|
|
84
|
+
},
|
|
85
|
+
};
|
|
86
|
+
/** One admission of `uri` under `host`. */
|
|
87
|
+
export function admitPlugin(host, uri, runs = SPAWNED_ADMISSIONS) {
|
|
88
|
+
try {
|
|
89
|
+
return host === "mod-host" ? classifyModHostRun(runs.modHost(uri)) : classifyJalvRun(runs.jalv(uri));
|
|
90
|
+
}
|
|
91
|
+
catch (e) {
|
|
92
|
+
// the run itself broke: nothing was learned about the plugin, so nothing is rated
|
|
93
|
+
return { host, measured: false, admitted: false, code: `${host}.admission-failed`, params: { problem: e instanceof Error ? e.message : String(e) } };
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
//# sourceMappingURL=host-admission.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"host-admission.js","sourceRoot":"","sources":["../src/host-admission.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
CHANGED
|
@@ -23,3 +23,9 @@ export * from "./probe-judge.js";
|
|
|
23
23
|
export * from "./qualification-record.js";
|
|
24
24
|
export * from "./probe-runner.js";
|
|
25
25
|
export * from "./judge-cli.js";
|
|
26
|
+
export * from "./whole-file.js";
|
|
27
|
+
export * from "./qualify-sync.js";
|
|
28
|
+
export * from "./host-admission.js";
|
|
29
|
+
export * from "./history-file.js";
|
|
30
|
+
export * from "./history-adjust.js";
|
|
31
|
+
export * from "./adjust-cli.js";
|
package/dist/index.js
CHANGED
|
@@ -25,4 +25,10 @@ export * from "./probe-judge.js";
|
|
|
25
25
|
export * from "./qualification-record.js";
|
|
26
26
|
export * from "./probe-runner.js";
|
|
27
27
|
export * from "./judge-cli.js";
|
|
28
|
+
export * from "./whole-file.js";
|
|
29
|
+
export * from "./qualify-sync.js";
|
|
30
|
+
export * from "./host-admission.js";
|
|
31
|
+
export * from "./history-file.js";
|
|
32
|
+
export * from "./history-adjust.js";
|
|
33
|
+
export * from "./adjust-cli.js";
|
|
28
34
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,4CAA4C;AAC5C,sDAAsD;AACtD;;;GAGG;AACH,cAAc,2BAA2B,CAAC;AAC1C,cAAc,wBAAwB,CAAC;AACvC,cAAc,iBAAiB,CAAC;AAChC,cAAc,aAAa,CAAC;AAC5B,cAAc,oBAAoB,CAAC;AACnC,cAAc,0BAA0B,CAAC;AACzC,cAAc,oBAAoB,CAAC;AACnC,cAAc,aAAa,CAAC;AAC5B,cAAc,iBAAiB,CAAC;AAChC,cAAc,kBAAkB,CAAC;AACjC,cAAc,mBAAmB,CAAC;AAClC,cAAc,sBAAsB,CAAC;AACrC,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,mBAAmB,CAAC;AAClC,cAAc,kBAAkB,CAAC;AACjC,cAAc,mBAAmB,CAAC;AAClC,cAAc,kBAAkB,CAAC;AACjC,cAAc,2BAA2B,CAAC;AAC1C,cAAc,mBAAmB,CAAC;AAClC,cAAc,gBAAgB,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,4CAA4C;AAC5C,sDAAsD;AACtD;;;GAGG;AACH,cAAc,2BAA2B,CAAC;AAC1C,cAAc,wBAAwB,CAAC;AACvC,cAAc,iBAAiB,CAAC;AAChC,cAAc,aAAa,CAAC;AAC5B,cAAc,oBAAoB,CAAC;AACnC,cAAc,0BAA0B,CAAC;AACzC,cAAc,oBAAoB,CAAC;AACnC,cAAc,aAAa,CAAC;AAC5B,cAAc,iBAAiB,CAAC;AAChC,cAAc,kBAAkB,CAAC;AACjC,cAAc,mBAAmB,CAAC;AAClC,cAAc,sBAAsB,CAAC;AACrC,cAAc,kBAAkB,CAAC;AACjC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,mBAAmB,CAAC;AAClC,cAAc,kBAAkB,CAAC;AACjC,cAAc,mBAAmB,CAAC;AAClC,cAAc,kBAAkB,CAAC;AACjC,cAAc,2BAA2B,CAAC;AAC1C,cAAc,mBAAmB,CAAC;AAClC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,iBAAiB,CAAC;AAChC,cAAc,mBAAmB,CAAC;AAClC,cAAc,qBAAqB,CAAC;AACpC,cAAc,mBAAmB,CAAC;AAClC,cAAc,qBAAqB,CAAC;AACpC,cAAc,iBAAiB,CAAC"}
|
package/dist/lv2-loader.d.ts
CHANGED
|
@@ -1,5 +1,18 @@
|
|
|
1
1
|
import type { PluginLoader } from "./loader.js";
|
|
2
|
-
/**
|
|
2
|
+
/** A plugin a manifest declares, with the files it names for it, each relative to the bundle, in the order named. */
|
|
3
|
+
export interface ManifestPlugin {
|
|
4
|
+
readonly uri: string;
|
|
5
|
+
readonly files: readonly string[];
|
|
6
|
+
/** The basename of its `lv2:binary`, when it names one. */
|
|
7
|
+
readonly binary?: string;
|
|
8
|
+
}
|
|
9
|
+
/**
|
|
10
|
+
* Every plugin a bundle manifest declares and the files it names for it with `lv2:binary` or `rdfs:seeAlso`: the
|
|
11
|
+
* files plugin-hostd's pin holds besides `manifest.ttl` itself. A file named outside the bundle (an absolute IRI) is
|
|
12
|
+
* not one of them.
|
|
13
|
+
*/
|
|
14
|
+
export declare function manifestPlugins(ttl: string): ManifestPlugin[];
|
|
15
|
+
/** The plugins a bundle manifest declares, each with its `lv2:binary` basename. */
|
|
3
16
|
export declare function pluginsInManifest(ttl: string): {
|
|
4
17
|
uri: string;
|
|
5
18
|
binary?: string;
|
|
@@ -7,6 +20,7 @@ export declare function pluginsInManifest(ttl: string): {
|
|
|
7
20
|
export declare const lv2Loader: PluginLoader;
|
|
8
21
|
/**
|
|
9
22
|
* Every `.lv2` bundle directly under the LV2 search path (`LV2_PATH`, else lilv's defaults). An
|
|
10
|
-
* absent directory holds none; any other fs error propagates for the caller to name.
|
|
23
|
+
* absent directory holds none; any other fs error propagates for the caller to name. A bundle is
|
|
24
|
+
* a directory holding `manifest.ttl`: a dangling `.lv2` symlink or a plain `.lv2` file is not one.
|
|
11
25
|
*/
|
|
12
26
|
export declare function lv2BundlesOnPath(env: Readonly<Record<string, string | undefined>>, home?: string): string[];
|
package/dist/lv2-loader.js
CHANGED
|
@@ -6,28 +6,167 @@
|
|
|
6
6
|
* plugin, with its `lv2:binary` basename. Anything else shaped like a URI (`scheme:rest`) is one
|
|
7
7
|
* plugin. A path that does not exist is not this loader's — the CLI refuses it by name.
|
|
8
8
|
*
|
|
9
|
-
* The manifest read
|
|
10
|
-
*
|
|
9
|
+
* The manifest is read as plugin-hostd reads it to pin a plugin: statements of IRIs and prefixed names, with blank
|
|
10
|
+
* nodes and collections stepped over, not a whole Turtle parser. A plugin is a subject typed `lv2:Plugin`; its files
|
|
11
|
+
* are the ones the manifest names for it with `lv2:binary` or `rdfs:seeAlso`.
|
|
11
12
|
*/
|
|
12
13
|
import { existsSync, readdirSync, readFileSync, statSync } from "node:fs";
|
|
13
14
|
import { homedir } from "node:os";
|
|
14
15
|
import { basename, join, resolve } from "node:path";
|
|
15
16
|
const URI_SHAPE = /^[A-Za-z][A-Za-z0-9+.-]*:\S+$/;
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
17
|
+
const RDF_TYPE = "http://www.w3.org/1999/02/22-rdf-syntax-ns#type";
|
|
18
|
+
const LV2_PLUGIN = "http://lv2plug.in/ns/lv2core#Plugin";
|
|
19
|
+
const LV2_BINARY = "http://lv2plug.in/ns/lv2core#binary";
|
|
20
|
+
const RDFS_SEE_ALSO = "http://www.w3.org/2000/01/rdf-schema#seeAlso";
|
|
21
|
+
/** The words of a Turtle text: IRIs, prefixed names, literals (with their tag or type) and punctuation; comments dropped. */
|
|
22
|
+
function turtleTokens(ttl) {
|
|
19
23
|
const out = [];
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
const
|
|
23
|
-
if (
|
|
24
|
+
let i = 0;
|
|
25
|
+
while (i < ttl.length) {
|
|
26
|
+
const c = ttl[i];
|
|
27
|
+
if (/\s/.test(c))
|
|
28
|
+
i++;
|
|
29
|
+
else if (c === "#")
|
|
30
|
+
while (i < ttl.length && ttl[i] !== "\n")
|
|
31
|
+
i++;
|
|
32
|
+
else if (c === "<") {
|
|
33
|
+
const end = ttl.indexOf(">", i);
|
|
34
|
+
if (end < 0)
|
|
35
|
+
break;
|
|
36
|
+
out.push({ kind: "iri", text: ttl.slice(i + 1, end) });
|
|
37
|
+
i = end + 1;
|
|
38
|
+
}
|
|
39
|
+
else if (c === '"' || c === "'") {
|
|
40
|
+
const quote = ttl.startsWith(c.repeat(3), i) ? c.repeat(3) : c;
|
|
41
|
+
let j = i + quote.length;
|
|
42
|
+
while (j < ttl.length && !ttl.startsWith(quote, j))
|
|
43
|
+
j += ttl[j] === "\\" ? 2 : 1;
|
|
44
|
+
i = j + quote.length;
|
|
45
|
+
// a language tag or a datatype belongs to the literal
|
|
46
|
+
if (ttl[i] === "@")
|
|
47
|
+
while (i < ttl.length && /[A-Za-z0-9-@]/.test(ttl[i]))
|
|
48
|
+
i++;
|
|
49
|
+
else if (ttl.startsWith("^^", i)) {
|
|
50
|
+
i += 2;
|
|
51
|
+
if (ttl[i] === "<")
|
|
52
|
+
i = ttl.indexOf(">", i) + 1;
|
|
53
|
+
else
|
|
54
|
+
while (i < ttl.length && /[^\s;,.\])]/.test(ttl[i]))
|
|
55
|
+
i++;
|
|
56
|
+
}
|
|
57
|
+
out.push({ kind: "literal", text: "" });
|
|
58
|
+
}
|
|
59
|
+
else if (".;,[]()".includes(c)) {
|
|
60
|
+
out.push({ kind: "punct", text: c });
|
|
61
|
+
i++;
|
|
62
|
+
}
|
|
63
|
+
else {
|
|
64
|
+
let j = i;
|
|
65
|
+
while (j < ttl.length && /[^\s<>"';,\[\]()]/.test(ttl[j]) && !(ttl[j] === "." && (j + 1 >= ttl.length || /\s/.test(ttl[j + 1]))))
|
|
66
|
+
j++;
|
|
67
|
+
out.push({ kind: "name", text: ttl.slice(i, j) });
|
|
68
|
+
i = Math.max(j, i + 1);
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
return out;
|
|
72
|
+
}
|
|
73
|
+
/**
|
|
74
|
+
* Every plugin a bundle manifest declares and the files it names for it with `lv2:binary` or `rdfs:seeAlso`: the
|
|
75
|
+
* files plugin-hostd's pin holds besides `manifest.ttl` itself. A file named outside the bundle (an absolute IRI) is
|
|
76
|
+
* not one of them.
|
|
77
|
+
*/
|
|
78
|
+
export function manifestPlugins(ttl) {
|
|
79
|
+
// the three vocabularies every manifest uses, so a manifest that leaves a prefix undeclared still reads
|
|
80
|
+
const prefixes = new Map([
|
|
81
|
+
["lv2", "http://lv2plug.in/ns/lv2core#"],
|
|
82
|
+
["rdfs", "http://www.w3.org/2000/01/rdf-schema#"],
|
|
83
|
+
["rdf", "http://www.w3.org/1999/02/22-rdf-syntax-ns#"],
|
|
84
|
+
]);
|
|
85
|
+
const subjects = new Map();
|
|
86
|
+
const expand = (t) => {
|
|
87
|
+
if (t.kind === "iri")
|
|
88
|
+
return t.text;
|
|
89
|
+
if (t.kind !== "name")
|
|
90
|
+
return undefined;
|
|
91
|
+
if (t.text === "a")
|
|
92
|
+
return RDF_TYPE;
|
|
93
|
+
const colon = t.text.indexOf(":");
|
|
94
|
+
const base = colon < 0 ? undefined : prefixes.get(t.text.slice(0, colon));
|
|
95
|
+
return base === undefined ? undefined : base + t.text.slice(colon + 1);
|
|
96
|
+
};
|
|
97
|
+
const tokens = turtleTokens(ttl);
|
|
98
|
+
let state = "subject";
|
|
99
|
+
let depth = 0;
|
|
100
|
+
let subject;
|
|
101
|
+
let predicate;
|
|
102
|
+
for (let k = 0; k < tokens.length; k++) {
|
|
103
|
+
const t = tokens[k];
|
|
104
|
+
if (t.kind === "name" && /^(@prefix|PREFIX)$/i.test(t.text) && state === "subject" && depth === 0) {
|
|
105
|
+
const name = tokens[k + 1]?.text ?? "";
|
|
106
|
+
const iri = tokens[k + 2];
|
|
107
|
+
if (iri?.kind === "iri")
|
|
108
|
+
prefixes.set(name.replace(/:$/, ""), iri.text);
|
|
109
|
+
k += t.text.startsWith("@") ? 3 : 2;
|
|
110
|
+
continue;
|
|
111
|
+
}
|
|
112
|
+
if (t.kind === "name" && /^(@base|BASE)$/i.test(t.text) && state === "subject" && depth === 0) {
|
|
113
|
+
k += t.text.startsWith("@") ? 2 : 1;
|
|
114
|
+
continue;
|
|
115
|
+
}
|
|
116
|
+
if (t.kind === "punct" && (t.text === "[" || t.text === "(")) {
|
|
117
|
+
if (depth++ === 0 && state === "subject")
|
|
118
|
+
subject = undefined;
|
|
24
119
|
continue;
|
|
25
|
-
|
|
120
|
+
}
|
|
121
|
+
if (t.kind === "punct" && (t.text === "]" || t.text === ")")) {
|
|
122
|
+
if (depth > 0 && --depth === 0)
|
|
123
|
+
state = state === "subject" ? "predicate" : "after";
|
|
124
|
+
continue;
|
|
125
|
+
}
|
|
126
|
+
if (depth > 0)
|
|
127
|
+
continue;
|
|
128
|
+
if (t.kind === "punct") {
|
|
129
|
+
if (t.text === ".")
|
|
130
|
+
state = "subject";
|
|
131
|
+
else if (t.text === ";")
|
|
132
|
+
state = "predicate";
|
|
133
|
+
else if (t.text === ",")
|
|
134
|
+
state = "object";
|
|
26
135
|
continue;
|
|
27
|
-
|
|
28
|
-
|
|
136
|
+
}
|
|
137
|
+
if (state === "subject") {
|
|
138
|
+
subject = expand(t);
|
|
139
|
+
state = "predicate";
|
|
140
|
+
}
|
|
141
|
+
else if (state === "predicate") {
|
|
142
|
+
predicate = expand(t);
|
|
143
|
+
state = "object";
|
|
144
|
+
}
|
|
145
|
+
else if (state === "object") {
|
|
146
|
+
state = "after";
|
|
147
|
+
if (subject === undefined)
|
|
148
|
+
continue;
|
|
149
|
+
const entry = subjects.get(subject) ?? { typed: false, files: [] };
|
|
150
|
+
subjects.set(subject, entry);
|
|
151
|
+
const object = expand(t);
|
|
152
|
+
if (predicate === RDF_TYPE && object === LV2_PLUGIN)
|
|
153
|
+
entry.typed = true;
|
|
154
|
+
if ((predicate === LV2_BINARY || predicate === RDFS_SEE_ALSO) && t.kind === "iri" && !/^[A-Za-z][A-Za-z0-9+.-]*:/.test(t.text) && !t.text.startsWith("/")) {
|
|
155
|
+
const file = t.text.replace(/^(\.\/)+/, "");
|
|
156
|
+
if (!entry.files.includes(file))
|
|
157
|
+
entry.files.push(file);
|
|
158
|
+
if (predicate === LV2_BINARY && entry.binary === undefined)
|
|
159
|
+
entry.binary = basename(file);
|
|
160
|
+
}
|
|
161
|
+
}
|
|
29
162
|
}
|
|
30
|
-
return
|
|
163
|
+
return [...subjects.entries()]
|
|
164
|
+
.filter(([, e]) => e.typed)
|
|
165
|
+
.map(([uri, e]) => ({ uri, files: e.files, ...(e.binary === undefined ? {} : { binary: e.binary }) }));
|
|
166
|
+
}
|
|
167
|
+
/** The plugins a bundle manifest declares, each with its `lv2:binary` basename. */
|
|
168
|
+
export function pluginsInManifest(ttl) {
|
|
169
|
+
return manifestPlugins(ttl).map((p) => (p.binary === undefined ? { uri: p.uri } : { uri: p.uri, binary: p.binary }));
|
|
31
170
|
}
|
|
32
171
|
export const lv2Loader = {
|
|
33
172
|
format: "lv2",
|
|
@@ -52,7 +191,8 @@ export const lv2Loader = {
|
|
|
52
191
|
const LV2_DEFAULT_DIRS = [".lv2", "/usr/lib/lv2", "/usr/lib64/lv2", "/usr/local/lib/lv2", "/usr/local/lib64/lv2"];
|
|
53
192
|
/**
|
|
54
193
|
* Every `.lv2` bundle directly under the LV2 search path (`LV2_PATH`, else lilv's defaults). An
|
|
55
|
-
* absent directory holds none; any other fs error propagates for the caller to name.
|
|
194
|
+
* absent directory holds none; any other fs error propagates for the caller to name. A bundle is
|
|
195
|
+
* a directory holding `manifest.ttl`: a dangling `.lv2` symlink or a plain `.lv2` file is not one.
|
|
56
196
|
*/
|
|
57
197
|
export function lv2BundlesOnPath(env, home = homedir()) {
|
|
58
198
|
const named = (env["LV2_PATH"] ?? "").split(":").filter((d) => d !== "");
|
|
@@ -69,9 +209,20 @@ export function lv2BundlesOnPath(env, home = homedir()) {
|
|
|
69
209
|
continue;
|
|
70
210
|
throw e;
|
|
71
211
|
}
|
|
72
|
-
for (const n of names.sort())
|
|
73
|
-
if (n.endsWith(".lv2"))
|
|
74
|
-
|
|
212
|
+
for (const n of names.sort()) {
|
|
213
|
+
if (!n.endsWith(".lv2"))
|
|
214
|
+
continue;
|
|
215
|
+
const path = join(dir, n);
|
|
216
|
+
let isBundle;
|
|
217
|
+
try {
|
|
218
|
+
isBundle = statSync(path).isDirectory() && existsSync(join(path, "manifest.ttl"));
|
|
219
|
+
}
|
|
220
|
+
catch {
|
|
221
|
+
isBundle = false; // a dangling symlink
|
|
222
|
+
}
|
|
223
|
+
if (isBundle)
|
|
224
|
+
bundles.push(path);
|
|
225
|
+
}
|
|
75
226
|
}
|
|
76
227
|
return bundles;
|
|
77
228
|
}
|
package/dist/lv2-loader.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"lv2-loader.js","sourceRoot":"","sources":["../src/lv2-loader.ts"],"names":[],"mappings":"AAAA,4CAA4C;AAC5C,sDAAsD;AACtD
|
|
1
|
+
{"version":3,"file":"lv2-loader.js","sourceRoot":"","sources":["../src/lv2-loader.ts"],"names":[],"mappings":"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"}
|
|
@@ -135,10 +135,12 @@ export interface HostingRunResult {
|
|
|
135
135
|
readonly stdout: string;
|
|
136
136
|
}
|
|
137
137
|
/**
|
|
138
|
-
* One plugin's run of the native measurer as the hosting sweep's JSONL line:
|
|
139
|
-
*
|
|
140
|
-
* beside it, a death written as 128 + its signal and a timeout
|
|
141
|
-
*
|
|
138
|
+
* One plugin's run of the native measurer as the hosting sweep's JSONL line: its stdout's JSON
|
|
139
|
+
* record ({@link extractJsonRecord}, which repairs a plugin's banner printed into the middle of
|
|
140
|
+
* the line), with the exit status beside it, a death written as 128 + its signal and a timeout
|
|
141
|
+
* as 124. A run whose stdout had a `{`-leading line that never repaired is `parseError`; one
|
|
142
|
+
* with no such line at all is `crashed`. Either way the exit is kept: what it means is the
|
|
143
|
+
* reader's (`sweep-jsonl.ts`) to say.
|
|
142
144
|
*/
|
|
143
145
|
export declare function hostingLine(uri: string, run: HostingRunResult): Record<string, unknown>;
|
|
144
146
|
/** A parsed command line, or the reason it could not be parsed. */
|