@jkudish/jev-mcp 0.2.0 → 0.3.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/CHANGELOG.md CHANGED
@@ -1,5 +1,12 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.3.0
4
+
5
+ - Cloudflare Workers AI support: with `CLOUDFLARE_API_TOKEN` (or `JEV_CLOUDFLARE_API_TOKEN`) and `CLOUDFLARE_ACCOUNT_ID` set, judgments run through Cloudflare at the `typesafe/jev` alias; `JEV_PROVIDER=cloudflare` forces it. Usage tokens are reported on every call.
6
+ - Vercel AI Gateway support: with `AI_GATEWAY_API_KEY` set, judgments run through the AI SDK evaluate API at `typesafe-ai/jev`; `JEV_PROVIDER=vercel` forces it. Noul, choice, and score answers are adapted back to this package's shapes, with TypeSafe confidence included.
7
+ - Provider resolution order: TypeSafe direct, OpenRouter, Cloudflare, Vercel.
8
+ - Internal fix: transport branches are explicitly guarded per provider.
9
+
3
10
  ## 0.2.0
4
11
 
5
12
  - OpenRouter support: with only an `OPENROUTER_API_KEY`, all judgments route through OpenRouter's Decisions API (alpha) at the same pricing; `JEV_PROVIDER` forces `typesafe` or `openrouter`. `jev-latest` maps to `typesafe/jev-1.13` there.
package/README.md CHANGED
@@ -196,10 +196,20 @@ Jev is TypeSafe's System One model: it returns typed answers with calibrated pro
196
196
  | --- | --- | --- |
197
197
  | `TYPESAFE_API_KEY` | none | TypeSafe direct. Default provider when set. |
198
198
  | `OPENROUTER_API_KEY` | none | OpenRouter `sk-or-` key; used when `TYPESAFE_API_KEY` is absent. |
199
- | `JEV_PROVIDER` | `auto` | Force `typesafe` or `openrouter` instead of auto-detection. |
199
+ | `CLOUDFLARE_API_TOKEN` + `CLOUDFLARE_ACCOUNT_ID` | none | Cloudflare Workers AI; used when no other provider key is present. `JEV_CLOUDFLARE_API_TOKEN` is honored first for separate credentials. |
200
+ | `AI_GATEWAY_API_KEY` | none | Vercel AI Gateway; used when no other provider key is present. |
201
+ | `JEV_PROVIDER` | `auto` | Force `typesafe`, `openrouter`, `cloudflare`, or `vercel` instead of auto-detection. |
200
202
  | `JEV_MCP_MODEL` | `jev-latest` | Pin a Jev version, e.g. `jev-1.12`, or `typesafe/jev-1.13` on OpenRouter. |
201
203
  | `TYPESAFE_BASE_URL` | none | Custom direct endpoint (origin only; the SDK appends its route). |
202
204
 
205
+ ### Vercel
206
+
207
+ With `AI_GATEWAY_API_KEY` set, judgments run through the Vercel AI Gateway at `typesafe-ai/jev`, using the AI SDK's evaluate API. Answers are adapted back to this package's shapes, including TypeSafe's confidence statistic. Gateway calls appear in Vercel logs and budgets.
208
+
209
+ ### Cloudflare
210
+
211
+ With `CLOUDFLARE_API_TOKEN` and `CLOUDFLARE_ACCOUNT_ID` set (and no other provider key), judgments run through Cloudflare Workers AI at `typesafe/jev`, the single always-current alias. Usage tokens come back on every call. Cloudflare serves one alias rather than pinned versions, and pricing is listed in the Cloudflare dashboard. Direct TypeSafe remains the recommended default when you have several keys.
212
+
203
213
  ### OpenRouter
204
214
 
205
215
  If you already have an OpenRouter key, that is all you need: with no `TYPESAFE_API_KEY` present, every call goes through OpenRouter's Decisions API at identical pricing. The endpoint is alpha and adds a hop, and OpenRouter serves pinned versions rather than a `latest` alias, so the default `jev-latest` maps to `typesafe/jev-1.13` there. Direct TypeSafe remains the recommended default when you have both keys.
@@ -208,6 +218,10 @@ If you already have an OpenRouter key, that is all you need: with no `TYPESAFE_A
208
218
 
209
219
  Need those judgments to drive a real browser? [Jev Browser](https://github.com/jkudish/jev-browser) gives an agent a task and a URL and lets Jev pick the actions: click, type, select, stop. It uses the same judgment style this server exposes. The npm package is [@jkudish/jev-browser](https://www.npmjs.com/package/@jkudish/jev-browser).
210
220
 
221
+ ## Sponsoring
222
+
223
+ If you find Jev MCP useful, consider becoming a [sponsor](https://github.com/sponsors/jkudish) or [donating](https://stripe.com/@jkudish).
224
+
211
225
  ## Development
212
226
 
213
227
  ```bash
@@ -1,4 +1,4 @@
1
- export type JevProvider = "typesafe" | "openrouter";
1
+ export type JevProvider = "typesafe" | "openrouter" | "cloudflare" | "vercel";
2
2
  export interface AskResult {
3
3
  answers: Record<string, any>;
4
4
  usage: {
package/dist/provider.js CHANGED
@@ -1,7 +1,8 @@
1
- // Jev transport: TypeSafe direct (default) or OpenRouter's Decisions API.
2
- // Both speak the same {state, questions} / answers contract; only the URL,
3
- // auth, and model slug differ. OpenRouter is an alpha endpoint and adds a
4
- // hop, so direct TypeSafe remains the recommended default.
1
+ // Jev transport: TypeSafe direct (default), OpenRouter Decisions, or
2
+ // Cloudflare Workers AI. All speak the {state, questions} / answers contract;
3
+ // URL, auth, and model slugs differ. Proxies add hops, so direct TypeSafe
4
+ // remains the recommended default.
5
+ import { experimental_evaluate } from "ai";
5
6
  import { TypeSafeClient } from "@typesafe-ai/sdk";
6
7
  const X_TITLE = "jev-mcp";
7
8
  const REFERER = "https://github.com/jkudish/jev-mcp";
@@ -10,6 +11,8 @@ function resolve(env) {
10
11
  const explicit = (env.JEV_PROVIDER ?? "auto").toLowerCase();
11
12
  const hasTypesafe = Boolean(env.TYPESAFE_API_KEY);
12
13
  const hasOpenRouter = /^sk-or-/.test(env.OPENROUTER_API_KEY ?? "");
14
+ const cfToken = env.JEV_CLOUDFLARE_API_TOKEN || env.CLOUDFLARE_API_TOKEN;
15
+ const hasCloudflare = Boolean(cfToken && env.CLOUDFLARE_ACCOUNT_ID);
13
16
  if (explicit === "typesafe") {
14
17
  if (!hasTypesafe)
15
18
  throw new Error("JEV_PROVIDER=typesafe but TYPESAFE_API_KEY is not set.");
@@ -20,11 +23,25 @@ function resolve(env) {
20
23
  throw new Error("JEV_PROVIDER=openrouter but OPENROUTER_API_KEY is not set or not an sk-or- key.");
21
24
  return "openrouter";
22
25
  }
26
+ if (explicit === "vercel") {
27
+ if (!env.AI_GATEWAY_API_KEY)
28
+ throw new Error("JEV_PROVIDER=vercel but AI_GATEWAY_API_KEY is not set.");
29
+ return "vercel";
30
+ }
31
+ if (explicit === "cloudflare") {
32
+ if (!hasCloudflare)
33
+ throw new Error("JEV_PROVIDER=cloudflare but a Cloudflare API token (CLOUDFLARE_API_TOKEN or JEV_CLOUDFLARE_API_TOKEN) and CLOUDFLARE_ACCOUNT_ID are not both set.");
34
+ return "cloudflare";
35
+ }
23
36
  if (hasTypesafe)
24
37
  return "typesafe";
25
38
  if (hasOpenRouter)
26
39
  return "openrouter";
27
- throw new Error("No TYPESAFE_API_KEY or OPENROUTER_API_KEY (sk-or-) found. Set one, or JEV_PROVIDER to choose explicitly.");
40
+ if (hasCloudflare)
41
+ return "cloudflare";
42
+ if (env.AI_GATEWAY_API_KEY)
43
+ return "vercel";
44
+ throw new Error("No TYPESAFE_API_KEY, OPENROUTER_API_KEY (sk-or-), or Cloudflare token + CLOUDFLARE_ACCOUNT_ID found. Set one, or JEV_PROVIDER to choose explicitly.");
28
45
  }
29
46
  export async function askJev(state, questions, model, signal) {
30
47
  const provider = resolve(process.env);
@@ -38,34 +55,106 @@ export async function askJev(state, questions, model, signal) {
38
55
  model,
39
56
  };
40
57
  }
41
- // OpenRouter has no redirecting "latest" slug; map it to the current release.
42
- // Pin exact versions with the model env var when that matters.
43
- const OPENROUTER_LATEST = "jev-1.13";
44
- const effective = model === "jev-latest" ? OPENROUTER_LATEST : model;
45
- const slug = effective.startsWith("typesafe/") ? effective : `typesafe/${effective}`;
46
- const response = await fetch("https://openrouter.ai/api/alpha/decisions", {
58
+ if (provider === "openrouter") {
59
+ // OpenRouter has no redirecting "latest" slug; map it to the current
60
+ // release. Pin exact versions with the model env var when that matters.
61
+ const OPENROUTER_LATEST = "jev-1.13";
62
+ const effective = model === "jev-latest" ? OPENROUTER_LATEST : model;
63
+ const slug = effective.startsWith("typesafe/") ? effective : `typesafe/${effective}`;
64
+ const response = await fetch("https://openrouter.ai/api/alpha/decisions", {
65
+ method: "POST",
66
+ headers: {
67
+ Authorization: `Bearer ${process.env.OPENROUTER_API_KEY}`,
68
+ "Content-Type": "application/json",
69
+ "HTTP-Referer": REFERER,
70
+ "X-Title": X_TITLE,
71
+ "X-OpenRouter-Title": X_TITLE,
72
+ },
73
+ body: JSON.stringify({ model: slug, state, questions }),
74
+ signal,
75
+ });
76
+ if (!response.ok) {
77
+ const body = await response.text().catch(() => "");
78
+ throw new Error(`OpenRouter decisions API ${response.status}: ${body.slice(0, 200)}`);
79
+ }
80
+ const body = await response.json();
81
+ return {
82
+ answers: body.answers ?? {},
83
+ // The decisions endpoint does not document a usage block; tolerate absence.
84
+ usage: { input_tokens: body.usage?.input_tokens ?? 0, output_tokens: body.usage?.output_tokens ?? 0 },
85
+ provider,
86
+ model: slug,
87
+ };
88
+ }
89
+ if (provider === "vercel") {
90
+ // Vercel AI Gateway exposes Jev through the AI SDK's experimental evaluate
91
+ // API: "noul" questions become "boolean", answers return as probabilities,
92
+ // and Choice/Score confidence lives in providerMetadata.typesafe.
93
+ const vercelQuestions = {};
94
+ for (const [id, question] of Object.entries(questions)) {
95
+ const q = question;
96
+ vercelQuestions[id] = {
97
+ type: q.type === "noul" ? "boolean" : q.type,
98
+ instructions: q.instructions,
99
+ criteria: q.criteria,
100
+ };
101
+ }
102
+ const result = await experimental_evaluate({
103
+ model: model.startsWith("typesafe-ai/") ? model : "typesafe-ai/jev",
104
+ state: state,
105
+ questions: vercelQuestions,
106
+ abortSignal: signal,
107
+ });
108
+ const confidence = (result.providerMetadata?.typesafe?.confidence ?? {});
109
+ const adapted = {};
110
+ for (const [id, answer] of Object.entries(result.answers)) {
111
+ if (answer?.type === "boolean") {
112
+ adapted[id] = { type: "noul", noul: answer.probability };
113
+ }
114
+ else if (answer?.type === "choice") {
115
+ adapted[id] = { type: "choice", choice: answer.choice, probabilities: answer.probabilities ?? {}, confidence: confidence[id] ?? null };
116
+ }
117
+ else if (answer?.type === "score") {
118
+ adapted[id] = { type: "score", score: answer.score, probabilities: answer.probabilities ?? {}, confidence: confidence[id] ?? null };
119
+ }
120
+ else {
121
+ adapted[id] = answer;
122
+ }
123
+ }
124
+ return {
125
+ answers: adapted,
126
+ usage: { input_tokens: result.usage?.inputTokens ?? 0, output_tokens: result.usage?.outputTokens ?? 0 },
127
+ provider,
128
+ model: "typesafe-ai/jev",
129
+ };
130
+ }
131
+ // Cloudflare Workers AI wraps the same contract in {model, input} and the
132
+ // v4 {result, success} envelope. Single alias; no version pinning.
133
+ const cfSlug = model.startsWith("typesafe/") ? model : `typesafe/${model === "jev-latest" ? "jev" : model}`;
134
+ const cfResponse = await fetch(`https://api.cloudflare.com/client/v4/accounts/${process.env.CLOUDFLARE_ACCOUNT_ID}/ai/run`, {
47
135
  method: "POST",
48
136
  headers: {
49
- Authorization: `Bearer ${process.env.OPENROUTER_API_KEY}`,
137
+ Authorization: `Bearer ${process.env.JEV_CLOUDFLARE_API_TOKEN || process.env.CLOUDFLARE_API_TOKEN}`,
50
138
  "Content-Type": "application/json",
51
- "HTTP-Referer": REFERER,
52
- "X-Title": X_TITLE,
53
- "X-OpenRouter-Title": X_TITLE,
54
139
  },
55
- body: JSON.stringify({ model: slug, state, questions }),
140
+ body: JSON.stringify({ model: cfSlug, input: { state, questions } }),
56
141
  signal,
57
142
  });
58
- if (!response.ok) {
59
- const body = await response.text().catch(() => "");
60
- throw new Error(`OpenRouter decisions API ${response.status}: ${body.slice(0, 200)}`);
143
+ const cfBody = await cfResponse.json().catch(() => ({}));
144
+ if (!cfResponse.ok || cfBody.success === false) {
145
+ throw new Error(`Cloudflare AI run ${cfResponse.status}: ${JSON.stringify(cfBody.errors ?? cfBody).slice(0, 200)}`);
146
+ }
147
+ // The v4 envelope double-nests: body.result.result holds the model output.
148
+ const cfOuter = cfBody.result;
149
+ if (cfOuter && typeof cfOuter.state === "string" && cfOuter.state !== "Completed") {
150
+ throw new Error(`Cloudflare AI run state ${cfOuter.state}: ${JSON.stringify(cfBody.errors ?? []).slice(0, 200)}`);
61
151
  }
62
- const body = await response.json();
152
+ const cfPayload = cfOuter?.result ?? cfOuter ?? cfBody;
63
153
  return {
64
- answers: body.answers ?? {},
65
- // The decisions endpoint does not document a usage block; tolerate absence.
66
- usage: { input_tokens: body.usage?.input_tokens ?? 0, output_tokens: body.usage?.output_tokens ?? 0 },
154
+ answers: cfPayload.answers ?? {},
155
+ usage: { input_tokens: cfPayload.usage?.input_tokens ?? 0, output_tokens: cfPayload.usage?.output_tokens ?? 0 },
67
156
  provider,
68
- model: slug,
157
+ model: cfPayload.model ?? cfSlug,
69
158
  };
70
159
  }
71
160
  //# sourceMappingURL=provider.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"provider.js","sourceRoot":"","sources":["../src/provider.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"provider.js","sourceRoot":"","sources":["../src/provider.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@jkudish/jev-mcp",
3
- "version": "0.2.0",
3
+ "version": "0.3.0",
4
4
  "description": "MCP server exposing TypeSafe's Jev (System One) as purpose-built judgment tools: verify claims against evidence, screen content for injection, find semantically without embeddings.",
5
5
  "type": "module",
6
6
  "license": "MIT",
@@ -43,7 +43,8 @@
43
43
  "dependencies": {
44
44
  "@modelcontextprotocol/sdk": "^1.17.0",
45
45
  "@typesafe-ai/sdk": "^0.6.0",
46
- "zod": "^3.25.0"
46
+ "zod": "^3.25.0",
47
+ "ai": "^7.0.105"
47
48
  },
48
49
  "devDependencies": {
49
50
  "@types/node": "^22.0.0",