gsd-pi 0.2.3 → 0.2.5

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/dist/cli.js CHANGED
@@ -7,19 +7,27 @@ loadStoredEnvKeys(authStorage);
7
7
  await runWizardIfNeeded(authStorage);
8
8
  const modelRegistry = new ModelRegistry(authStorage);
9
9
  const settingsManager = SettingsManager.create(agentDir);
10
- // Auto-select a default model if none is configured.
11
- // This prevents the "No model configured" error for users who logged in
12
- // but never explicitly ran /model to pick one.
13
- if (!settingsManager.getDefaultModel()) {
14
- const availableModels = modelRegistry.getAvailable();
10
+ // Auto-select a default model if none is configured, or if the configured
11
+ // model no longer exists (e.g. stale settings referencing a retired model).
12
+ const configuredProvider = settingsManager.getDefaultProvider();
13
+ const configuredModel = settingsManager.getDefaultModel();
14
+ const availableModels = modelRegistry.getAvailable();
15
+ const configuredExists = configuredProvider && configuredModel &&
16
+ availableModels.some((m) => m.provider === configuredProvider && m.id === configuredModel);
17
+ if (!configuredModel || !configuredExists) {
15
18
  if (availableModels.length > 0) {
16
- // Prefer a mid-tier Anthropic model (sonnet), then any Anthropic, then first available
17
- const preferred = availableModels.find((m) => m.provider === 'anthropic' && m.id.includes('sonnet')) ||
19
+ // Preferred default: anthropic/claude-sonnet-4-6
20
+ const preferred = availableModels.find((m) => m.provider === 'anthropic' && m.id === 'claude-sonnet-4-6') ||
21
+ availableModels.find((m) => m.provider === 'anthropic' && m.id.includes('sonnet')) ||
18
22
  availableModels.find((m) => m.provider === 'anthropic') ||
19
23
  availableModels[0];
20
24
  settingsManager.setDefaultModelAndProvider(preferred.provider, preferred.id);
21
25
  }
22
26
  }
27
+ // Default thinking level: off
28
+ if (!settingsManager.getDefaultThinkingLevel()) {
29
+ settingsManager.setDefaultThinkingLevel('off');
30
+ }
23
31
  // GSD always uses quiet startup — the gsd extension renders its own branded header
24
32
  if (!settingsManager.getQuietStartup()) {
25
33
  settingsManager.setQuietStartup(true);
package/dist/loader.js CHANGED
@@ -38,7 +38,7 @@ if (!existsSync(appRoot)) {
38
38
  ` Get Shit Done ${dim}v${version}${reset}\n` +
39
39
  ` ${green}Welcome.${reset} Setting up your environment...\n\n`);
40
40
  }
41
- // GSD_CODING_AGENT_DIR — tells pi's getAgentDir() to return ~/.gsd/agent/ instead of ~/.pi/agent/
41
+ // GSD_CODING_AGENT_DIR — tells pi's getAgentDir() to return ~/.gsd/agent/ instead of ~/.gsd/agent/
42
42
  process.env.GSD_CODING_AGENT_DIR = agentDir;
43
43
  // NODE_PATH — make gsd's own node_modules available to extensions loaded via jiti.
44
44
  // Without this, extensions (e.g. browser-tools) can't resolve dependencies like
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "gsd-pi",
3
- "version": "0.2.3",
3
+ "version": "0.2.5",
4
4
  "description": "GSD — Get Stuff Done coding agent",
5
5
  "license": "MIT",
6
6
  "repository": {
@@ -132,7 +132,7 @@ auto_supervisor: {}
132
132
 
133
133
  Project-specific guidance for skill selection and execution preferences.
134
134
 
135
- See \`~/.pi/agent/extensions/gsd/docs/preferences-reference.md\` for full field documentation and examples.
135
+ See \`~/.gsd/agent/extensions/gsd/docs/preferences-reference.md\` for full field documentation and examples.
136
136
 
137
137
  ## Fields
138
138
 
@@ -107,7 +107,7 @@ export interface SkillResolutionReport {
107
107
 
108
108
  /**
109
109
  * Known skill directories, in priority order.
110
- * User skills (~/.pi/agent/skills/) take precedence over project skills.
110
+ * User skills (~/.gsd/agent/skills/) take precedence over project skills.
111
111
  */
112
112
  function getSkillSearchDirs(cwd: string): Array<{ dir: string; method: SkillResolution["method"] }> {
113
113
  return [
@@ -12,4 +12,4 @@ auto_supervisor: {}
12
12
 
13
13
  # GSD Skill Preferences
14
14
 
15
- See `~/.pi/agent/extensions/gsd/docs/preferences-reference.md` for full field documentation and examples.
15
+ See `~/.gsd/agent/extensions/gsd/docs/preferences-reference.md` for full field documentation and examples.
@@ -3,7 +3,7 @@ import { join, dirname } from "node:path";
3
3
  import { tmpdir } from "node:os";
4
4
  import { fileURLToPath } from "node:url";
5
5
 
6
- // loadPrompt reads from ~/.pi/agent/extensions/gsd/prompts/ (main checkout).
6
+ // loadPrompt reads from ~/.gsd/agent/extensions/gsd/prompts/ (main checkout).
7
7
  // In a worktree the file may not exist there yet, so we resolve prompts
8
8
  // relative to this test file's location (the worktree copy).
9
9
  const __dirname = dirname(fileURLToPath(import.meta.url));
@@ -2,7 +2,7 @@ import { readFileSync } from "node:fs";
2
2
  import { join, dirname } from "node:path";
3
3
  import { fileURLToPath } from "node:url";
4
4
 
5
- // loadPrompt reads from ~/.pi/agent/extensions/gsd/prompts/ (main checkout).
5
+ // loadPrompt reads from ~/.gsd/agent/extensions/gsd/prompts/ (main checkout).
6
6
  // In a worktree the file may not exist there yet, so we resolve prompts
7
7
  // relative to this test file's location (the worktree copy).
8
8
  const __dirname = dirname(fileURLToPath(import.meta.url));
@@ -221,41 +221,41 @@ function sendPrompt(description: string, result: RoundResult, pi: ExtensionAPI):
221
221
  : "";
222
222
 
223
223
  const docHints: string[] = [
224
- "- `~/.pi/agent/docs/extending-pi/01-what-are-extensions.md` — capabilities overview",
225
- "- `~/.pi/agent/docs/extending-pi/03-getting-started.md` — minimal extension, hot reload",
226
- "- `~/.pi/agent/docs/extending-pi/08-extensioncontext-what-you-can-access.md` — ExtensionContext API",
227
- "- `~/.pi/agent/docs/extending-pi/09-extensionapi-what-you-can-do.md` — ExtensionAPI: registration, messaging",
228
- "- `~/.pi/agent/docs/extending-pi/22-key-rules-gotchas.md` — must-read rules before shipping",
224
+ "- `~/.gsd/agent/docs/extending-pi/01-what-are-extensions.md` — capabilities overview",
225
+ "- `~/.gsd/agent/docs/extending-pi/03-getting-started.md` — minimal extension, hot reload",
226
+ "- `~/.gsd/agent/docs/extending-pi/08-extensioncontext-what-you-can-access.md` — ExtensionContext API",
227
+ "- `~/.gsd/agent/docs/extending-pi/09-extensionapi-what-you-can-do.md` — ExtensionAPI: registration, messaging",
228
+ "- `~/.gsd/agent/docs/extending-pi/22-key-rules-gotchas.md` — must-read rules before shipping",
229
229
  ];
230
230
 
231
231
  if (uiSelected.includes("custom component")) {
232
- docHints.push("- `~/.pi/agent/docs/extending-pi/12-custom-ui-visual-components.md` — dialogs, widgets, overlays");
233
- docHints.push("- `~/.pi/agent/docs/pi-ui-tui/06-ctx-ui-custom-full-custom-components.md` — ctx.ui.custom() API");
234
- docHints.push("- `~/.pi/agent/docs/pi-ui-tui/07-built-in-components-the-building-blocks.md` — Text, Box, SelectList");
235
- docHints.push("- `~/.pi/agent/docs/pi-ui-tui/09-keyboard-input-how-to-handle-keys.md` — Key, matchesKey");
236
- docHints.push("- `~/.pi/agent/docs/pi-ui-tui/10-line-width-the-cardinal-rule.md` — truncation, width rules");
237
- docHints.push("- `~/.pi/agent/docs/pi-ui-tui/19-building-a-complete-component-step-by-step.md` — step-by-step guide");
238
- docHints.push("- `~/.pi/agent/docs/pi-ui-tui/21-common-mistakes-and-how-to-avoid-them.md` — pitfalls");
232
+ docHints.push("- `~/.gsd/agent/docs/extending-pi/12-custom-ui-visual-components.md` — dialogs, widgets, overlays");
233
+ docHints.push("- `~/.gsd/agent/docs/pi-ui-tui/06-ctx-ui-custom-full-custom-components.md` — ctx.ui.custom() API");
234
+ docHints.push("- `~/.gsd/agent/docs/pi-ui-tui/07-built-in-components-the-building-blocks.md` — Text, Box, SelectList");
235
+ docHints.push("- `~/.gsd/agent/docs/pi-ui-tui/09-keyboard-input-how-to-handle-keys.md` — Key, matchesKey");
236
+ docHints.push("- `~/.gsd/agent/docs/pi-ui-tui/10-line-width-the-cardinal-rule.md` — truncation, width rules");
237
+ docHints.push("- `~/.gsd/agent/docs/pi-ui-tui/19-building-a-complete-component-step-by-step.md` — step-by-step guide");
238
+ docHints.push("- `~/.gsd/agent/docs/pi-ui-tui/21-common-mistakes-and-how-to-avoid-them.md` — pitfalls");
239
239
  } else if (uiSelected.includes("Dialogs")) {
240
- docHints.push("- `~/.pi/agent/docs/pi-ui-tui/04-built-in-dialog-methods.md` — select, confirm, input, editor");
240
+ docHints.push("- `~/.gsd/agent/docs/pi-ui-tui/04-built-in-dialog-methods.md` — select, confirm, input, editor");
241
241
  } else if (uiSelected.includes("Status")) {
242
- docHints.push("- `~/.pi/agent/docs/pi-ui-tui/05-persistent-ui-elements.md` — status, widgets, footer, header");
242
+ docHints.push("- `~/.gsd/agent/docs/pi-ui-tui/05-persistent-ui-elements.md` — status, widgets, footer, header");
243
243
  }
244
244
 
245
245
  if (uiSelected.includes("tool") || result.answers["purpose"]) {
246
- docHints.push("- `~/.pi/agent/docs/extending-pi/14-custom-rendering-controlling-what-the-user-sees.md` — renderCall / renderResult");
246
+ docHints.push("- `~/.gsd/agent/docs/extending-pi/14-custom-rendering-controlling-what-the-user-sees.md` — renderCall / renderResult");
247
247
  }
248
248
 
249
249
  if (eventsSelected && !eventsSelected.includes("standalone")) {
250
- docHints.push("- `~/.pi/agent/docs/extending-pi/07-events-the-nervous-system.md` — all events reference");
250
+ docHints.push("- `~/.gsd/agent/docs/extending-pi/07-events-the-nervous-system.md` — all events reference");
251
251
  }
252
252
 
253
253
  if (eventsSelected.includes("context / prompt")) {
254
- docHints.push("- `~/.pi/agent/docs/extending-pi/15-system-prompt-modification.md` — system prompt hooks");
254
+ docHints.push("- `~/.gsd/agent/docs/extending-pi/15-system-prompt-modification.md` — system prompt hooks");
255
255
  }
256
256
 
257
257
  if (persistenceSelected.includes("session")) {
258
- docHints.push("- `~/.pi/agent/docs/extending-pi/13-state-management-persistence.md` — pi.appendEntry, session state");
258
+ docHints.push("- `~/.gsd/agent/docs/extending-pi/13-state-management-persistence.md` — pi.appendEntry, session state");
259
259
  }
260
260
 
261
261
  const prompt = `Create a new pi extension based on this description:
@@ -272,11 +272,11 @@ ${docHints.join("\n")}
272
272
 
273
273
  Write the complete implementation as a single self-contained extension file:
274
274
 
275
- \`~/.pi/agent/extensions/<kebab-case-name>.ts\`
275
+ \`~/.gsd/agent/extensions/<kebab-case-name>.ts\`
276
276
 
277
277
  Then register it in the main extensions index:
278
278
 
279
- \`~/.pi/agent/extensions/index.ts\` — import and call the new extension's default export alongside existing ones
279
+ \`~/.gsd/agent/extensions/index.ts\` — import and call the new extension's default export alongside existing ones
280
280
 
281
281
  ## Rules you must follow exactly
282
282
 
@@ -211,8 +211,8 @@ function sendPrompt(description: string, result: RoundResult, pi: ExtensionAPI):
211
211
  ${contextSection}
212
212
  Write the complete file contents for two files:
213
213
 
214
- 1. \`~/.pi/agent/extensions/slash-commands/<name>.ts\` — the command implementation
215
- 2. Update \`~/.pi/agent/extensions/slash-commands/index.ts\` — import and register the new command alongside existing ones
214
+ 1. \`~/.gsd/agent/extensions/slash-commands/<name>.ts\` — the command implementation
215
+ 2. Update \`~/.gsd/agent/extensions/slash-commands/index.ts\` — import and register the new command alongside existing ones
216
216
 
217
217
  Rules you must follow exactly:
218
218
  - Command registration: \`pi.registerCommand("name", { description, handler })\`
@@ -418,7 +418,7 @@ export default function (pi: ExtensionAPI) {
418
418
  handler: async (_args, ctx) => {
419
419
  const discovery = discoverAgents(ctx.cwd, "both");
420
420
  if (discovery.agents.length === 0) {
421
- ctx.ui.notify("No agents found. Add .md files to ~/.pi/agent/agents/ or .pi/agents/", "warning");
421
+ ctx.ui.notify("No agents found. Add .md files to ~/.gsd/agent/agents/ or .gsd/agents/", "warning");
422
422
  return;
423
423
  }
424
424
  const lines = discovery.agents.map(
@@ -435,7 +435,7 @@ export default function (pi: ExtensionAPI) {
435
435
  "Delegate tasks to specialized subagents with isolated context windows.",
436
436
  "Each subagent is a separate pi process with its own tools, model, and system prompt.",
437
437
  "Modes: single ({ agent, task }), parallel ({ tasks: [{agent, task},...] }), chain ({ chain: [{agent, task},...] } with {previous} placeholder).",
438
- "Agents are defined as .md files in ~/.pi/agent/agents/ (user) or .pi/agents/ (project).",
438
+ "Agents are defined as .md files in ~/.gsd/agent/agents/ (user) or .gsd/agents/ (project).",
439
439
  "Use the /subagent command to list available agents and their descriptions.",
440
440
  "Use chain mode to pipeline: scout finds context, planner designs, worker implements.",
441
441
  ].join(" "),