@konneal/engine 0.2.75 → 0.2.76

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.
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  handleAsk
3
- } from "./chunk-XJPJO376.js";
3
+ } from "./chunk-64G44J7U.js";
4
4
  import "./chunk-7HWJOFTQ.js";
5
5
  import "./chunk-SPKPH54J.js";
6
6
  import "./chunk-A3QHHUN5.js";
@@ -2050,23 +2050,31 @@ function nameplateRegisterQuery(np, question) {
2050
2050
 
2051
2051
  // workers/worker_public/src/nameplate.ts
2052
2052
  async function extractNameplate(ai, model, image) {
2053
- try {
2054
- const res = await ai.run(model, {
2055
- messages: [
2056
- { role: "system", content: nameplate_default.trimEnd() },
2057
- { role: "user", content: [{ type: "image_url", image_url: { url: image } }] }
2058
- ],
2059
- max_tokens: 512,
2060
- reasoning_effort: "low"
2061
- });
2062
- const text = typeof res?.response === "string" ? res.response : res?.choices?.[0]?.message?.content;
2063
- const np = parseNameplate(text ?? "");
2064
- console.log(`nameplate-extract: ${np ? `${np.manufacturer} / ${np.model}` : `no parse (${(text ?? "").slice(0, 120)})`}`);
2065
- return np;
2066
- } catch (e) {
2067
- console.log(`nameplate-extract: FAILED ${String(e).slice(0, 160)}`);
2068
- return null;
2053
+ for (let attempt = 0; attempt < 2; attempt++) {
2054
+ try {
2055
+ const res = await ai.run(model, {
2056
+ messages: [
2057
+ { role: "system", content: nameplate_default.trimEnd() },
2058
+ { role: "user", content: [{ type: "image_url", image_url: { url: image } }] }
2059
+ ],
2060
+ // the budget rises with the retry's effort — elevated effort under
2061
+ // a flat budget starves the answer on this model (measured,
2062
+ // 2026-09-18: 5/38 at medium with the flat budget)
2063
+ max_tokens: attempt === 0 ? 512 : 1536,
2064
+ reasoning_effort: attempt === 0 ? "low" : "medium"
2065
+ });
2066
+ const text = typeof res?.response === "string" ? res.response : res?.choices?.[0]?.message?.content;
2067
+ const np = parseNameplate(text ?? "");
2068
+ if (np) {
2069
+ console.log(`nameplate-extract: ${np.manufacturer} / ${np.model}${attempt ? " (on retry)" : ""}`);
2070
+ return np;
2071
+ }
2072
+ console.log(`nameplate-extract: no parse on attempt ${attempt + 1} (${(text ?? "").slice(0, 120)})`);
2073
+ } catch (e) {
2074
+ console.log(`nameplate-extract: FAILED attempt ${attempt + 1} ${String(e).slice(0, 160)}`);
2075
+ }
2069
2076
  }
2077
+ return null;
2070
2078
  }
2071
2079
 
2072
2080
  // workers/worker_public/src/ask.ts
@@ -6,7 +6,7 @@ import {
6
6
  modelGroundingBlock,
7
7
  scoreFaithfulness,
8
8
  scoreJudge
9
- } from "../../chunk-XJPJO376.js";
9
+ } from "../../chunk-64G44J7U.js";
10
10
  import {
11
11
  handleSearch
12
12
  } from "../../chunk-KO6DRI7C.js";
@@ -959,7 +959,7 @@ async function handleMcp(env, ctx, req, tier, key) {
959
959
  // stream:false forces the JSON lane (anon defaults to SSE)
960
960
  body: JSON.stringify({ ...args, stream: false })
961
961
  });
962
- const res = name === "ask" ? await (await import("../../ask-AJJCWGW6.js")).handleAsk(env, ctx, inner, tier, key) : await (await import("../../search-LVUQLA3C.js")).handleSearch(env, ctx, inner, tier, key);
962
+ const res = name === "ask" ? await (await import("../../ask-PK75QJ66.js")).handleAsk(env, ctx, inner, tier, key) : await (await import("../../search-LVUQLA3C.js")).handleSearch(env, ctx, inner, tier, key);
963
963
  return res.json().catch(() => ({ error: { message: "tool transport failed", status: res.status } }));
964
964
  });
965
965
  if (out.ok && "accepted" in out) return new Response(null, { status: 202 });
package/package.json CHANGED
@@ -27,7 +27,7 @@
27
27
  "playwright": "^1.62.1",
28
28
  "yaml": "^2.9.1"
29
29
  },
30
- "version": "0.2.75",
30
+ "version": "0.2.76",
31
31
  "description": "The Konneal engine: the publisher-agnostic build pipeline and API plane for standards intelligence (retrieval, answer contract, verdicts, evaluation).",
32
32
  "license": "BSD-3-Clause",
33
33
  "type": "module",
@@ -14,23 +14,36 @@ export type { Nameplate };
14
14
  export { nameplateRegisterQuery };
15
15
 
16
16
  export async function extractNameplate(ai: any, model: string, image: string): Promise<Nameplate | null> {
17
- try {
18
- const res: any = await ai.run(model, {
19
- messages: [
20
- { role: "system", content: nameplatePrompt.trimEnd() },
21
- { role: "user", content: [{ type: "image_url", image_url: { url: image } }] },
22
- ],
23
- max_tokens: 512,
24
- reasoning_effort: "low",
25
- });
26
- const text = typeof res?.response === "string" ? res.response : res?.choices?.[0]?.message?.content;
27
- const np = parseNameplate(text ?? "");
28
- console.log(`nameplate-extract: ${np ? `${np.manufacturer} / ${np.model}` : `no parse (${(text ?? "").slice(0, 120)})`}`);
29
- return np;
30
- } catch (e) {
31
- console.log(`nameplate-extract: FAILED ${String(e).slice(0, 160)}`);
32
- return null; // the bridge is optional — the ask never depends on it
17
+ // one retry, decided on the RESULT not the error: the observed live
18
+ // failure (2026-10-03) is a structurally valid response carrying null
19
+ // fields — the same image the answer model read perfectly a moment
20
+ // later. A transient vision-call miss must not strand a certificate
21
+ // question with no register rows.
22
+ for (let attempt = 0; attempt < 2; attempt++) {
23
+ try {
24
+ const res: any = await ai.run(model, {
25
+ messages: [
26
+ { role: "system", content: nameplatePrompt.trimEnd() },
27
+ { role: "user", content: [{ type: "image_url", image_url: { url: image } }] },
28
+ ],
29
+ // the budget rises with the retry's effort — elevated effort under
30
+ // a flat budget starves the answer on this model (measured,
31
+ // 2026-09-18: 5/38 at medium with the flat budget)
32
+ max_tokens: attempt === 0 ? 512 : 1536,
33
+ reasoning_effort: attempt === 0 ? "low" : "medium",
34
+ });
35
+ const text = typeof res?.response === "string" ? res.response : res?.choices?.[0]?.message?.content;
36
+ const np = parseNameplate(text ?? "");
37
+ if (np) {
38
+ console.log(`nameplate-extract: ${np.manufacturer} / ${np.model}${attempt ? " (on retry)" : ""}`);
39
+ return np;
40
+ }
41
+ console.log(`nameplate-extract: no parse on attempt ${attempt + 1} (${(text ?? "").slice(0, 120)})`);
42
+ } catch (e) {
43
+ console.log(`nameplate-extract: FAILED attempt ${attempt + 1} ${String(e).slice(0, 160)}`);
44
+ }
33
45
  }
46
+ return null; // the bridge is optional — the ask never depends on it
34
47
  }
35
48
 
36
49
  export const nameplateModel = () => MODELS.member;