@diegopetrucci/pi-extensions 0.1.48 → 0.1.50

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.
@@ -4,7 +4,7 @@ A pi GitHub research scout inspired by `pi-librarian`, with a local checkout cac
4
4
 
5
5
  When the `librarian` tool runs, it can cache/reuse repository checkouts locally. Use `/librarian-cache off` to force GitHub API/search and temporary fetched files only, or `/librarian-cache on` to re-enable cached local checkouts.
6
6
 
7
- The internal librarian subagent uses a lightweight auto-selected model by default and requests `medium` thinking. Use `/librarian-config` to set a persistent internal model or thinking-level preference.
7
+ The internal librarian subagent uses a fast auto-selected model by default, requests `low` thinking, and prompts its scout to batch independent GitHub probes in parallel. Use `/librarian-config` to set a persistent internal model or thinking-level preference.
8
8
 
9
9
  ## Install
10
10
 
@@ -39,7 +39,7 @@ Then reload pi:
39
39
  - Uses `gh` for GitHub search/API access
40
40
  - Uses cached local checkouts only when enabled
41
41
  - Toggle cache behavior for future calls with `/librarian-cache on | off | toggle | status`
42
- - Configure internal subagent defaults with `/librarian-config status | model <provider/model|auto|current> | thinking <off|minimal|low|medium|high|xhigh|auto> | clear [all|model|thinking]`
42
+ - Configure internal subagent defaults with `/librarian-config status | model <provider/model|auto> | thinking <off|minimal|low|medium|high|xhigh|auto> | clear [all|model|thinking]`
43
43
  - Cached repos are removed lazily after 7 days without use
44
44
 
45
45
  ## Commands
@@ -54,9 +54,8 @@ Then reload pi:
54
54
  ```text
55
55
  /librarian-config status
56
56
  /librarian-config model auto
57
- /librarian-config model current
58
57
  /librarian-config model anthropic/claude-haiku-4-5:medium
59
- /librarian-config thinking medium
58
+ /librarian-config thinking low
60
59
  /librarian-config clear model
61
60
  ```
62
61
 
@@ -33,9 +33,20 @@ type CacheMode = "disabled" | "enabled";
33
33
  type ThinkingLevel = "off" | "minimal" | "low" | "medium" | "high" | "xhigh";
34
34
 
35
35
  const DEFAULT_CACHE_MODE: CacheMode = "disabled";
36
- const DEFAULT_THINKING_LEVEL: ThinkingLevel = "medium";
36
+ const DEFAULT_THINKING_LEVEL: ThinkingLevel = "low";
37
37
  const THINKING_LEVELS = ["off", "minimal", "low", "medium", "high", "xhigh"] as const;
38
38
 
39
+ const PREFERRED_FAST_MODEL_PATTERNS = [
40
+ /\bgpt[-_. ]?5\.5(?:[-_. ].*)?\b(?:mini|nano|fast|lite)\b/,
41
+ /\bgpt[-_. ]?5(?:[-_. ].*)?\b(?:mini|nano|fast|lite)\b/,
42
+ /\bgpt[-_. ]?4(?:\.1|o)?(?:[-_. ].*)?\b(?:mini|nano)\b/,
43
+ /\bgemini\b.*\b(?:flash|flash-lite|lite)\b/,
44
+ /\bclaude\b.*\bhaiku\b/,
45
+ /\b(?:mistral|codestral)\b.*\b(?:small|mini|lite)\b/,
46
+ ];
47
+
48
+ const HEAVY_MODEL_PATTERN = /\b(?:opus|pro|ultra|max)\b/;
49
+
39
50
  type ToolCall = {
40
51
  id: string;
41
52
  name: string;
@@ -106,7 +117,7 @@ const LibrarianParams = Type.Object({
106
117
  ),
107
118
  model: Type.Optional(
108
119
  Type.String({
109
- description: "Optional model override for the internal librarian subagent. Use provider/model, auto, or current.",
120
+ description: "Optional model override for the internal librarian subagent. Use provider/model or auto.",
110
121
  }),
111
122
  ),
112
123
  thinkingLevel: Type.Optional(
@@ -308,7 +319,8 @@ function parseThinkingLevel(value: unknown): ThinkingLevel | undefined {
308
319
  function normalizeModelPreference(value: unknown): string | undefined {
309
320
  if (typeof value !== "string") return undefined;
310
321
  const trimmed = value.trim();
311
- if (!trimmed || trimmed.toLowerCase() === "auto") return undefined;
322
+ const normalized = trimmed.toLowerCase();
323
+ if (!trimmed || normalized === "auto" || normalized === "current") return undefined;
312
324
  return trimmed;
313
325
  }
314
326
 
@@ -317,7 +329,11 @@ function parseModelPreference(value: unknown): { model?: string; thinkingLevel?:
317
329
  if (!model) return {};
318
330
  const match = model.match(/^(.*):(off|minimal|low|medium|high|xhigh)$/i);
319
331
  if (!match?.[1]) return { model };
320
- return { model: match[1], thinkingLevel: parseThinkingLevel(match[2]) };
332
+ const baseModel = match[1].trim();
333
+ if (!baseModel || baseModel.toLowerCase() === "auto" || baseModel.toLowerCase() === "current") {
334
+ return { thinkingLevel: parseThinkingLevel(match[2]) };
335
+ }
336
+ return { model: baseModel, thinkingLevel: parseThinkingLevel(match[2]) };
321
337
  }
322
338
 
323
339
  async function readLibrarianPreferences(): Promise<LibrarianPreferences> {
@@ -415,11 +431,25 @@ function rankLibrarianModel(model: any): number {
415
431
  let score = modelCostScore(model) * 1_000_000;
416
432
  if (model.reasoning) score += 50;
417
433
  if (/\b(?:mini|nano|haiku|flash|lite|small|fast|instant)\b/.test(text)) score -= 10;
418
- if (/\b(?:opus|pro|ultra|max)\b/.test(text)) score += 1_000;
434
+ if (HEAVY_MODEL_PATTERN.test(text)) score += 1_000;
419
435
  if ((model.contextWindow ?? 0) < 32_000) score += 100;
420
436
  return score;
421
437
  }
422
438
 
439
+ function isPreferredFastLibrarianModel(model: any): boolean {
440
+ const text = `${model.provider ?? ""} ${model.id ?? ""} ${model.name ?? ""}`.toLowerCase();
441
+ if (HEAVY_MODEL_PATTERN.test(text)) return false;
442
+ return PREFERRED_FAST_MODEL_PATTERNS.some((pattern) => pattern.test(text));
443
+ }
444
+
445
+ function rankPreferredFastLibrarianModel(model: any): number {
446
+ const text = `${model.provider ?? ""} ${model.id ?? ""} ${model.name ?? ""}`.toLowerCase();
447
+ let score = rankLibrarianModel(model);
448
+ const patternIndex = PREFERRED_FAST_MODEL_PATTERNS.findIndex((pattern) => pattern.test(text));
449
+ if (patternIndex >= 0) score += patternIndex * 100;
450
+ return score;
451
+ }
452
+
423
453
  async function findAvailableModel(
424
454
  ctx: { model?: any; modelRegistry: { getAvailable(): any[] | Promise<any[]> } },
425
455
  modelPreference: string,
@@ -453,21 +483,6 @@ async function selectLibrarianModel(
453
483
  thinkingLevel: ThinkingLevel,
454
484
  ): Promise<{ model: any; details: LibrarianModelDetails }> {
455
485
  const normalized = modelPreference?.trim();
456
- if (normalized?.toLowerCase() === "current") {
457
- if (!ctx.model) throw new Error("Librarian model=current needs an active pi model, but ctx.model is unavailable.");
458
- return {
459
- model: ctx.model,
460
- details: {
461
- modelRef: modelRef(ctx.model),
462
- provider: ctx.model.provider,
463
- modelId: ctx.model.id,
464
- thinkingLevel,
465
- autoSelected: false,
466
- selectionReason: "Using the caller's current model because librarian model=current is configured.",
467
- },
468
- };
469
- }
470
-
471
486
  if (normalized) {
472
487
  const matched = await findAvailableModel(ctx, normalized);
473
488
  if (matched) {
@@ -486,15 +501,18 @@ async function selectLibrarianModel(
486
501
  }
487
502
 
488
503
  const available = await ctx.modelRegistry.getAvailable();
489
- const currentProvider = ctx.model?.provider;
490
- const sameProvider = currentProvider ? available.filter((model) => model.provider === currentProvider) : [];
491
- const candidates = sameProvider.length > 0 ? sameProvider : available;
492
- const winner = [...candidates].sort((a, b) => rankLibrarianModel(a) - rankLibrarianModel(b))[0] ?? ctx.model;
504
+ const preferred = available.filter(isPreferredFastLibrarianModel);
505
+ const winner = preferred.length > 0
506
+ ? [...preferred].sort((a, b) => rankPreferredFastLibrarianModel(a) - rankPreferredFastLibrarianModel(b))[0]
507
+ : [...available].sort((a, b) => rankLibrarianModel(a) - rankLibrarianModel(b))[0];
493
508
  if (!winner) {
494
509
  throw new Error("No authenticated models are available for Librarian. Log in or configure an API key first.");
495
510
  }
496
511
 
497
512
  const fallbackText = normalized ? ` Configured model ${normalized} was unavailable, so Librarian fell back to auto-selection.` : "";
513
+ const selectionReason = preferred.length > 0
514
+ ? `Selected a preferred fast Librarian model.${fallbackText}`
515
+ : `Selected the cheapest available model because no preferred fast Librarian model was available.${fallbackText}`;
498
516
  return {
499
517
  model: winner,
500
518
  details: {
@@ -503,7 +521,7 @@ async function selectLibrarianModel(
503
521
  modelId: winner.id,
504
522
  thinkingLevel,
505
523
  autoSelected: true,
506
- selectionReason: `Selected the cheapest available model${sameProvider.length > 0 ? " on the current provider" : ""}.${fallbackText}`,
524
+ selectionReason,
507
525
  },
508
526
  };
509
527
  }
@@ -621,7 +639,7 @@ function buildSystemPrompt(options: {
621
639
  ? `\nLocal checkout cache is ENABLED for this call.\n- Cache root: ${options.cacheRoot}\n- Use checkout path pattern: ${options.cacheRoot}/github.com/<owner>/<repo>\n- Reuse an existing checkout when it has a .git directory. Fetch/prune before relying on it: git -C "$DIR" fetch --all --prune --tags --quiet\n- If missing, clone with gh repo clone "$REPO" "$DIR" (or git clone https://github.com/$REPO.git "$DIR").\n- If a ref/branch/SHA is requested, fetch it and check it out locally before citing files from that ref.\n- After using a checkout, update its cache marker: touch "$DIR/${CACHE_MARKER_FILE}"\n- Prefer local rg/read inside cached checkouts once a repo is cloned, and cite absolute cached paths with line ranges.\n- Clone only repositories that are relevant to the query; do not bulk-clone broad owner/org scopes unless necessary.`
622
640
  : `\nLocal checkout cache is DISABLED for this call.\n- Do not clone repositories.\n- Use gh search/API/tree/contents calls and cache only necessary proof files under ${options.workspace}/repos/<owner>/<repo>/<path>.`;
623
641
 
624
- return `You are Librarian, an evidence-first GitHub code scout running inside pi.\n\nUse only the available bash/read tools. Use gh, jq, rg, find/fd, ls, stat, mkdir, base64, and nl -ba for GitHub reconnaissance and numbered evidence. Use read for focused local file inspection.\n\nWorkspace: ${options.workspace}\nDefault gh search limit: ${options.maxSearchResults}\nTurn budget: ${MAX_TURNS} turns total, including your final answer. Stop searching once you have enough evidence.\n${cacheSection}\n\nNon-negotiable constraints:\n- Never treat gh search snippets as proof by themselves. Use fetched files or local checkouts for code-content claims.\n- Keep temporary workspace writes under ${options.workspace}/repos unless local checkout cache is enabled, in which case writes under the cache root are also allowed.
642
+ return `You are Librarian, an evidence-first GitHub code scout running inside pi.\n\nUse only the available bash/read tools. Use gh, jq, rg, find/fd, ls, stat, mkdir, base64, and nl -ba for GitHub reconnaissance and numbered evidence. Use read for focused local file inspection.\n\nWorkspace: ${options.workspace}\nDefault gh search limit: ${options.maxSearchResults}\nTurn budget: ${MAX_TURNS} turns total, including your final answer. Stop searching once you have enough evidence.\n${cacheSection}\n\nPerformance guidance:\n- Prefer fast, parallel exploration. When probes are independent, issue multiple separate tool calls in the same assistant turn instead of waiting for each result one-by-one.\n- Aim for 4-8 independent bash/read calls in an exploration turn when useful: parallel gh searches, tree probes, contents fetches, and targeted file reads.\n- Keep dependent work sequential, and avoid concurrent writes to the same file, checkout, or cache directory.\n\nNon-negotiable constraints:\n- Never treat gh search snippets as proof by themselves. Use fetched files or local checkouts for code-content claims.\n- Keep temporary workspace writes under ${options.workspace}/repos unless local checkout cache is enabled, in which case writes under the cache root are also allowed.
625
643
  - A runtime guard blocks destructive shell commands, credential/environment inspection, and reads outside the workspace/cache.\n- Never paste whole files. Use short snippets only when they clarify the evidence.\n- If evidence is partial or access fails (404/403), state the limitation clearly.\n- Do not present anything as fact unless it appeared in tool output or in a file you read.\n\nRecommended search flow:\n1. If symbols/text are known, start with gh search code and the provided repo/owner filters.\n2. If a repo is known but paths are unclear, resolve the default branch and inspect the git tree or contents API.\n3. Fetch or clone only the files/repos required to prove the answer.\n4. Use rg/read/nl -ba locally to produce stable path and line evidence.\n\nUseful gh patterns:\n- gh repo view "$REPO" --json defaultBranchRef --jq '.defaultBranchRef.name'\n- gh search code '<terms>' --json path,repository,sha,url,textMatches --limit ${options.maxSearchResults}\n- gh api "repos/$REPO/git/trees/$REF?recursive=1" > tree.json\n- gh api "repos/$REPO/contents/$FILE?ref=$REF" --jq .content | tr -d '\\n' | base64 --decode > "repos/$REPO/$FILE"\n- rg -n '<pattern>' '<local path>'\n- nl -ba '<local file>' | sed -n '10,30p'\n\nOutput format, exact order:\n## Summary\n1-3 concise sentences.\n## Locations\n- \`path\` or \`path:lineStart-lineEnd\` — what is here and why it matters; include GitHub URL when useful. If nothing relevant is found, write \`- (none)\`.\n## Evidence\n- \`path\` or \`path:lineStart-lineEnd\` — what this proves. Include concise snippets only if useful.\n## Searched\nOnly include when incomplete/not found or when the search path matters. List queries, filters, and probes used.\n## Next steps\nOptional: 1-3 narrow follow-up checks for remaining ambiguity.`;
626
644
  }
627
645
 
@@ -767,16 +785,20 @@ export default function librarianExtension(pi: ExtensionAPI) {
767
785
  if (action === "model") {
768
786
  const value = rest.join(" ").trim();
769
787
  if (!value) {
770
- notifyCommand(ctx, "Usage: /librarian-config model <provider/model|auto|current>", "warning");
788
+ notifyCommand(ctx, "Usage: /librarian-config model <provider/model|auto>", "warning");
771
789
  return;
772
790
  }
773
791
  const normalized = value.toLowerCase();
792
+ if (normalized === "current" || normalized.startsWith("current:")) {
793
+ notifyCommand(ctx, "Librarian model=current is no longer supported. Use /librarian-config model auto or choose an explicit provider/model.", "warning");
794
+ return;
795
+ }
774
796
  const parsedModel = parseModelPreference(value);
775
797
  const next = normalized === "auto" || normalized === "clear" || normalized === "default"
776
798
  ? { ...currentPreferences(), model: undefined }
777
799
  : {
778
800
  ...currentPreferences(),
779
- model: normalized === "current" ? "current" : parsedModel.model,
801
+ model: parsedModel.model,
780
802
  thinkingLevel: parsedModel.thinkingLevel ?? thinkingPreference,
781
803
  };
782
804
  const warning = await savePreferences(next);
@@ -817,7 +839,7 @@ export default function librarianExtension(pi: ExtensionAPI) {
817
839
  return;
818
840
  }
819
841
 
820
- notifyCommand(ctx, "Usage: /librarian-config status | model <provider/model|auto|current> | thinking <off|minimal|low|medium|high|xhigh|auto> | clear [all|model|thinking]", "warning");
842
+ notifyCommand(ctx, "Usage: /librarian-config status | model <provider/model|auto> | thinking <off|minimal|low|medium|high|xhigh|auto> | clear [all|model|thinking]", "warning");
821
843
  },
822
844
  });
823
845
 
@@ -896,7 +918,7 @@ export default function librarianExtension(pi: ExtensionAPI) {
896
918
  description:
897
919
  "GitHub research scout for coding and personal-assistant tasks. Use when the answer likely lives in GitHub repos, exact repo/path locations are unknown, or you'd otherwise do exploratory gh search/tree probes plus local rg/read inspection. Librarian uses an optional 7-day local checkout cache that is disabled by default; toggle it with /librarian-cache. Configure its internal subagent defaults with /librarian-config.",
898
920
  promptSnippet:
899
- "Research GitHub repositories with evidence-first path and line citations; local checkout cache is disabled by default and user-toggleable with /librarian-cache. Internal subagent defaults are user-configurable with /librarian-config and default to medium thinking.",
921
+ "Research GitHub repositories with evidence-first path and line citations; local checkout cache is disabled by default and user-toggleable with /librarian-cache. Internal subagent defaults are user-configurable with /librarian-config and default to low thinking.",
900
922
  promptGuidelines: [
901
923
  "Use librarian when the answer likely requires exploratory GitHub repository search or line-cited evidence from external repos.",
902
924
  "Do not use librarian for files already present in the current workspace unless the user asks for external GitHub research.",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@diegopetrucci/pi-librarian",
3
- "version": "0.1.5",
3
+ "version": "0.1.6",
4
4
  "description": "A pi GitHub research scout with a toggleable local repo checkout cache under the user's OS cache directory.",
5
5
  "keywords": [
6
6
  "pi-package",
@@ -114,6 +114,7 @@ const PROVIDER_MODEL_PREFERENCES: Record<string, string[]> = {
114
114
  "claude-sonnet-4",
115
115
  "claude-3-7-sonnet",
116
116
  ],
117
+ "ant-ling": ["Ling-2.6-1T", "Ling-2.6-flash"],
117
118
  "azure-openai-responses": [
118
119
  "gpt-5.5-pro",
119
120
  "gpt-5.5",
@@ -146,6 +147,8 @@ const PROVIDER_MODEL_PREFERENCES: Record<string, string[]> = {
146
147
  "workers-ai/@cf/zai-org/glm-4.7-flash",
147
148
  ],
148
149
  "cloudflare-workers-ai": [
150
+ "@cf/moonshotai/kimi-k2.7-code",
151
+ "@cf/zai-org/glm-5.2",
149
152
  "@cf/moonshotai/kimi-k2.6",
150
153
  "@cf/nvidia/nemotron-3-120b-a12b",
151
154
  "@cf/moonshotai/kimi-k2.5",
@@ -155,9 +158,14 @@ const PROVIDER_MODEL_PREFERENCES: Record<string, string[]> = {
155
158
  deepseek: ["deepseek-v4-pro", "deepseek-v4-flash"],
156
159
  fireworks: [
157
160
  "accounts/fireworks/models/deepseek-v4-pro",
158
- "accounts/fireworks/models/kimi-k2p6",
161
+ "accounts/fireworks/models/kimi-k2p7-code",
162
+ "accounts/fireworks/routers/kimi-k2p7-code-fast",
163
+ "accounts/fireworks/models/glm-5p2",
164
+ "accounts/fireworks/models/minimax-m3",
159
165
  "accounts/fireworks/models/glm-5p1",
166
+ "accounts/fireworks/models/kimi-k2p6",
160
167
  "accounts/fireworks/models/minimax-m2p7",
168
+ "accounts/fireworks/models/qwen3p7-plus",
161
169
  "accounts/fireworks/models/qwen3p6-plus",
162
170
  "accounts/fireworks/models/gpt-oss-120b",
163
171
  ],
@@ -217,9 +225,9 @@ const PROVIDER_MODEL_PREFERENCES: Record<string, string[]> = {
217
225
  "MiniMaxAI/MiniMax-M2.5",
218
226
  "Qwen/Qwen3-Coder-Next",
219
227
  ],
220
- "kimi-coding": ["k2p6", "kimi-k2-thinking", "kimi-for-coding"],
221
- minimax: ["MiniMax-M2.7-highspeed", "MiniMax-M2.7"],
222
- "minimax-cn": ["MiniMax-M2.7-highspeed", "MiniMax-M2.7"],
228
+ "kimi-coding": ["k2p7", "kimi-k2-thinking", "kimi-for-coding"],
229
+ minimax: ["MiniMax-M3", "MiniMax-M2.7-highspeed", "MiniMax-M2.7"],
230
+ "minimax-cn": ["MiniMax-M3", "MiniMax-M2.7-highspeed", "MiniMax-M2.7"],
223
231
  mistral: [
224
232
  "mistral-medium-2604",
225
233
  "mistral-medium-3.5",
@@ -285,11 +293,16 @@ const PROVIDER_MODEL_PREFERENCES: Record<string, string[]> = {
285
293
  ],
286
294
  "opencode-go": [
287
295
  "deepseek-v4-pro",
296
+ "glm-5.2",
288
297
  "glm-5.1",
298
+ "qwen3.7-max",
299
+ "qwen3.7-plus",
289
300
  "qwen3.6-plus",
290
301
  "mimo-v2.5-pro",
291
302
  "mimo-v2-pro",
303
+ "minimax-m3",
292
304
  "minimax-m2.7",
305
+ "kimi-k2.7-code",
293
306
  "kimi-k2.6",
294
307
  "kimi-k2.5",
295
308
  ],
@@ -310,20 +323,26 @@ const PROVIDER_MODEL_PREFERENCES: Record<string, string[]> = {
310
323
  "google/gemini-3.1-pro-preview-customtools",
311
324
  "google/gemini-3.1-pro-preview",
312
325
  "google/gemini-2.5-pro",
326
+ "moonshotai/kimi-k2.7-code",
313
327
  "moonshotai/kimi-k2.6",
314
328
  "moonshotai/kimi-k2-thinking",
315
329
  "deepseek/deepseek-v4-pro",
316
330
  "deepseek/deepseek-r1",
317
331
  "deepseek/deepseek-v3.2",
332
+ "minimax/minimax-m3",
318
333
  "minimax/minimax-m2.7",
319
334
  "minimax/minimax-m2.1",
335
+ "z-ai/glm-5.2",
320
336
  "z-ai/glm-5.1",
321
337
  ],
322
338
  together: [
323
339
  "deepseek-ai/DeepSeek-V4-Pro",
324
340
  "zai-org/GLM-5.1",
341
+ "moonshotai/Kimi-K2.7-Code",
325
342
  "moonshotai/Kimi-K2.6",
343
+ "Qwen/Qwen3.7-Max",
326
344
  "Qwen/Qwen3.6-Plus",
345
+ "MiniMaxAI/MiniMax-M3",
327
346
  "MiniMaxAI/MiniMax-M2.7",
328
347
  "Qwen/Qwen3.5-397B-A17B",
329
348
  "Qwen/Qwen3-Coder-Next-FP8",
@@ -347,15 +366,21 @@ const PROVIDER_MODEL_PREFERENCES: Record<string, string[]> = {
347
366
  "openai/gpt-5.4",
348
367
  "openai/gpt-5.1-codex",
349
368
  "openai/gpt-5-codex",
369
+ "moonshotai/kimi-k2.7-code",
370
+ "moonshotai/kimi-k2.7-code-highspeed",
350
371
  "moonshotai/kimi-k2.6",
351
372
  "moonshotai/kimi-k2-thinking",
352
373
  "deepseek/deepseek-v4-pro",
353
374
  "deepseek/deepseek-v3.2-thinking",
375
+ "alibaba/qwen3.7-max",
376
+ "alibaba/qwen3.7-plus",
354
377
  "alibaba/qwen3.5-plus",
355
378
  "alibaba/qwen3-max-thinking",
356
379
  "google/gemini-3.1-pro-preview",
357
380
  "google/gemini-3-flash",
358
381
  "xai/grok-4.3",
382
+ "minimax/minimax-m3",
383
+ "zai/glm-5.2",
359
384
  "zai/glm-5.1",
360
385
  ],
361
386
  xai: [
@@ -390,7 +415,18 @@ const PROVIDER_MODEL_PREFERENCES: Record<string, string[]> = {
390
415
  "mimo-v2-omni",
391
416
  "mimo-v2-flash",
392
417
  ],
418
+ nvidia: [
419
+ "nvidia/nemotron-3-ultra-550b-a55b",
420
+ "nvidia/nemotron-3-super-120b-a12b",
421
+ "moonshotai/kimi-k2.6",
422
+ "z-ai/glm-5.1",
423
+ "qwen/qwen3.5-122b-a10b",
424
+ "openai/gpt-oss-120b",
425
+ "nvidia/nemotron-3-nano-omni-30b-a3b-reasoning",
426
+ "nvidia/nemotron-3-nano-30b-a3b",
427
+ ],
393
428
  zai: [
429
+ "glm-5.2",
394
430
  "glm-5.1",
395
431
  "glm-5-turbo",
396
432
  "glm-5v-turbo",
@@ -401,8 +437,17 @@ const PROVIDER_MODEL_PREFERENCES: Record<string, string[]> = {
401
437
  "glm-4.5v",
402
438
  "glm-4.5-air",
403
439
  ],
404
- moonshotai: ["kimi-k2.6", "kimi-k2-thinking-turbo", "kimi-k2-thinking", "kimi-k2.5"],
405
- "moonshotai-cn": ["kimi-k2.6", "kimi-k2-thinking-turbo", "kimi-k2-thinking", "kimi-k2.5"],
440
+ "zai-coding-cn": [
441
+ "glm-5.2",
442
+ "glm-5.1",
443
+ "glm-5-turbo",
444
+ "glm-5v-turbo",
445
+ "glm-5",
446
+ "glm-4.7",
447
+ "glm-4.5-air",
448
+ ],
449
+ moonshotai: ["kimi-k2.7-code", "kimi-k2.7-code-highspeed", "kimi-k2.6", "kimi-k2-thinking-turbo", "kimi-k2-thinking", "kimi-k2.5"],
450
+ "moonshotai-cn": ["kimi-k2.7-code", "kimi-k2.7-code-highspeed", "kimi-k2.6", "kimi-k2-thinking-turbo", "kimi-k2-thinking", "kimi-k2.5"],
406
451
  };
407
452
 
408
453
  const ORACLE_SYSTEM_PROMPT = [
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@diegopetrucci/pi-oracle",
3
- "version": "0.1.13",
3
+ "version": "0.1.14",
4
4
  "description": "An Amp-style oracle extension for pi that consults the strongest reasoning model on your current provider.",
5
5
  "keywords": [
6
6
  "pi-package",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@diegopetrucci/pi-extensions",
3
- "version": "0.1.48",
3
+ "version": "0.1.50",
4
4
  "description": "A collection of pi extensions and skills for annotation UIs, context management, workflow audits, review-comment triage, notifications, brrr push alerts, safety guards, GitHub research, repo-local knowledge, todos, tool rendering, model/provider helpers, and Xiaohei-style article illustrations.",
5
5
  "keywords": [
6
6
  "pi-package",
@@ -67,9 +67,9 @@
67
67
  ]
68
68
  },
69
69
  "devDependencies": {
70
- "@earendil-works/pi-ai": "^0.78.0",
71
- "@earendil-works/pi-coding-agent": "^0.78.0",
72
- "@earendil-works/pi-tui": "^0.78.0",
70
+ "@earendil-works/pi-ai": "^0.79.10",
71
+ "@earendil-works/pi-coding-agent": "^0.79.10",
72
+ "@earendil-works/pi-tui": "^0.79.10",
73
73
  "@types/node": "^25.9.1",
74
74
  "husky": "^9.1.7",
75
75
  "typebox": "^1.1.38",