@pugi/cli 0.1.0-beta.37 → 0.1.0-beta.39

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.
@@ -2,10 +2,19 @@
2
2
  * β1 defaults. Source of truth for the per-command budget envelope.
3
3
  * The runtime is allowed to look these up directly (no need to round
4
4
  * trip through settings.json when no override is in play).
5
+ *
6
+ * 2026-05-28 bump (post-Wave-7 hooks-v2 + 6-perm-modes + auto-classifier
7
+ * added ~12K tokens of system-prompt + tools-schema overhead per turn):
8
+ * `code` 30k → 80k и `fix` 30k → 50k so a single-file refactor on a
9
+ * 1000-line source file no longer exhausts the budget on turn 2.
10
+ * Empirical: smoke `pugi code "сделай snake.html"` on beta.37 burned
11
+ * 36k/30k after 2 tool calls; beta.36 same task closed in 8k. The Wave-7
12
+ * additions are good (Claude Code parity), but the budget cap did not move with
13
+ * them. Claude Code's `code` default is ~80k; matching that restores headroom.
5
14
  */
6
15
  export const beta1DefaultBudgets = {
7
- fix: { maxTokens: 30_000, maxToolCalls: 20 },
8
- code: { maxTokens: 30_000, maxToolCalls: 20 },
16
+ fix: { maxTokens: 50_000, maxToolCalls: 20 },
17
+ code: { maxTokens: 80_000, maxToolCalls: 20 },
9
18
  build: { maxTokens: 200_000, maxToolCalls: 30 },
10
19
  plan: { maxTokens: 200_000, maxToolCalls: 8 },
11
20
  explain: { maxTokens: 20_000, maxToolCalls: 5 },
@@ -862,7 +862,14 @@ function extractPathArg(raw) {
862
862
  try {
863
863
  const parsed = JSON.parse(raw);
864
864
  if (parsed && typeof parsed === 'object' && !Array.isArray(parsed)) {
865
- const path = parsed.path;
865
+ const obj = parsed;
866
+ // Accept canonical `path` OR the Claude-Code-trained `filePath`
867
+ // alias so the filesChanged summary captures writes regardless of
868
+ // which key the model emitted. Without the alias the operator
869
+ // sees "Files modified: none" even when a write actually landed,
870
+ // because the dispatcher accepted the alias but the tracker did
871
+ // not (CEO live smoke 2026-05-28).
872
+ const path = obj['path'] ?? obj['filePath'];
866
873
  if (typeof path === 'string' && path.length > 0)
867
874
  return path;
868
875
  }
@@ -516,6 +516,23 @@ function requireString(obj, key) {
516
516
  return v;
517
517
  throw new Error(`tool argument "${key}" must be a string`);
518
518
  }
519
+ /**
520
+ * Accept `path` (canonical) or `filePath` (Claude Code convention) for
521
+ * write/edit/read tool arguments. Models trained on CC system prompts
522
+ * emit `filePath`; insisting on `path` only forces 2-3 retry waste on
523
+ * every file write (CEO live smoke 2026-05-28: snake.html dispatch
524
+ * burned 2 turns retrying `{filePath: ...}` payloads before falling
525
+ * back к bash heredoc). Defense-in-depth alias keeps canonical name
526
+ * (so persona prompts can still teach `path` as the right answer) AND
527
+ * tolerates the CC-trained variant without operator-visible failure.
528
+ */
529
+ function requirePathArg(obj) {
530
+ if (typeof obj['path'] === 'string')
531
+ return obj['path'];
532
+ if (typeof obj['filePath'] === 'string')
533
+ return obj['filePath'];
534
+ throw new Error('tool argument "path" must be a string (alias "filePath" also accepted)');
535
+ }
519
536
  export function buildExecutor(input) {
520
537
  const { kind, ctx, hooks, mvpHooksConfig, sessionId, askUserBridge, interactive, allowFetch, allowSearch, agentDispatch, mcpRegistry, permissionMode, permissionAlwaysCache, permissionAsk, } = input;
521
538
  // Leak L31: per-cycle budget. Default to a fresh instance scoped to
@@ -916,7 +933,7 @@ function extractToolPath(name, argsRaw) {
916
933
  function dispatchTool(name, args, ctx) {
917
934
  switch (name) {
918
935
  case 'read': {
919
- const { path } = { path: requireString(args, 'path') };
936
+ const { path } = { path: requirePathArg(args) };
920
937
  const content = readTool(ctx, path);
921
938
  // Cap the content surfaced back to the model so a 10MB file
922
939
  // does not blow the context window. The model sees the head
@@ -929,7 +946,7 @@ function dispatchTool(name, args, ctx) {
929
946
  }
930
947
  case 'write': {
931
948
  const wargs = {
932
- path: requireString(args, 'path'),
949
+ path: requirePathArg(args),
933
950
  content: requireString(args, 'content'),
934
951
  };
935
952
  writeTool(ctx, wargs.path, wargs.content);
@@ -937,7 +954,7 @@ function dispatchTool(name, args, ctx) {
937
954
  }
938
955
  case 'edit': {
939
956
  const eargs = {
940
- path: requireString(args, 'path'),
957
+ path: requirePathArg(args),
941
958
  oldString: requireString(args, 'oldString'),
942
959
  newString: requireString(args, 'newString'),
943
960
  };
@@ -1669,12 +1669,12 @@ const COMMAND_HELP_BODIES = {
1669
1669
  ' pugi explain "trace the auth flow in src/auth/"',
1670
1670
  ],
1671
1671
  code: [
1672
- 'pugi code "<brief>" — engineering-mode write loop (30k token budget).',
1672
+ 'pugi code "<brief>" — engineering-mode write loop (80k token budget).',
1673
1673
  '',
1674
1674
  'Writes files in the current workspace. Use --no-tty in CI / pipes.',
1675
1675
  ],
1676
1676
  fix: [
1677
- 'pugi fix "<brief>" — minimal-diff bugfix loop (30k token budget).',
1677
+ 'pugi fix "<brief>" — minimal-diff bugfix loop (50k token budget).',
1678
1678
  '',
1679
1679
  'Same as `pugi code` but the prompt biases toward the smallest patch',
1680
1680
  'that closes the brief — refuses scope creep / refactor invitations.',
@@ -44,7 +44,7 @@ export function sanitizeSemver(raw) {
44
44
  * during import). When bumping the CLI version BOTH literals must be
45
45
  * updated; the release smoke-test (`pack:smoke`) verifies they agree.
46
46
  */
47
- export const PUGI_CLI_VERSION = sanitizeSemver('0.1.0-beta.37');
47
+ export const PUGI_CLI_VERSION = sanitizeSemver('0.1.0-beta.39');
48
48
  /**
49
49
  * Outbound: the CLI's installed semver. Read at request time by
50
50
  * `version-interceptor.ts` and injected on every `fetch` call.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pugi/cli",
3
- "version": "0.1.0-beta.37",
3
+ "version": "0.1.0-beta.39",
4
4
  "description": "Pugi CLI - terminal-native software execution system",
5
5
  "homepage": "https://pugi.io",
6
6
  "repository": {
@@ -54,8 +54,8 @@
54
54
  "turndown": "^7.2.4",
55
55
  "undici": "^8.3.0",
56
56
  "zod": "^3.23.0",
57
- "@pugi/personas": "0.1.2",
58
- "@pugi/sdk": "0.1.0-beta.37"
57
+ "@pugi/sdk": "0.1.0-beta.39",
58
+ "@pugi/personas": "0.1.2"
59
59
  },
60
60
  "devDependencies": {
61
61
  "@types/node": "^22.0.0",