@sagentlab/navarch-runtime 0.1.80 → 0.1.81

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/README.md CHANGED
@@ -959,7 +959,10 @@ different endpoint (for example, Ollama's `http://127.0.0.1:11434/v1`).
959
959
  `NAVARCH_PI_BIN` overrides the executable; `NAVARCH_PI_EXTRA_ARGS` adds CLI
960
960
  arguments. `--model` at connect pins this machine's model as for other agents.
961
961
 
962
- Bare model IDs use the generated `local` provider. Exact `provider/model`
962
+ Bare model IDs first resolve a unique matching model in the operator's catalog;
963
+ ambiguous matches require an explicit `provider/model`. Without a match, they
964
+ use the generated `local` provider. Setting `NAVARCH_PI_LOCAL_BASE_URL` explicitly
965
+ selects that generated provider. Exact `provider/model`
963
966
  references use the machine's existing Pi catalog and credentials from
964
967
  `~/.pi/agent/models.json` and `auth.json` (or `PI_CODING_AGENT_DIR`). Run
965
968
  `pi --list-models` to inspect that catalog. The UI puts the local default first
@@ -165,10 +165,20 @@ function attachPiOutput(result) {
165
165
  let costUsd;
166
166
  let sawUsage = false;
167
167
  let reportText = "";
168
+ let terminalError;
168
169
  for (const event of events) {
169
170
  const message = event.message;
171
+ if (event.type === "error") {
172
+ terminalError = typeof event.error === "string" ? event.error :
173
+ typeof event.errorMessage === "string" ? event.errorMessage : "Pi provider error";
174
+ }
170
175
  if (event.type !== "message_end" || !message || message.role !== "assistant")
171
176
  continue;
177
+ // Pi can settle an exhausted provider retry with process exit code zero.
178
+ // A later successful assistant message supersedes a recovered error.
179
+ terminalError = message.stopReason === "error" || message.errorMessage
180
+ ? typeof message.errorMessage === "string" ? message.errorMessage : "Pi provider error"
181
+ : undefined;
172
182
  const text = extractText(message.content);
173
183
  if (text.trim())
174
184
  reportText = text.trim();
@@ -193,6 +203,9 @@ function attachPiOutput(result) {
193
203
  }
194
204
  return {
195
205
  ...result,
206
+ ...(terminalError && result.exitCode === 0 && !result.timedOut && !result.killedByLeaseLoss
207
+ ? { exitCode: 1, stderr: `${result.stderr}${result.stderr ? "\n" : ""}Pi provider failed: ${terminalError}` }
208
+ : {}),
196
209
  ...(sawUsage
197
210
  ? {
198
211
  // AdapterResult semantics: tokensIn folds every input category
@@ -269,13 +282,23 @@ async function runOnHost(options, args, local = false) {
269
282
  const configPath = node_path_1.default.join(agentDir, "models.json");
270
283
  const config = JSON.parse(await node_fs_1.promises.readFile(configPath, "utf8").catch(() => "{}"));
271
284
  config.providers ??= {};
272
- // Explicit provider/model references use the machine's catalog unchanged.
273
- config.providers.local = {
274
- baseUrl: options.env.NAVARCH_PI_LOCAL_BASE_URL ?? process.env.NAVARCH_PI_LOCAL_BASE_URL ?? "http://127.0.0.1:8080/v1",
275
- api: "openai-completions", apiKey: "local",
276
- models: [{ id: model, reasoning: false, input: ["text"], cost: { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 } }],
277
- };
278
- await node_fs_1.promises.writeFile(configPath, JSON.stringify(config), { mode: 0o600 });
285
+ const endpointOverride = options.env.NAVARCH_PI_LOCAL_BASE_URL ?? process.env.NAVARCH_PI_LOCAL_BASE_URL;
286
+ const matches = endpointOverride ? [] : Object.entries(config.providers).filter(([, provider]) => provider.models?.some((entry) => entry.id === model)).map(([name]) => name);
287
+ if (matches.length > 1)
288
+ throw new Error(`Pi model ${model} matches multiple providers; select an explicit provider/model.`);
289
+ if (matches.length === 1) {
290
+ args = [...args];
291
+ args[args.lastIndexOf("--model") + 1] = `${matches[0]}/${model}`;
292
+ }
293
+ else {
294
+ // Without a catalog match, retain the default local endpoint behavior.
295
+ config.providers.local = {
296
+ baseUrl: endpointOverride ?? "http://127.0.0.1:8080/v1",
297
+ api: "openai-completions", apiKey: "local",
298
+ models: [{ id: model, reasoning: false, input: ["text"], cost: { input: 0, output: 0, cacheRead: 0, cacheWrite: 0 } }],
299
+ };
300
+ await node_fs_1.promises.writeFile(configPath, JSON.stringify(config), { mode: 0o600 });
301
+ }
279
302
  }
280
303
  if (options.mcpConfigPath) {
281
304
  await node_fs_1.promises.copyFile(options.mcpConfigPath, node_path_1.default.join(agentDir, "mcp.json"));
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sagentlab/navarch-runtime",
3
- "version": "0.1.80",
3
+ "version": "0.1.81",
4
4
  "description": "Navarch machine-side session manager: claims delivery tasks and runs them through local coding agents.",
5
5
  "type": "commonjs",
6
6
  "license": "MIT",