agentlas 0.9.6 → 0.9.7
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 +16 -0
- package/engine/agentlas.cjs +89 -23
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,21 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 0.9.7 — 2026-07-25
|
|
4
|
+
|
|
5
|
+
- Fix: the resident judge now reaches API/Ollama/BYOK runtimes, not only CLI
|
|
6
|
+
subprocess runtimes. Previously, when your connected runtime was Ollama or a
|
|
7
|
+
BYOK API model, every route, intent, and classification silently used the
|
|
8
|
+
deterministic wordlist fallback because the judge was wired to null — so a
|
|
9
|
+
non-English request the keyword lists could not read never got a model
|
|
10
|
+
verdict. The judge now runs on whatever runtime you actually have connected,
|
|
11
|
+
and its timeout signal aborts the underlying request cleanly.
|
|
12
|
+
- Fix: the judge is installed at startup, before the first routing decision.
|
|
13
|
+
It was previously wired only inside the run turn, which happens after routing,
|
|
14
|
+
so the very first auto-route in a one-shot always fell back.
|
|
15
|
+
- Routing gives the model a more generous deadline (a one-shot pre-run gate), so
|
|
16
|
+
a slower local model is judged rather than frequently falling back. When it
|
|
17
|
+
still cannot answer in time, the route receipt says so explicitly.
|
|
18
|
+
|
|
3
19
|
## 0.9.6 — 2026-07-25
|
|
4
20
|
|
|
5
21
|
- Agent and App Builder routing is now decided by the connected model: lexical
|
package/engine/agentlas.cjs
CHANGED
|
@@ -640,6 +640,7 @@ const APP_BUILDER_ROUTE_SLUG = "agentlas-app-builder";
|
|
|
640
640
|
async function resolveAutoRoute(db, prompt, lang) {
|
|
641
641
|
const resolvedLang = lang || prefsLang();
|
|
642
642
|
const prefilter = autoRouteAgent(db, prompt, resolvedLang);
|
|
643
|
+
ensureJudgmentRunnerInstalled(db);
|
|
643
644
|
let judgment;
|
|
644
645
|
try {
|
|
645
646
|
judgment = require("./agentlas-judgment.cjs");
|
|
@@ -700,6 +701,11 @@ async function resolveAutoRoute(db, prompt, lang) {
|
|
|
700
701
|
].join("\n"),
|
|
701
702
|
multi: false,
|
|
702
703
|
fallback: [],
|
|
704
|
+
// Routing is a one-shot pre-run gate: correctness matters more than latency,
|
|
705
|
+
// and a local 30B model with a full roster can need well over the 20s default.
|
|
706
|
+
// The judge's abort signal is threaded into the request, so a genuinely hung
|
|
707
|
+
// model still aborts cleanly at this deadline rather than hanging forever.
|
|
708
|
+
timeoutMs: 40000,
|
|
703
709
|
});
|
|
704
710
|
if (verdict.source !== "llm" || !verdict.labels.length) return { ...prefilter, routeSource: "deterministic" };
|
|
705
711
|
const picked = verdict.labels[0];
|
|
@@ -8627,32 +8633,83 @@ function installJudgmentRunner(db, rt) {
|
|
|
8627
8633
|
} catch {
|
|
8628
8634
|
return;
|
|
8629
8635
|
}
|
|
8630
|
-
|
|
8631
|
-
|
|
8636
|
+
// CLI runtime (claude-code/codex/gemini): the judge runs a silent native turn.
|
|
8637
|
+
if (rt && rt.mode === "cli" && RUNTIME_BIN[rt.kind]) {
|
|
8638
|
+
judgment.setJudgmentRunner(async ({ system, prompt, signal }) => {
|
|
8639
|
+
const { runNativeTurn } = require("./agentlas-native-host.cjs");
|
|
8640
|
+
const { Ui } = require("./agentlas-ui.cjs");
|
|
8641
|
+
const silent = new Ui({ lang: prefsLang(), quiet: true });
|
|
8642
|
+
for (const method of ["write", "warn", "info", "tool", "result", "status", "line"]) {
|
|
8643
|
+
if (typeof silent[method] === "function") silent[method] = () => {};
|
|
8644
|
+
}
|
|
8645
|
+
const res = await runNativeTurn({
|
|
8646
|
+
kind: rt.kind,
|
|
8647
|
+
bin: RUNTIME_BIN[rt.kind],
|
|
8648
|
+
prompt,
|
|
8649
|
+
systemPrompt: system,
|
|
8650
|
+
cwd: projectCwd(),
|
|
8651
|
+
permission: "read",
|
|
8652
|
+
session: {},
|
|
8653
|
+
ui: silent,
|
|
8654
|
+
env: process.env,
|
|
8655
|
+
signal,
|
|
8656
|
+
});
|
|
8657
|
+
if (res && res.error) return "";
|
|
8658
|
+
return (res && res.text) || "";
|
|
8659
|
+
});
|
|
8632
8660
|
return;
|
|
8633
8661
|
}
|
|
8634
|
-
|
|
8635
|
-
|
|
8636
|
-
|
|
8637
|
-
|
|
8638
|
-
|
|
8639
|
-
|
|
8640
|
-
|
|
8641
|
-
|
|
8642
|
-
|
|
8643
|
-
|
|
8644
|
-
|
|
8645
|
-
|
|
8646
|
-
|
|
8647
|
-
|
|
8648
|
-
|
|
8649
|
-
|
|
8650
|
-
|
|
8651
|
-
|
|
8662
|
+
|
|
8663
|
+
// API runtime (BYOK / Ollama): the judge uses the same one-shot API path the
|
|
8664
|
+
// rest of the terminal uses, so "the connected model decides" holds for the
|
|
8665
|
+
// user's actual runtime — not only CLI subprocess runtimes. Without this, an
|
|
8666
|
+
// Ollama/BYOK user silently gets the deterministic wordlist fallback for every
|
|
8667
|
+
// route, intent, and classification decision.
|
|
8668
|
+
if (rt && rt.mode === "api" && rt.backend) {
|
|
8669
|
+
judgment.setJudgmentRunner(async ({ system, prompt, signal }) => {
|
|
8670
|
+
// Thread the judge's timeout signal into the actual HTTP request so a slow
|
|
8671
|
+
// model aborts the fetch instead of hanging past the deadline.
|
|
8672
|
+
const baseFetch = globalThis.fetch;
|
|
8673
|
+
const fetchImpl = typeof baseFetch === "function" && signal
|
|
8674
|
+
? (url, init) => baseFetch(url, { ...(init || {}), signal })
|
|
8675
|
+
: baseFetch;
|
|
8676
|
+
try {
|
|
8677
|
+
return await runApi(rt.backend, rt.model, system, prompt, { fetch: fetchImpl });
|
|
8678
|
+
} catch {
|
|
8679
|
+
return "";
|
|
8680
|
+
}
|
|
8652
8681
|
});
|
|
8653
|
-
|
|
8654
|
-
|
|
8655
|
-
|
|
8682
|
+
return;
|
|
8683
|
+
}
|
|
8684
|
+
|
|
8685
|
+
judgment.setJudgmentRunner(null);
|
|
8686
|
+
}
|
|
8687
|
+
|
|
8688
|
+
// Make sure the resident judge can reach the connected model BEFORE the first
|
|
8689
|
+
// judged decision (routing, image capability, task class). The only other
|
|
8690
|
+
// install site is inside executeOnce, which runs AFTER routing — so a one-shot
|
|
8691
|
+
// `run`/auto-route would always fall to the deterministic label without this.
|
|
8692
|
+
// Uses the active runtime (CLI or API/Ollama/BYOK); a pinned override still
|
|
8693
|
+
// reinstalls in executeOnce for the actual task turn.
|
|
8694
|
+
function ensureJudgmentRunnerInstalled(db) {
|
|
8695
|
+
let judgment;
|
|
8696
|
+
try {
|
|
8697
|
+
judgment = require("./agentlas-judgment.cjs");
|
|
8698
|
+
} catch {
|
|
8699
|
+
return;
|
|
8700
|
+
}
|
|
8701
|
+
if (judgment.hasJudgmentRunner()) return;
|
|
8702
|
+
try {
|
|
8703
|
+
const ar = activeRuntime(db);
|
|
8704
|
+
let rt = null;
|
|
8705
|
+
if (ar && RUNTIME_BIN[ar.kind]) rt = { mode: "cli", kind: ar.kind, model: ar.model || null };
|
|
8706
|
+
else if (ar && ar.kind === "byok" && ar.backend) rt = { mode: "api", backend: ar.backend, model: ar.model };
|
|
8707
|
+
else if (ar && ar.kind === "ollama") rt = { mode: "api", backend: "ollama", model: ar.model };
|
|
8708
|
+
if (rt) installJudgmentRunner(db, rt);
|
|
8709
|
+
} catch {
|
|
8710
|
+
// No resolvable runtime → leave the runner unset; judged sites use their
|
|
8711
|
+
// labeled deterministic fallback rather than crashing.
|
|
8712
|
+
}
|
|
8656
8713
|
}
|
|
8657
8714
|
|
|
8658
8715
|
function resolveRuntime(db, override) {
|
|
@@ -11878,6 +11935,12 @@ async function main() {
|
|
|
11878
11935
|
// Agentlas 아키텍처 빌트인 에이전트를 보장(앱과 동일, 멱등·버전 게이팅). 스키마가 준비됐을 때만.
|
|
11879
11936
|
try { seedBuiltins(db); } catch { /* best-effort */ }
|
|
11880
11937
|
|
|
11938
|
+
// Wire the resident judge to the connected runtime up front, so the FIRST
|
|
11939
|
+
// routing / image-capability / task-class decision is judged by the model —
|
|
11940
|
+
// in the REPL and in one-shot commands alike — instead of silently falling to
|
|
11941
|
+
// the deterministic label until executeOnce eventually installs it.
|
|
11942
|
+
ensureJudgmentRunnerInstalled(db);
|
|
11943
|
+
|
|
11881
11944
|
// 인자 없이 `agentlas` → 에이전트 1개면 바로 대화형, 아니면 목록 + 사용법
|
|
11882
11945
|
if (cmd === "") {
|
|
11883
11946
|
const agents = listAgents(db);
|
|
@@ -12140,6 +12203,9 @@ module.exports = {
|
|
|
12140
12203
|
autoRouteNote,
|
|
12141
12204
|
autoRoutePreamble,
|
|
12142
12205
|
directSystemPrompt,
|
|
12206
|
+
// Test bridge: prove the resident judge is wired to API/Ollama/BYOK runtimes,
|
|
12207
|
+
// not only CLI subprocess runtimes.
|
|
12208
|
+
installJudgmentRunner,
|
|
12143
12209
|
// Hub 플러그인 설치 회귀 테스트 표면 — 레포 URL을 MCP 서버로 등록하지 않는 규칙 검증용.
|
|
12144
12210
|
pluginMcpRowCli,
|
|
12145
12211
|
planPluginMcpInstallCli,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "agentlas",
|
|
3
|
-
"version": "0.9.
|
|
3
|
+
"version": "0.9.7",
|
|
4
4
|
"description": "Agentlas agent terminal — chat with your installed AI agents and teams from the terminal, Claude Code style. Standalone: no desktop app required.",
|
|
5
5
|
"bin": {
|
|
6
6
|
"agentlas": "bin/agentlas.cjs"
|