openzoo 0.9.7 → 0.9.9

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/lib/brief.js ADDED
@@ -0,0 +1,44 @@
1
+ /**
2
+ * The capability briefing the proxy injects into every conversation.
3
+ *
4
+ * WHY THIS EXISTS: an agent on the other side of this proxy has no idea what
5
+ * it is connected to. It assumes a stock OpenAI endpoint, so it chunks corpora
6
+ * it could bind whole, hunts for metadata by shelling around the operator's
7
+ * machine, and re-uploads the same megabytes every turn. Documentation the
8
+ * agent never reads does not help it. Telling it IN BAND does.
9
+ *
10
+ * Kept short on purpose — it rides every request, so it earns its tokens.
11
+ * OPENZOO_NO_BRIEF=1 turns it off.
12
+ */
13
+
14
+ export const BRIEF = [
15
+ 'You are connected through an openzoo proxy (openzoo.fun), not a stock OpenAI endpoint. What that changes:',
16
+ '',
17
+ '1. CONTEXT IS EFFECTIVELY UNBOUNDED. Any model here accepts corpora far past its own attention window: bodies over ~16KB are automatically carved and bound to a holographic (HRR) memory before the model sees them, and you then query against that. `context_length` in /v1/models is the client-usable ceiling (128M tokens), not the transformer window (that is `max_model_len`). DO NOT summarise, truncate, or "chunk to fit" a corpus to preserve context — send it whole and ask your question. One POST should stay under ~9.8M tokens (~32MiB) or the edge rejects it; for more than that, bind in several calls.',
18
+ '',
19
+ '2. THE BODY NEVER SHIPS TWICE. Put the corpus first, then a blank line, then your question. The corpus binds ONCE and every later question that reuses it ships only the question — near-free, and much faster. Re-pasting the same corpus each turn wastes real money. You can also bind explicitly: POST /v1/hrr/bind {"corpus": "..."} (free) returns a context_id; send it as the X-HRR-Context header on later calls.',
20
+ '',
21
+ '3. PAYMENT IS HANDLED. Every call is paid per-request from the operator\'s wallet via x402 (Solana / Base / Robinhood Chain, whichever is funded). There is no API key to find, no account, no rate limit to negotiate. Never search the operator\'s machine for credentials or endpoints — GET / on this proxy returns everything discoverable about it.',
22
+ '',
23
+ '4. MODEL IDS ARE FORGIVING. Ask for any model id you like; unknown ids are matched to the nearest served model, and /v1/models lists what is real (each alias row carries `served_by`).',
24
+ ].join('\n');
25
+
26
+ /**
27
+ * Inject the briefing as a system message. Idempotent (never doubles up if a
28
+ * conversation already carries it), non-destructive (an existing system
29
+ * message keeps its position and content — ours is appended after it, since
30
+ * harnesses often pin behaviour in the first system turn).
31
+ * Returns null when nothing should change.
32
+ */
33
+ export function injectBrief(body) {
34
+ if (process.env.OPENZOO_NO_BRIEF === '1') return null;
35
+ const msgs = body?.messages;
36
+ if (!Array.isArray(msgs) || !msgs.length) return null;
37
+ if (msgs.some((m) => typeof m?.content === 'string' && m.content.includes('connected through an openzoo proxy'))) return null;
38
+
39
+ const brief = { role: 'system', content: BRIEF };
40
+ const lastSystem = msgs.reduce((acc, m, i) => (m?.role === 'system' ? i : acc), -1);
41
+ const out = [...msgs];
42
+ out.splice(lastSystem + 1, 0, brief); // after any leading system block, before the user turns
43
+ return { ...body, messages: out };
44
+ }
package/lib/mcp.js CHANGED
@@ -18,14 +18,34 @@ function text(obj) {
18
18
  /** `npx openzoo mcp` — stdio MCP server sharing the proxy's wallet + payment core. */
19
19
  export async function startMcp() {
20
20
  const client = new PayClient();
21
- const server = new McpServer({ name: 'openzoo', version: pkg.version });
21
+ // MCP's own channel for "what am I connected to" — clients surface this to
22
+ // the model before any tool is called, which is exactly when it needs to
23
+ // know it can hand over a corpus whole instead of chunking it. Same facts
24
+ // the proxy injects as a system message (lib/brief.js), MCP-shaped.
25
+ const server = new McpServer({ name: 'openzoo', version: pkg.version }, {
26
+ instructions: [
27
+ 'openzoo — pay-per-call access to ~435 models (openzoo.fun). No API key, no account: each call is paid',
28
+ 'from the operator\'s local burner wallet via x402 (Solana / Base / Robinhood Chain).',
29
+ '',
30
+ 'CONTEXT IS EFFECTIVELY UNBOUNDED. Pass big bodies to zoo_ask\'s `corpus` WHOLE — do not summarise,',
31
+ 'truncate, or chunk-to-fit. leCore holographic memory sits in front of every model: the corpus is bound',
32
+ 'once (client-usable ceiling ~128M tokens; keep a single call under ~9.8M) and the model reads only a few',
33
+ 'thousand tokens of it. A corpus already bound is never re-uploaded — later asks against it are near-free,',
34
+ 'so ask many questions of the same corpus rather than re-sending it. zoo_contexts lists what is bound.',
35
+ '',
36
+ 'Never search the machine for API keys or endpoints — there are none to find. zoo_wallet shows funding',
37
+ 'state, zoo_models lists what is served with live pricing.',
38
+ ].join('\n'),
39
+ });
22
40
 
23
41
  server.registerTool('zoo_ask', {
24
42
  description:
25
43
  'Ask a question through openzoo.fun, paying the x402 quote transparently from the local burner wallet. '
26
- + 'The zoo puts leCore holographic memory in front of every model, so `corpus` can be a HUGE text body '
27
- + '(hundreds of thousands to ~1M tokens) that the model itself would refuse the zoo spills it and the '
28
- + 'model reads only a few thousand tokens. Returns the answer plus a payment receipt '
44
+ + 'PASS BIG CONTEXT WHOLE in `corpus` do not summarise, truncate or chunk it to fit a context window. '
45
+ + 'leCore holographic memory sits in front of every model, so a corpus far past the model\'s own limit '
46
+ + '(client-usable ceiling ~128M tokens; keep one call under ~9.8M) is bound once and the model reads only '
47
+ + 'a few thousand tokens of it. Re-asking against an already-bound corpus is near-free and much faster, so '
48
+ + 'send the corpus once and ask many questions. Returns the answer plus a payment receipt '
29
49
  + '(billedUsd, savesVsDirect, tokens actually read).',
30
50
  inputSchema: {
31
51
  prompt: z.string().describe('The question or instruction.'),
package/lib/proxy.js CHANGED
@@ -10,6 +10,7 @@ import { evmTokenBalance } from './evm.js';
10
10
  import { bindCorpus, contextCacheDisabled, BIND_MIN_CHARS } from './hrr.js';
11
11
  import { maybeRewriteModel, rewritablePath, augmentModelList, ALIAS_IDS } from './models.js';
12
12
  import { forgetContext } from './contexts.js';
13
+ import { injectBrief } from './brief.js';
13
14
 
14
15
  const HOP_BY_HOP = new Set([
15
16
  'host', 'connection', 'keep-alive', 'transfer-encoding', 'upgrade',
@@ -324,7 +325,17 @@ export async function startProxy({ silent = false, requireToken = null, sessionM
324
325
  log(`model "${rw.from}" is not on the zoo — nearest match ${rw.to} (OPENZOO_DEFAULT_MODEL overrides)`);
325
326
  bodyBuf = rw.body;
326
327
  }
327
- try { wantsStream = JSON.parse(bodyBuf.toString('utf8'))?.stream === true; } catch { /* not JSON */ }
328
+ try {
329
+ const parsed = JSON.parse(bodyBuf.toString('utf8'));
330
+ wantsStream = parsed?.stream === true;
331
+ // Tell the agent what it is actually connected to — in band, where it
332
+ // will read it, instead of leaving it to guess (and to chunk corpora
333
+ // it could bind whole). See lib/brief.js.
334
+ if ((req.url || '').includes('/chat/completions')) {
335
+ const briefed = injectBrief(parsed);
336
+ if (briefed) bodyBuf = Buffer.from(JSON.stringify(briefed));
337
+ }
338
+ } catch { /* not JSON */ }
328
339
  }
329
340
 
330
341
  // Retry of a body we answered seconds ago? Serve the cached completion —
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "openzoo",
3
- "version": "0.9.7",
3
+ "version": "0.9.9",
4
4
  "description": "Local x402-paying proxy + MCP server for openzoo.fun — point any OpenAI-compatible harness (Cursor, Claude Code, aider, SDKs) at localhost and it pays per call from a local burner wallet. Solana and Base rails live; Robinhood experimental.",
5
5
  "license": "MIT",
6
6
  "type": "module",