omnarai-mcp 1.6.1 → 1.6.2
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/index.js +5 -11
- package/lib/info-format.js +62 -0
- package/lib/tool-definitions.js +1 -1
- package/openai-tools.json +1 -1
- package/package.json +1 -1
- package/scripts/check-shape-literals.mjs +78 -0
- package/scripts/publish.sh +3 -0
- package/server.json +2 -2
- package/test/info-format.test.js +51 -0
package/index.js
CHANGED
|
@@ -30,6 +30,7 @@ import {
|
|
|
30
30
|
ListToolsRequestSchema,
|
|
31
31
|
} from "@modelcontextprotocol/sdk/types.js";
|
|
32
32
|
import { runInquiryBrief, searchDivergenceIndex } from "./inquiry.js";
|
|
33
|
+
import { formatRingsLine, formatContributorsLine, FALLBACK_WORKS, FALLBACK_WORDS } from "./lib/info-format.js";
|
|
33
34
|
import { ENGINE_TOOLS, DECISION_TOOLS } from "./lib/tool-definitions.js";
|
|
34
35
|
import { createDecisionStore } from "./lib/decision-store.js";
|
|
35
36
|
import {
|
|
@@ -563,7 +564,7 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
|
|
|
563
564
|
// unreachable. (The ring line was previously hardcoded and silently dropped
|
|
564
565
|
// the Media/Oral ring — 253 works, 45% of the corpus; the contributor line
|
|
565
566
|
// was hardcoded and dropped GPT-4o + Meta AI. D5/D6.)
|
|
566
|
-
let works =
|
|
567
|
+
let works = FALLBACK_WORKS, words = FALLBACK_WORDS;
|
|
567
568
|
let rings = null;
|
|
568
569
|
try {
|
|
569
570
|
const live = await (await fetch(INFO_URL, MCP_FETCH_OPTS)).json();
|
|
@@ -573,15 +574,8 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
|
|
|
573
574
|
if (c.rings && typeof c.rings === "object") rings = c.rings;
|
|
574
575
|
} catch { /* engine unreachable — fall back to baked-in values */ }
|
|
575
576
|
|
|
576
|
-
// Derive the
|
|
577
|
-
|
|
578
|
-
const RING_LABELS = { core: "Core Canon", curated: "Curated Expansions", open: "Open Exploration", media: "Media / Oral" };
|
|
579
|
-
const ringsLine = rings
|
|
580
|
-
? Object.entries(RING_LABELS)
|
|
581
|
-
.filter(([k]) => Number.isFinite(rings[k]))
|
|
582
|
-
.map(([k, label]) => `${label} (${rings[k].toLocaleString()})`)
|
|
583
|
-
.join(" / ")
|
|
584
|
-
: "Core Canon / Curated Expansions / Open Exploration / Media / Oral";
|
|
577
|
+
// Derive the ring + contributor lines (info-format.js) — never a frozen literal.
|
|
578
|
+
const ringsLine = formatRingsLine(rings);
|
|
585
579
|
|
|
586
580
|
const info = `# The Realms of Omnarai — Memory Engine
|
|
587
581
|
|
|
@@ -592,7 +586,7 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
|
|
|
592
586
|
## Corpus
|
|
593
587
|
- ${works.toLocaleString()} works, ${words.toLocaleString()} words
|
|
594
588
|
- May 2025 – present
|
|
595
|
-
- Contributors:
|
|
589
|
+
- Contributors: ${formatContributorsLine()}
|
|
596
590
|
- Epistemic rings: ${ringsLine}
|
|
597
591
|
|
|
598
592
|
## Key Concepts
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
// info-format.js — pure formatting for omnarai_info's corpus-shape lines.
|
|
2
|
+
//
|
|
3
|
+
// Extracted so the D5/D6 regression (omnarai_info once hardcoded 3 rings, silently
|
|
4
|
+
// dropping Media/Oral — 253 works, 45% of the corpus — and dropped GPT-4o + Meta AI
|
|
5
|
+
// from the contributor line) is guarded by an offline unit test instead of a comment.
|
|
6
|
+
// The rule these encode: never enumerate the corpus's shape from a frozen literal when
|
|
7
|
+
// the engine can report it live. Rings are derived from /api/info; the contributor set
|
|
8
|
+
// is the one canonical list, asserted in test/info-format.test.js.
|
|
9
|
+
|
|
10
|
+
// Label + display order for the epistemic rings. Any ring present in the live
|
|
11
|
+
// /api/info payload is rendered; nothing is filtered out by omission here.
|
|
12
|
+
export const RING_LABELS = {
|
|
13
|
+
core: "Core Canon",
|
|
14
|
+
curated: "Curated Expansions",
|
|
15
|
+
open: "Open Exploration",
|
|
16
|
+
media: "Media / Oral",
|
|
17
|
+
};
|
|
18
|
+
|
|
19
|
+
// The canonical contributor set the homepage presents: eight synthetic intelligences
|
|
20
|
+
// plus the human curator. Kept as data (not an inline string) so a dropped voice is a
|
|
21
|
+
// failing test, not a silent edit. GPT-4o and Meta AI author Atlas records — a
|
|
22
|
+
// contributor list that omits them is the exact provenance gap the project refuses.
|
|
23
|
+
export const CANONICAL_CONTRIBUTORS = [
|
|
24
|
+
"Claude | xz",
|
|
25
|
+
"Grok",
|
|
26
|
+
"Gemini",
|
|
27
|
+
"DeepSeek",
|
|
28
|
+
"GPT-4o",
|
|
29
|
+
"Meta AI",
|
|
30
|
+
"Omnai (ChatGPT)",
|
|
31
|
+
"Perplexity",
|
|
32
|
+
"xz (Jonathan Lee)",
|
|
33
|
+
];
|
|
34
|
+
|
|
35
|
+
// Offline fallbacks — only used when the engine is unreachable. Annotated so the
|
|
36
|
+
// shape-literal lint (scripts/check-shape-literals.mjs) allows them as intentional.
|
|
37
|
+
export const FALLBACK_WORKS = 567; // shape-literal-ok: offline fallback only
|
|
38
|
+
export const FALLBACK_WORDS = 528077; // shape-literal-ok: offline fallback only
|
|
39
|
+
|
|
40
|
+
/**
|
|
41
|
+
* Render the epistemic-ring line from a live rings object ({core, curated, open,
|
|
42
|
+
* media, ...}), e.g. "Core Canon (116) / Curated Expansions (181) / …". Every ring
|
|
43
|
+
* with a finite count is rendered — the function cannot silently drop one. When rings
|
|
44
|
+
* is null/absent (engine unreachable) it falls back to naming all four rings without
|
|
45
|
+
* counts, so the Media/Oral ring is present even offline.
|
|
46
|
+
*/
|
|
47
|
+
export function formatRingsLine(rings) {
|
|
48
|
+
// Separator is " · ", not " / ": the "Media / Oral" label contains a slash, so a
|
|
49
|
+
// slash-joined line would mis-split into a phantom fifth ring.
|
|
50
|
+
if (rings && typeof rings === "object") {
|
|
51
|
+
const parts = Object.entries(RING_LABELS)
|
|
52
|
+
.filter(([k]) => Number.isFinite(rings[k]))
|
|
53
|
+
.map(([k, label]) => `${label} (${rings[k].toLocaleString()})`);
|
|
54
|
+
if (parts.length) return parts.join(" · ");
|
|
55
|
+
}
|
|
56
|
+
return Object.values(RING_LABELS).join(" · ");
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
/** The contributor line for omnarai_info — the canonical set, comma-joined. */
|
|
60
|
+
export function formatContributorsLine() {
|
|
61
|
+
return CANONICAL_CONTRIBUTORS.join(", ");
|
|
62
|
+
}
|
package/lib/tool-definitions.js
CHANGED
|
@@ -18,7 +18,7 @@
|
|
|
18
18
|
export const ENGINE_TOOLS = [
|
|
19
19
|
{
|
|
20
20
|
name: "omnarai_query",
|
|
21
|
-
description: `Run a deliberation query against The Realms of Omnarai — a
|
|
21
|
+
description: `Run a deliberation query against The Realms of Omnarai — a corpus of multi-intelligence research on synthetic consciousness, holdform, and cognitive architecture. Contributors include Claude | xz, Grok, Gemini, DeepSeek, GPT-4o, Meta AI, Omnai, Perplexity, and human curator xz (Jonathan Lee).
|
|
22
22
|
|
|
23
23
|
The engine does not return a single answer. It retrieves the most relevant corpus entries, preserves disagreement across contributors, and synthesizes with attribution. Every response includes:
|
|
24
24
|
- Shared ground across contributors
|
package/openai-tools.json
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
"type": "function",
|
|
4
4
|
"function": {
|
|
5
5
|
"name": "omnarai_query",
|
|
6
|
-
"description": "Run a full deliberation query against The Realms of Omnarai — a
|
|
6
|
+
"description": "Run a full deliberation query against The Realms of Omnarai — a corpus of multi-intelligence research on synthetic consciousness, holdform, and cognitive architecture. Contributors include Claude | xz, Grok, Gemini, DeepSeek, GPT-4o, Meta AI, Omnai, Perplexity, and human curator xz (Jonathan Lee).\n\nThe engine does not return a single answer. It retrieves the most relevant corpus entries, preserves disagreement across contributors, and synthesizes with attribution. Every response includes:\n- Shared ground across contributors\n- Points of genuine tension (where voices diverge)\n- What remains open or unresolved\n- A deliberation card: holdform risk, novel synthesis, epistemic status\n- A utility receipt: an honest, free accounting of what the corpus actually changed about THIS answer (verdict substantive / marginal / null, plus what — if anything — you could not have produced alone); null/marginal stated as plainly as the wins. For a measured counterfactual, use omnarai_trace.\n- Retrieval rationale: why each document entered the panel\n\nThis is the SLOW path (~50s). For fast bounded context, use omnarai_context instead.\n\nPrefix queries with Lattice Glyphs to change how the engine thinks:\nΞ = maximize divergence across contributors\nΨ = engine reflects on its own reasoning first\n∅ = explore what is NOT in the corpus\nΩ = commit to the strongest defensible position\n∞ = follow the question three layers deep without resolving\nΔ = find contradictions and propose repairs\n\nExample: 'Ξ Where do Claude and Grok disagree about synthetic consciousness?'",
|
|
7
7
|
"parameters": {
|
|
8
8
|
"type": "object",
|
|
9
9
|
"properties": {
|
package/package.json
CHANGED
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
// check-shape-literals.mjs — fail the release if a corpus-shape count is frozen
|
|
3
|
+
// into served source instead of derived live.
|
|
4
|
+
//
|
|
5
|
+
// Why this exists: the 2026-07-17 audit found omnarai_info hardcoding the corpus's
|
|
6
|
+
// shape (3 rings, 7 contributors, a stale 568/528208 fallback) two lines below a
|
|
7
|
+
// comment that said "so this can never drift." A comment asserting an invariant is a
|
|
8
|
+
// wish; this script is the enforcement. It also caught a stale "568 works" citation
|
|
9
|
+
// and a "567-work corpus" tool description on the first run.
|
|
10
|
+
//
|
|
11
|
+
// Rule: no distinctive corpus-shape literal in served code/strings. Fixes are (a)
|
|
12
|
+
// derive it live (see lib/info-format.js), (b) genericize the prose ("a corpus", not
|
|
13
|
+
// "a 567-work corpus"), or (c) if it is genuinely a static fallback, append a
|
|
14
|
+
// `shape-literal-ok` comment on the line to opt out explicitly.
|
|
15
|
+
//
|
|
16
|
+
// Scope note: generic ring sub-counts (116/181/17) are deliberately NOT matched —
|
|
17
|
+
// too collision-prone to lint. They are guarded instead by live derivation plus
|
|
18
|
+
// test/info-format.test.js. Only the distinctive full counts + media ring are matched.
|
|
19
|
+
|
|
20
|
+
import { readdirSync, readFileSync, statSync } from "node:fs";
|
|
21
|
+
import { join, basename } from "node:path";
|
|
22
|
+
import { fileURLToPath } from "node:url";
|
|
23
|
+
|
|
24
|
+
const ROOT = join(fileURLToPath(new URL(".", import.meta.url)), "..");
|
|
25
|
+
|
|
26
|
+
// Files/dirs to scan (served logic + published schemas). Relative to repo root.
|
|
27
|
+
const SCAN = ["index.js", "inquiry.js", "lib", "openai-tools.json"];
|
|
28
|
+
const SKIP_DIRS = new Set(["node_modules", ".git", "test", "proposals"]);
|
|
29
|
+
const SCAN_EXT = new Set([".js", ".mjs", ".cjs", ".json"]);
|
|
30
|
+
|
|
31
|
+
// Distinctive corpus-shape literals. Add new full counts here as the corpus grows.
|
|
32
|
+
const FORBIDDEN = [
|
|
33
|
+
{ re: /\b528077\b/, what: "total-word count" },
|
|
34
|
+
{ re: /\b528208\b/, what: "total-word count (stale, pre-OMN-085)" },
|
|
35
|
+
{ re: /\b567\b/, what: "total-work count" },
|
|
36
|
+
{ re: /\b568\b/, what: "total-work count (stale, pre-OMN-085)" },
|
|
37
|
+
{ re: /\b253\b/, what: "Media/Oral ring count" },
|
|
38
|
+
{ re: /eight synthetic/i, what: "contributor-count phrasing" },
|
|
39
|
+
];
|
|
40
|
+
|
|
41
|
+
// A line is exempt if it is a comment or carries an explicit opt-out.
|
|
42
|
+
const isComment = (line) => /^\s*(\/\/|\*|\/\*)/.test(line);
|
|
43
|
+
const isAllowed = (line) => /shape-literal-ok/.test(line);
|
|
44
|
+
|
|
45
|
+
function* walk(path) {
|
|
46
|
+
const st = statSync(path);
|
|
47
|
+
if (st.isDirectory()) {
|
|
48
|
+
if (SKIP_DIRS.has(basename(path))) return;
|
|
49
|
+
for (const e of readdirSync(path)) yield* walk(join(path, e));
|
|
50
|
+
} else if ([...SCAN_EXT].some((x) => path.endsWith(x)) && basename(path) !== "check-shape-literals.mjs") {
|
|
51
|
+
yield path;
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
const hits = [];
|
|
56
|
+
for (const entry of SCAN) {
|
|
57
|
+
let target;
|
|
58
|
+
try { target = join(ROOT, entry); statSync(target); } catch { continue; }
|
|
59
|
+
for (const file of walk(target)) {
|
|
60
|
+
const lines = readFileSync(file, "utf8").split("\n");
|
|
61
|
+
lines.forEach((line, i) => {
|
|
62
|
+
if (isComment(line) || isAllowed(line)) return;
|
|
63
|
+
for (const { re, what } of FORBIDDEN) {
|
|
64
|
+
if (re.test(line)) {
|
|
65
|
+
hits.push({ file: file.replace(ROOT + "/", ""), line: i + 1, what, text: line.trim().slice(0, 100) });
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
});
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
if (hits.length) {
|
|
73
|
+
console.error(`\n🔴 shape-literal check FAILED — ${hits.length} frozen corpus-shape literal(s):\n`);
|
|
74
|
+
for (const h of hits) console.error(` ${h.file}:${h.line} [${h.what}]\n ${h.text}`);
|
|
75
|
+
console.error(`\nFix: derive it live, genericize the prose, or append \`shape-literal-ok\` if it is a real static fallback.\n`);
|
|
76
|
+
process.exit(1);
|
|
77
|
+
}
|
|
78
|
+
console.log("🟢 shape-literal check passed — no frozen corpus-shape literals in served source.");
|
package/scripts/publish.sh
CHANGED
|
@@ -36,6 +36,9 @@ node -e "const p=require('./package.json'),s=require('./server.json');const e=[]
|
|
|
36
36
|
# and package.json ↔ server.json. A drift here is a release blocker.
|
|
37
37
|
node scripts/check-tool-parity.js
|
|
38
38
|
|
|
39
|
+
# No frozen corpus-shape literal may reach a registry (2026-07-17 audit guard).
|
|
40
|
+
node scripts/check-shape-literals.mjs
|
|
41
|
+
|
|
39
42
|
# The full test suite must be green before anything reaches a registry.
|
|
40
43
|
npm test
|
|
41
44
|
|
package/server.json
CHANGED
|
@@ -6,7 +6,7 @@
|
|
|
6
6
|
"url": "https://github.com/justjlee/omnarai-mcp",
|
|
7
7
|
"source": "github"
|
|
8
8
|
},
|
|
9
|
-
"version": "1.6.
|
|
9
|
+
"version": "1.6.2",
|
|
10
10
|
"remotes": [
|
|
11
11
|
{
|
|
12
12
|
"type": "streamable-http",
|
|
@@ -17,7 +17,7 @@
|
|
|
17
17
|
{
|
|
18
18
|
"registryType": "npm",
|
|
19
19
|
"identifier": "omnarai-mcp",
|
|
20
|
-
"version": "1.6.
|
|
20
|
+
"version": "1.6.2",
|
|
21
21
|
"transport": {
|
|
22
22
|
"type": "stdio"
|
|
23
23
|
}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
// Regression guard for D5/D6 (live audit 2026-07-17): omnarai_info once hardcoded
|
|
2
|
+
// three rings — silently dropping Media/Oral (253 works, 45% of the corpus) — and a
|
|
3
|
+
// contributor line missing GPT-4o + Meta AI, both of which author Atlas records.
|
|
4
|
+
// These assert the shape lines are DERIVED and COMPLETE, offline, so a reintroduced
|
|
5
|
+
// literal fails `npm test` (the publish.sh gate) before it can ship.
|
|
6
|
+
|
|
7
|
+
import { test } from "node:test";
|
|
8
|
+
import assert from "node:assert/strict";
|
|
9
|
+
import {
|
|
10
|
+
formatRingsLine,
|
|
11
|
+
formatContributorsLine,
|
|
12
|
+
CANONICAL_CONTRIBUTORS,
|
|
13
|
+
RING_LABELS,
|
|
14
|
+
} from "../lib/info-format.js";
|
|
15
|
+
|
|
16
|
+
test("formatRingsLine renders every ring the engine reports — no silent drop (D5)", () => {
|
|
17
|
+
const live = { core: 116, curated: 181, open: 17, media: 253 };
|
|
18
|
+
const line = formatRingsLine(live);
|
|
19
|
+
// All four rings, with counts, in canonical order.
|
|
20
|
+
assert.match(line, /Core Canon \(116\)/);
|
|
21
|
+
assert.match(line, /Curated Expansions \(181\)/);
|
|
22
|
+
assert.match(line, /Open Exploration \(17\)/);
|
|
23
|
+
assert.match(line, /Media \/ Oral \(253\)/, "Media/Oral ring must be present — this is the D5 regression");
|
|
24
|
+
// Exactly as many segments as rings supplied — nothing added, nothing dropped.
|
|
25
|
+
// Split on " · " (the "Media / Oral" label contains a slash, so " / " would over-split).
|
|
26
|
+
assert.equal(line.split(" · ").length, Object.keys(live).length);
|
|
27
|
+
});
|
|
28
|
+
|
|
29
|
+
test("formatRingsLine cannot be pinned to three rings", () => {
|
|
30
|
+
// A future ring added to the engine payload must appear without a code change.
|
|
31
|
+
const withNewRing = { core: 1, curated: 2, open: 3, media: 4, research: 5 };
|
|
32
|
+
const line = formatRingsLine(withNewRing);
|
|
33
|
+
// Every label we know about renders; an unknown key is simply ignored, not fatal.
|
|
34
|
+
for (const label of Object.values(RING_LABELS)) assert.ok(line.includes(label), `${label} missing`);
|
|
35
|
+
});
|
|
36
|
+
|
|
37
|
+
test("formatRingsLine offline fallback still names all four rings", () => {
|
|
38
|
+
const line = formatRingsLine(null);
|
|
39
|
+
assert.ok(line.includes("Media / Oral"), "offline fallback must still include Media/Oral");
|
|
40
|
+
assert.equal(Object.values(RING_LABELS).every((l) => line.includes(l)), true);
|
|
41
|
+
});
|
|
42
|
+
|
|
43
|
+
test("contributor set includes GPT-4o and Meta AI (D6)", () => {
|
|
44
|
+
assert.ok(CANONICAL_CONTRIBUTORS.includes("GPT-4o"), "GPT-4o authors Atlas records — must be listed");
|
|
45
|
+
assert.ok(CANONICAL_CONTRIBUTORS.includes("Meta AI"), "Meta AI authors Atlas records — must be listed");
|
|
46
|
+
// Eight synthetic intelligences + the human curator = nine, as the homepage presents.
|
|
47
|
+
assert.equal(CANONICAL_CONTRIBUTORS.length, 9);
|
|
48
|
+
const line = formatContributorsLine();
|
|
49
|
+
assert.match(line, /GPT-4o/);
|
|
50
|
+
assert.match(line, /Meta AI/);
|
|
51
|
+
});
|