my-pi 0.1.31 → 0.1.33

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/api.d.ts CHANGED
@@ -12,6 +12,9 @@ import * as _$_spences10_pi_sqlite_tools0 from "@spences10/pi-sqlite-tools";
12
12
  import * as _$_spences10_pi_confirm_destructive0 from "@spences10/pi-confirm-destructive";
13
13
  import * as _$_spences10_pi_team_mode0 from "@spences10/pi-team-mode";
14
14
 
15
+ //#region src/extensions/startup-screen/index.d.ts
16
+ declare function startup_screen_extension(pi: ExtensionAPI): void;
17
+ //#endregion
15
18
  //#region src/extensions/prompt-presets/index.d.ts
16
19
  declare function prompt_presets(pi: ExtensionAPI): Promise<void>;
17
20
  //#endregion
@@ -115,6 +118,22 @@ declare const BUILTIN_EXTENSION_REGISTRY: readonly [{
115
118
  readonly cli_description: "Disable mcp-sqlite-tools reminder extension";
116
119
  readonly aliases: readonly ["sqlite-tools", "sqlite", "mcp-sqlite-tools"];
117
120
  readonly load: () => Promise<typeof _$_spences10_pi_sqlite_tools0.default>;
121
+ }, {
122
+ readonly key: "startup-screen";
123
+ readonly label: "Startup screen";
124
+ readonly docs_label: "Startup screen";
125
+ readonly description: "Pixel-art gradient startup header for interactive sessions";
126
+ readonly default_enabled: true;
127
+ readonly option_name: "startup_screen";
128
+ readonly cli_arg: "no-startup-screen";
129
+ readonly cli_flag: "--no-startup-screen";
130
+ readonly cli_description: "Disable the custom startup screen";
131
+ readonly aliases: readonly ["startup-screen", "startup", "header", "splash"];
132
+ readonly mode_constraints: {
133
+ readonly disabled_in: readonly ["print", "json", "rpc"];
134
+ readonly reason: "Startup screen only renders in the interactive TUI";
135
+ };
136
+ readonly load: () => Promise<typeof startup_screen_extension>;
118
137
  }, {
119
138
  readonly key: "prompt-presets";
120
139
  readonly label: "Prompt presets";
package/dist/api.js CHANGED
@@ -1,4 +1,4 @@
1
- import { n as BUILTIN_EXTENSION_REGISTRY, t as BUILTIN_EXTENSIONS } from "./builtin-registry-Dwgexb9N.js";
1
+ import { n as BUILTIN_EXTENSION_REGISTRY, t as BUILTIN_EXTENSIONS } from "./builtin-registry-BM3CCt86.js";
2
2
  import { createRequire } from "node:module";
3
3
  import { existsSync, mkdirSync, readFileSync, renameSync, writeFileSync } from "node:fs";
4
4
  import { dirname, isAbsolute, join, relative, resolve } from "node:path";
@@ -128,6 +128,32 @@ const BUILTIN_EXTENSION_REGISTRY = [
128
128
  ],
129
129
  load: async () => (await import("@spences10/pi-sqlite-tools")).default
130
130
  },
131
+ {
132
+ key: "startup-screen",
133
+ label: "Startup screen",
134
+ docs_label: "Startup screen",
135
+ description: "Pixel-art gradient startup header for interactive sessions",
136
+ default_enabled: true,
137
+ option_name: "startup_screen",
138
+ cli_arg: "no-startup-screen",
139
+ cli_flag: "--no-startup-screen",
140
+ cli_description: "Disable the custom startup screen",
141
+ aliases: [
142
+ "startup-screen",
143
+ "startup",
144
+ "header",
145
+ "splash"
146
+ ],
147
+ mode_constraints: {
148
+ disabled_in: [
149
+ "print",
150
+ "json",
151
+ "rpc"
152
+ ],
153
+ reason: "Startup screen only renders in the interactive TUI"
154
+ },
155
+ load: async () => (await import("./startup-screen-DFywkmul.js")).default
156
+ },
131
157
  {
132
158
  key: "prompt-presets",
133
159
  label: "Prompt presets",
@@ -231,4 +257,4 @@ const BUILTIN_EXTENSIONS = BUILTIN_EXTENSION_REGISTRY.map(({ load: _load, ...ext
231
257
  //#endregion
232
258
  export { BUILTIN_EXTENSION_REGISTRY as n, BUILTIN_EXTENSIONS as t };
233
259
 
234
- //# sourceMappingURL=builtin-registry-Dwgexb9N.js.map
260
+ //# sourceMappingURL=builtin-registry-BM3CCt86.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"builtin-registry-BM3CCt86.js","names":[],"sources":["../src/extensions/builtin-registry.ts"],"sourcesContent":["import type { ExtensionFactory } from '@mariozechner/pi-coding-agent';\n\nexport type BuiltinExtensionRuntimeMode =\n\t| 'interactive'\n\t| 'print'\n\t| 'json'\n\t| 'rpc';\n\ntype BuiltinExtensionLoader = () => Promise<ExtensionFactory>;\n\nexport interface BuiltinExtensionManifestEntry {\n\tkey: string;\n\tlabel: string;\n\tdocs_label: string;\n\tdescription: string;\n\tdefault_enabled: boolean;\n\toption_name: string;\n\tcli_arg: string;\n\tcli_flag: `--${string}`;\n\tcli_description: string;\n\taliases: readonly string[];\n\tmode_constraints?: {\n\t\tdisabled_in: readonly BuiltinExtensionRuntimeMode[];\n\t\treason: string;\n\t};\n\tload: BuiltinExtensionLoader;\n}\n\nexport const BUILTIN_EXTENSION_REGISTRY = [\n\t{\n\t\tkey: 'context-sidecar',\n\t\tlabel: 'Context sidecar',\n\t\tdocs_label: 'SQLite context sidecar',\n\t\tdescription: 'Local SQLite FTS sidecar for oversized tool output',\n\t\tdefault_enabled: true,\n\t\toption_name: 'context_sidecar',\n\t\tcli_arg: 'no-context-sidecar',\n\t\tcli_flag: '--no-context-sidecar',\n\t\tcli_description:\n\t\t\t'Disable SQLite context sidecar for large tool output',\n\t\taliases: ['context-sidecar', 'context', 'sidecar'],\n\t\tload: async () => (await import('@spences10/pi-context')).default,\n\t},\n\t{\n\t\tkey: 'mcp',\n\t\tlabel: 'MCP',\n\t\tdocs_label: 'MCP',\n\t\tdescription: 'MCP server integration and /mcp command',\n\t\tdefault_enabled: true,\n\t\toption_name: 'mcp',\n\t\tcli_arg: 'no-mcp',\n\t\tcli_flag: '--no-mcp',\n\t\tcli_description: 'Disable built-in MCP extension',\n\t\taliases: ['mcp'],\n\t\tload: async () => (await import('@spences10/pi-mcp')).default,\n\t},\n\t{\n\t\tkey: 'skills',\n\t\tlabel: 'Skills',\n\t\tdocs_label: 'Skills',\n\t\tdescription: 'Managed pi-native skills and /skills command',\n\t\tdefault_enabled: true,\n\t\toption_name: 'skills',\n\t\tcli_arg: 'no-skills',\n\t\tcli_flag: '--no-skills',\n\t\tcli_description: 'Disable built-in skills extension',\n\t\taliases: ['skills', 'skill'],\n\t\tload: async () => (await import('@spences10/pi-skills')).default,\n\t},\n\t{\n\t\tkey: 'filter-output',\n\t\tlabel: 'Secret redaction',\n\t\tdocs_label: 'Secret redaction',\n\t\tdescription:\n\t\t\t'Redacts secrets from tool output before the model sees them',\n\t\tdefault_enabled: true,\n\t\toption_name: 'filter_output',\n\t\tcli_arg: 'no-filter',\n\t\tcli_flag: '--no-filter',\n\t\tcli_description: 'Disable secret redaction in tool output',\n\t\taliases: [\n\t\t\t'filter-output',\n\t\t\t'filter_output',\n\t\t\t'filter',\n\t\t\t'redaction',\n\t\t\t'secret-redaction',\n\t\t\t'output-redaction',\n\t\t],\n\t\tload: async () => (await import('@spences10/pi-redact')).default,\n\t},\n\t{\n\t\tkey: 'recall',\n\t\tlabel: 'Recall',\n\t\tdocs_label: 'Recall',\n\t\tdescription: 'pirecall reminder and background session sync',\n\t\tdefault_enabled: true,\n\t\toption_name: 'recall',\n\t\tcli_arg: 'no-recall',\n\t\tcli_flag: '--no-recall',\n\t\tcli_description: 'Disable recall extension',\n\t\taliases: ['recall', 'pirecall'],\n\t\tload: async () => (await import('@spences10/pi-recall')).default,\n\t},\n\t{\n\t\tkey: 'nopeek',\n\t\tlabel: 'Nopeek',\n\t\tdocs_label: 'Nopeek',\n\t\tdescription:\n\t\t\t'nopeek reminder for secret-safe environment loading',\n\t\tdefault_enabled: true,\n\t\toption_name: 'nopeek',\n\t\tcli_arg: 'no-nopeek',\n\t\tcli_flag: '--no-nopeek',\n\t\tcli_description: 'Disable nopeek reminder extension',\n\t\taliases: ['nopeek', 'secrets', 'secret-loading'],\n\t\tload: async () => (await import('@spences10/pi-nopeek')).default,\n\t},\n\t{\n\t\tkey: 'omnisearch',\n\t\tlabel: 'Omnisearch',\n\t\tdocs_label: 'Omnisearch',\n\t\tdescription: 'mcp-omnisearch reminder for verified web research',\n\t\tdefault_enabled: true,\n\t\toption_name: 'omnisearch',\n\t\tcli_arg: 'no-omnisearch',\n\t\tcli_flag: '--no-omnisearch',\n\t\tcli_description: 'Disable mcp-omnisearch reminder extension',\n\t\taliases: ['omnisearch', 'search', 'web-search', 'research'],\n\t\tload: async () =>\n\t\t\t(await import('@spences10/pi-omnisearch')).default,\n\t},\n\t{\n\t\tkey: 'sqlite-tools',\n\t\tlabel: 'SQLite tools',\n\t\tdocs_label: 'SQLite tools',\n\t\tdescription:\n\t\t\t'mcp-sqlite-tools reminder for safer SQLite database work',\n\t\tdefault_enabled: true,\n\t\toption_name: 'sqlite_tools',\n\t\tcli_arg: 'no-sqlite-tools',\n\t\tcli_flag: '--no-sqlite-tools',\n\t\tcli_description: 'Disable mcp-sqlite-tools reminder extension',\n\t\taliases: ['sqlite-tools', 'sqlite', 'mcp-sqlite-tools'],\n\t\tload: async () =>\n\t\t\t(await import('@spences10/pi-sqlite-tools')).default,\n\t},\n\t{\n\t\tkey: 'startup-screen',\n\t\tlabel: 'Startup screen',\n\t\tdocs_label: 'Startup screen',\n\t\tdescription:\n\t\t\t'Pixel-art gradient startup header for interactive sessions',\n\t\tdefault_enabled: true,\n\t\toption_name: 'startup_screen',\n\t\tcli_arg: 'no-startup-screen',\n\t\tcli_flag: '--no-startup-screen',\n\t\tcli_description: 'Disable the custom startup screen',\n\t\taliases: ['startup-screen', 'startup', 'header', 'splash'],\n\t\tmode_constraints: {\n\t\t\tdisabled_in: ['print', 'json', 'rpc'],\n\t\t\treason: 'Startup screen only renders in the interactive TUI',\n\t\t},\n\t\tload: async () =>\n\t\t\t(await import('./startup-screen/index.js')).default,\n\t},\n\t{\n\t\tkey: 'prompt-presets',\n\t\tlabel: 'Prompt presets',\n\t\tdocs_label: 'Prompt presets',\n\t\tdescription:\n\t\t\t'Runtime prompt preset selection and /prompt-preset command',\n\t\tdefault_enabled: true,\n\t\toption_name: 'prompt_presets',\n\t\tcli_arg: 'no-prompt-presets',\n\t\tcli_flag: '--no-prompt-presets',\n\t\tcli_description: 'Disable prompt presets extension',\n\t\taliases: ['prompt-preset', 'preset', 'presets'],\n\t\tload: async () =>\n\t\t\t(await import('./prompt-presets/index.js')).default,\n\t},\n\t{\n\t\tkey: 'lsp',\n\t\tlabel: 'LSP',\n\t\tdocs_label: 'LSP',\n\t\tdescription:\n\t\t\t'Language Server Protocol tools (diagnostics, hover, definition, references)',\n\t\tdefault_enabled: true,\n\t\toption_name: 'lsp',\n\t\tcli_arg: 'no-lsp',\n\t\tcli_flag: '--no-lsp',\n\t\tcli_description: 'Disable LSP extension',\n\t\taliases: ['lsp', 'language-server'],\n\t\tload: async () => (await import('@spences10/pi-lsp')).default,\n\t},\n\t{\n\t\tkey: 'session-name',\n\t\tlabel: 'Session name',\n\t\tdocs_label: 'Session auto-naming',\n\t\tdescription:\n\t\t\t'AI-powered session auto-naming and /session-name command',\n\t\tdefault_enabled: true,\n\t\toption_name: 'session_name',\n\t\tcli_arg: 'no-session-name',\n\t\tcli_flag: '--no-session-name',\n\t\tcli_description: 'Disable session name extension',\n\t\taliases: ['session-name', 'session', 'auto-name'],\n\t\tmode_constraints: {\n\t\t\tdisabled_in: ['print', 'json', 'rpc'],\n\t\t\treason:\n\t\t\t\t'UI-only session naming is only useful in interactive mode',\n\t\t},\n\t\tload: async () =>\n\t\t\t(await import('./session-name/index.js')).default,\n\t},\n\t{\n\t\tkey: 'confirm-destructive',\n\t\tlabel: 'Confirm destructive',\n\t\tdocs_label: 'Destructive action confirmation',\n\t\tdescription:\n\t\t\t'Prompt before destructive tool calls like file deletes, overwrites, and hard resets',\n\t\tdefault_enabled: true,\n\t\toption_name: 'confirm_destructive',\n\t\tcli_arg: 'no-confirm-destructive',\n\t\tcli_flag: '--no-confirm-destructive',\n\t\tcli_description: 'Disable destructive action confirmations',\n\t\taliases: ['confirm-destructive', 'confirm'],\n\t\tload: async () =>\n\t\t\t(await import('@spences10/pi-confirm-destructive')).default,\n\t},\n\t{\n\t\tkey: 'hooks-resolution',\n\t\tlabel: 'Hooks resolution',\n\t\tdocs_label: 'Hooks resolution',\n\t\tdescription:\n\t\t\t'Claude Code style PostToolUse hook compatibility from .claude, .rulesync, and .pi configs',\n\t\tdefault_enabled: true,\n\t\toption_name: 'hooks_resolution',\n\t\tcli_arg: 'no-hooks',\n\t\tcli_flag: '--no-hooks',\n\t\tcli_description: 'Disable Claude-style hook execution',\n\t\taliases: ['hooks-resolution', 'hooks'],\n\t\tload: async () =>\n\t\t\t(await import('./hooks-resolution/index.js')).default,\n\t},\n\t{\n\t\tkey: 'team-mode',\n\t\tlabel: 'Team mode',\n\t\tdocs_label: 'Team mode',\n\t\tdescription:\n\t\t\t'Experimental orchestrator/team mode with RPC teammates, tasks, and mailboxes',\n\t\tdefault_enabled: true,\n\t\toption_name: 'team_mode',\n\t\tcli_arg: 'no-team-mode',\n\t\tcli_flag: '--no-team-mode',\n\t\tcli_description: 'Disable experimental team mode extension',\n\t\taliases: ['team-mode', 'team', 'teammates'],\n\t\tload: async () =>\n\t\t\t(await import('@spences10/pi-team-mode')).default,\n\t},\n] as const satisfies readonly BuiltinExtensionManifestEntry[];\n\nexport type BuiltinExtensionKey =\n\t(typeof BUILTIN_EXTENSION_REGISTRY)[number]['key'];\n\nexport type BuiltinExtensionOptionName =\n\t(typeof BUILTIN_EXTENSION_REGISTRY)[number]['option_name'];\n\nexport type BuiltinExtensionInfo = Omit<\n\tBuiltinExtensionManifestEntry,\n\t'load'\n> & {\n\tkey: BuiltinExtensionKey;\n\toption_name: BuiltinExtensionOptionName;\n};\n\nexport const BUILTIN_EXTENSIONS: BuiltinExtensionInfo[] =\n\tBUILTIN_EXTENSION_REGISTRY.map(\n\t\t({ load: _load, ...extension }) => extension,\n\t);\n"],"mappings":"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"}
package/dist/index.js CHANGED
@@ -1,5 +1,5 @@
1
1
  #!/usr/bin/env node
2
- import { t as BUILTIN_EXTENSIONS } from "./builtin-registry-Dwgexb9N.js";
2
+ import { t as BUILTIN_EXTENSIONS } from "./builtin-registry-BM3CCt86.js";
3
3
  import { defineCommand, renderUsage, runMain } from "citty";
4
4
  import { readFileSync } from "node:fs";
5
5
  import { dirname, join, resolve } from "node:path";
@@ -0,0 +1,218 @@
1
+ import { readFileSync } from "node:fs";
2
+ import { basename } from "node:path";
3
+ import { truncateToWidth, visibleWidth } from "@mariozechner/pi-tui";
4
+ //#region src/extensions/startup-screen/index.ts
5
+ const RESET = "\x1B[0m";
6
+ const BOLD = "\x1B[1m";
7
+ const TRUECOLOR_FG_PREFIX = "\x1B[38;2;";
8
+ const XTERM_FG_PREFIX = "\x1B[38;5;";
9
+ const FALLBACK_PALETTE = [
10
+ [
11
+ 22,
12
+ 83,
13
+ 189
14
+ ],
15
+ [
16
+ 48,
17
+ 129,
18
+ 247
19
+ ],
20
+ [
21
+ 93,
22
+ 171,
23
+ 255
24
+ ],
25
+ [
26
+ 151,
27
+ 205,
28
+ 255
29
+ ],
30
+ [
31
+ 93,
32
+ 171,
33
+ 255
34
+ ],
35
+ [
36
+ 48,
37
+ 129,
38
+ 247
39
+ ]
40
+ ];
41
+ const THEME_GRADIENT_TOKENS = [
42
+ "accent",
43
+ "borderAccent",
44
+ "mdHeading",
45
+ "syntaxFunction",
46
+ "thinkingHigh",
47
+ "mdCode"
48
+ ];
49
+ const XTERM_CUBE_VALUES = [
50
+ 0,
51
+ 95,
52
+ 135,
53
+ 175,
54
+ 215,
55
+ 255
56
+ ];
57
+ const XTERM_GRAY_START = 232;
58
+ const TITLE_LINES = [
59
+ "███╗ ███╗ ██████╗ ██╗",
60
+ "████╗ ████║ ██╗ ██╗ ██╔══██╗ ",
61
+ "██╔████╔██║ ╚██╗ ██╔╝ ████╗ ██████╔╝██╗",
62
+ "██║╚██╔╝██║ ╚████╔╝ ╚═══╝ ██╔═══╝ ██║",
63
+ "██║ ╚═╝ ██║ ╚██╔╝ ██║ ██║",
64
+ "╚═╝ ╚═╝ ██╔╝ ╚═╝ ╚═╝"
65
+ ];
66
+ const TITLE_WIDTH = Math.max(...TITLE_LINES.map((line) => line.length));
67
+ function read_my_pi_version() {
68
+ const candidates = [new URL("../../../package.json", import.meta.url), new URL("../package.json", import.meta.url)];
69
+ for (const candidate of candidates) try {
70
+ const version = JSON.parse(readFileSync(candidate, "utf-8"))?.version;
71
+ if (typeof version === "string") return version;
72
+ } catch {}
73
+ return "dev";
74
+ }
75
+ const MY_PI_VERSION = read_my_pi_version();
76
+ function mix(a, b, t) {
77
+ return Math.round(a + (b - a) * t);
78
+ }
79
+ function sample_gradient(position, palette) {
80
+ const scaled = (position % 1 + 1) % 1 * palette.length;
81
+ const index = Math.floor(scaled);
82
+ const next_index = (index + 1) % palette.length;
83
+ const t = scaled - index;
84
+ const a = palette[index];
85
+ const b = palette[next_index];
86
+ return [
87
+ mix(a[0], b[0], t),
88
+ mix(a[1], b[1], t),
89
+ mix(a[2], b[2], t)
90
+ ];
91
+ }
92
+ function ansi_fg([r, g, b], text) {
93
+ return `\x1b[38;2;${r};${g};${b}m${text}${RESET}`;
94
+ }
95
+ function rgb_from_xterm(index) {
96
+ if (index < 0 || index > 255) return void 0;
97
+ if (index < 16) return void 0;
98
+ if (index >= XTERM_GRAY_START) {
99
+ const gray = 8 + (index - XTERM_GRAY_START) * 10;
100
+ return [
101
+ gray,
102
+ gray,
103
+ gray
104
+ ];
105
+ }
106
+ const cube = index - 16;
107
+ return [
108
+ XTERM_CUBE_VALUES[Math.floor(cube / 36)],
109
+ XTERM_CUBE_VALUES[Math.floor(cube % 36 / 6)],
110
+ XTERM_CUBE_VALUES[cube % 6]
111
+ ];
112
+ }
113
+ function ansi_params(ansi, prefix) {
114
+ if (!ansi.startsWith(prefix)) return void 0;
115
+ const end = ansi.indexOf("m", prefix.length);
116
+ if (end === -1) return void 0;
117
+ return ansi.slice(prefix.length, end).split(";");
118
+ }
119
+ function rgb_from_ansi(ansi) {
120
+ const truecolor = ansi_params(ansi, TRUECOLOR_FG_PREFIX);
121
+ if (truecolor?.length === 3) return [
122
+ Number(truecolor[0]),
123
+ Number(truecolor[1]),
124
+ Number(truecolor[2])
125
+ ];
126
+ const xterm = ansi_params(ansi, XTERM_FG_PREFIX);
127
+ return xterm?.length === 1 ? rgb_from_xterm(Number(xterm[0])) : void 0;
128
+ }
129
+ function theme_gradient_palette(theme) {
130
+ const palette = [];
131
+ const seen = /* @__PURE__ */ new Set();
132
+ for (const token of THEME_GRADIENT_TOKENS) {
133
+ const rgb = rgb_from_ansi(theme.getFgAnsi(token));
134
+ if (!rgb) continue;
135
+ const key = rgb.join(",");
136
+ if (seen.has(key)) continue;
137
+ seen.add(key);
138
+ palette.push(rgb);
139
+ }
140
+ return palette.length >= 2 ? palette : FALLBACK_PALETTE;
141
+ }
142
+ function gradient_text(text, phase, palette) {
143
+ const chars = text.split("");
144
+ const span = Math.max(chars.length - 1, 1);
145
+ return chars.map((char, index) => {
146
+ if (char === " ") return char;
147
+ return ansi_fg(sample_gradient(index / span + phase, palette), char);
148
+ }).join("");
149
+ }
150
+ function center_line(line, width) {
151
+ const clipped = visibleWidth(line) > width ? truncateToWidth(line, width, "") : line;
152
+ const padding = Math.max(0, Math.floor((width - visibleWidth(clipped)) / 2));
153
+ return `${" ".repeat(padding)}${clipped}`;
154
+ }
155
+ function color_line(theme, palette, line, phase) {
156
+ return theme.getColorMode() === "truecolor" ? gradient_text(line, phase, palette) : theme.fg("accent", line);
157
+ }
158
+ function gradient_or_theme(theme, palette, line, phase) {
159
+ return theme.getColorMode() === "truecolor" ? `${BOLD}${gradient_text(line, phase, palette)}${RESET}` : theme.bold(theme.fg("accent", line));
160
+ }
161
+ function render_brand(theme, palette, width) {
162
+ return gradient_or_theme(theme, palette, center_line(`My-Pi v${MY_PI_VERSION}`, width), .12);
163
+ }
164
+ function render_subtitle(ctx, theme, palette, model_id, width) {
165
+ return gradient_or_theme(theme, palette, center_line(`${model_id} · ${basename(ctx.cwd) || ctx.cwd}`, width), .18);
166
+ }
167
+ function render_startup_header(ctx, theme, width, model_id = ctx.model?.id ?? "no model selected") {
168
+ if (width < 24) return [center_line(theme.bold(theme.fg("accent", `My-Pi v${MY_PI_VERSION}`)), width), center_line(`${model_id} · ${basename(ctx.cwd) || ctx.cwd}`, width)];
169
+ const palette = theme_gradient_palette(theme);
170
+ const logo = TITLE_LINES.map((line, row) => color_line(theme, palette, center_line(line.padEnd(TITLE_WIDTH), width), row * .045));
171
+ return [
172
+ "",
173
+ render_brand(theme, palette, width),
174
+ ...logo,
175
+ render_subtitle(ctx, theme, palette, model_id, width),
176
+ ""
177
+ ];
178
+ }
179
+ function startup_screen_extension(pi) {
180
+ let request_render;
181
+ let current_model_id = "no model selected";
182
+ function install_header(ctx) {
183
+ ctx.ui.setHeader((tui, theme) => {
184
+ request_render = () => tui.requestRender();
185
+ return {
186
+ invalidate() {
187
+ tui.requestRender();
188
+ },
189
+ render(width) {
190
+ return render_startup_header(ctx, theme, width, current_model_id);
191
+ }
192
+ };
193
+ });
194
+ }
195
+ pi.on("session_start", async (_event, ctx) => {
196
+ current_model_id = ctx.model?.id ?? "no model selected";
197
+ if (!ctx.hasUI) return;
198
+ install_header(ctx);
199
+ });
200
+ pi.on("model_select", (event) => {
201
+ current_model_id = event.model.id;
202
+ request_render?.();
203
+ });
204
+ pi.on("session_shutdown", (_event, ctx) => {
205
+ if (ctx.hasUI) ctx.ui.setHeader(void 0);
206
+ });
207
+ pi.registerCommand("builtin-header", {
208
+ description: "Restore the built-in pi startup header",
209
+ handler: async (_args, ctx) => {
210
+ ctx.ui.setHeader(void 0);
211
+ ctx.ui.notify("Built-in startup header restored", "info");
212
+ }
213
+ });
214
+ }
215
+ //#endregion
216
+ export { startup_screen_extension as default };
217
+
218
+ //# sourceMappingURL=startup-screen-DFywkmul.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"startup-screen-DFywkmul.js","names":[],"sources":["../src/extensions/startup-screen/index.ts"],"sourcesContent":["import type {\n\tExtensionAPI,\n\tExtensionContext,\n\tTheme,\n\tThemeColor,\n} from '@mariozechner/pi-coding-agent';\nimport { truncateToWidth, visibleWidth } from '@mariozechner/pi-tui';\nimport { readFileSync } from 'node:fs';\nimport { basename } from 'node:path';\n\ntype Rgb = [number, number, number];\n\nconst RESET = '\\x1b[0m';\nconst BOLD = '\\x1b[1m';\nconst TRUECOLOR_FG_PREFIX = '\\x1b[38;2;';\nconst XTERM_FG_PREFIX = '\\x1b[38;5;';\n\nconst FALLBACK_PALETTE: Rgb[] = [\n\t[22, 83, 189],\n\t[48, 129, 247],\n\t[93, 171, 255],\n\t[151, 205, 255],\n\t[93, 171, 255],\n\t[48, 129, 247],\n];\n\nconst THEME_GRADIENT_TOKENS: ThemeColor[] = [\n\t'accent',\n\t'borderAccent',\n\t'mdHeading',\n\t'syntaxFunction',\n\t'thinkingHigh',\n\t'mdCode',\n];\n\nconst XTERM_CUBE_VALUES = [0, 95, 135, 175, 215, 255] as const;\nconst XTERM_GRAY_START = 232;\n\nconst TITLE_LINES = [\n\t'███╗ ███╗ ██████╗ ██╗',\n\t'████╗ ████║ ██╗ ██╗ ██╔══██╗ ',\n\t'██╔████╔██║ ╚██╗ ██╔╝ ████╗ ██████╔╝██╗',\n\t'██║╚██╔╝██║ ╚████╔╝ ╚═══╝ ██╔═══╝ ██║',\n\t'██║ ╚═╝ ██║ ╚██╔╝ ██║ ██║',\n\t'╚═╝ ╚═╝ ██╔╝ ╚═╝ ╚═╝',\n] as const;\n\nconst TITLE_WIDTH = Math.max(\n\t...TITLE_LINES.map((line) => line.length),\n);\n\nfunction read_my_pi_version(): string {\n\tconst candidates = [\n\t\tnew URL('../../../package.json', import.meta.url),\n\t\tnew URL('../package.json', import.meta.url),\n\t];\n\n\tfor (const candidate of candidates) {\n\t\ttry {\n\t\t\tconst parsed: unknown = JSON.parse(\n\t\t\t\treadFileSync(candidate, 'utf-8'),\n\t\t\t);\n\t\t\tconst version = (parsed as { version?: unknown } | null)\n\t\t\t\t?.version;\n\t\t\tif (typeof version === 'string') return version;\n\t\t} catch {\n\t\t\t// Try the next source/distro-relative location.\n\t\t}\n\t}\n\n\treturn 'dev';\n}\n\nconst MY_PI_VERSION = read_my_pi_version();\n\nfunction mix(a: number, b: number, t: number): number {\n\treturn Math.round(a + (b - a) * t);\n}\n\nfunction sample_gradient(position: number, palette: Rgb[]): Rgb {\n\tconst wrapped = ((position % 1) + 1) % 1;\n\tconst scaled = wrapped * palette.length;\n\tconst index = Math.floor(scaled);\n\tconst next_index = (index + 1) % palette.length;\n\tconst t = scaled - index;\n\tconst a = palette[index]!;\n\tconst b = palette[next_index]!;\n\treturn [mix(a[0], b[0], t), mix(a[1], b[1], t), mix(a[2], b[2], t)];\n}\n\nfunction ansi_fg([r, g, b]: Rgb, text: string): string {\n\treturn `\\x1b[38;2;${r};${g};${b}m${text}${RESET}`;\n}\n\nfunction rgb_from_xterm(index: number): Rgb | undefined {\n\tif (index < 0 || index > 255) return undefined;\n\tif (index < 16) return undefined;\n\tif (index >= XTERM_GRAY_START) {\n\t\tconst gray = 8 + (index - XTERM_GRAY_START) * 10;\n\t\treturn [gray, gray, gray];\n\t}\n\n\tconst cube = index - 16;\n\tconst r = XTERM_CUBE_VALUES[Math.floor(cube / 36)]!;\n\tconst g = XTERM_CUBE_VALUES[Math.floor((cube % 36) / 6)]!;\n\tconst b = XTERM_CUBE_VALUES[cube % 6]!;\n\treturn [r, g, b];\n}\n\nfunction ansi_params(\n\tansi: string,\n\tprefix: string,\n): string[] | undefined {\n\tif (!ansi.startsWith(prefix)) return undefined;\n\tconst end = ansi.indexOf('m', prefix.length);\n\tif (end === -1) return undefined;\n\treturn ansi.slice(prefix.length, end).split(';');\n}\n\nfunction rgb_from_ansi(ansi: string): Rgb | undefined {\n\tconst truecolor = ansi_params(ansi, TRUECOLOR_FG_PREFIX);\n\tif (truecolor?.length === 3) {\n\t\treturn [\n\t\t\tNumber(truecolor[0]),\n\t\t\tNumber(truecolor[1]),\n\t\t\tNumber(truecolor[2]),\n\t\t];\n\t}\n\n\tconst xterm = ansi_params(ansi, XTERM_FG_PREFIX);\n\treturn xterm?.length === 1\n\t\t? rgb_from_xterm(Number(xterm[0]))\n\t\t: undefined;\n}\n\nfunction theme_gradient_palette(theme: Theme): Rgb[] {\n\tconst palette: Rgb[] = [];\n\tconst seen = new Set<string>();\n\n\tfor (const token of THEME_GRADIENT_TOKENS) {\n\t\tconst rgb = rgb_from_ansi(theme.getFgAnsi(token));\n\t\tif (!rgb) continue;\n\t\tconst key = rgb.join(',');\n\t\tif (seen.has(key)) continue;\n\t\tseen.add(key);\n\t\tpalette.push(rgb);\n\t}\n\n\treturn palette.length >= 2 ? palette : FALLBACK_PALETTE;\n}\n\nfunction gradient_text(\n\ttext: string,\n\tphase: number,\n\tpalette: Rgb[],\n): string {\n\tconst chars = text.split('');\n\tconst span = Math.max(chars.length - 1, 1);\n\treturn chars\n\t\t.map((char, index) => {\n\t\t\tif (char === ' ') return char;\n\t\t\treturn ansi_fg(\n\t\t\t\tsample_gradient(index / span + phase, palette),\n\t\t\t\tchar,\n\t\t\t);\n\t\t})\n\t\t.join('');\n}\n\nfunction center_line(line: string, width: number): string {\n\tconst clipped =\n\t\tvisibleWidth(line) > width\n\t\t\t? truncateToWidth(line, width, '')\n\t\t\t: line;\n\tconst padding = Math.max(\n\t\t0,\n\t\tMath.floor((width - visibleWidth(clipped)) / 2),\n\t);\n\treturn `${' '.repeat(padding)}${clipped}`;\n}\n\nfunction color_line(\n\ttheme: Theme,\n\tpalette: Rgb[],\n\tline: string,\n\tphase: number,\n): string {\n\treturn theme.getColorMode() === 'truecolor'\n\t\t? gradient_text(line, phase, palette)\n\t\t: theme.fg('accent', line);\n}\n\nfunction gradient_or_theme(\n\ttheme: Theme,\n\tpalette: Rgb[],\n\tline: string,\n\tphase: number,\n): string {\n\treturn theme.getColorMode() === 'truecolor'\n\t\t? `${BOLD}${gradient_text(line, phase, palette)}${RESET}`\n\t\t: theme.bold(theme.fg('accent', line));\n}\n\nfunction render_brand(\n\ttheme: Theme,\n\tpalette: Rgb[],\n\twidth: number,\n): string {\n\treturn gradient_or_theme(\n\t\ttheme,\n\t\tpalette,\n\t\tcenter_line(`My-Pi v${MY_PI_VERSION}`, width),\n\t\t0.12,\n\t);\n}\n\nfunction render_subtitle(\n\tctx: ExtensionContext,\n\ttheme: Theme,\n\tpalette: Rgb[],\n\tmodel_id: string,\n\twidth: number,\n): string {\n\tconst project = basename(ctx.cwd) || ctx.cwd;\n\tconst subtitle = center_line(`${model_id} · ${project}`, width);\n\treturn gradient_or_theme(theme, palette, subtitle, 0.18);\n}\n\nexport function render_startup_header(\n\tctx: ExtensionContext,\n\ttheme: Theme,\n\twidth: number,\n\tmodel_id = ctx.model?.id ?? 'no model selected',\n): string[] {\n\tif (width < 24) {\n\t\treturn [\n\t\t\tcenter_line(\n\t\t\t\ttheme.bold(theme.fg('accent', `My-Pi v${MY_PI_VERSION}`)),\n\t\t\t\twidth,\n\t\t\t),\n\t\t\tcenter_line(\n\t\t\t\t`${model_id} · ${basename(ctx.cwd) || ctx.cwd}`,\n\t\t\t\twidth,\n\t\t\t),\n\t\t];\n\t}\n\n\tconst palette = theme_gradient_palette(theme);\n\tconst logo = TITLE_LINES.map((line, row) =>\n\t\tcolor_line(\n\t\t\ttheme,\n\t\t\tpalette,\n\t\t\tcenter_line(line.padEnd(TITLE_WIDTH), width),\n\t\t\trow * 0.045,\n\t\t),\n\t);\n\n\treturn [\n\t\t'',\n\t\trender_brand(theme, palette, width),\n\t\t...logo,\n\t\trender_subtitle(ctx, theme, palette, model_id, width),\n\t\t'',\n\t];\n}\n\nexport default function startup_screen_extension(\n\tpi: ExtensionAPI,\n): void {\n\tlet request_render: (() => void) | undefined;\n\tlet current_model_id = 'no model selected';\n\n\tfunction install_header(ctx: ExtensionContext): void {\n\t\tctx.ui.setHeader((tui, theme) => {\n\t\t\trequest_render = () => tui.requestRender();\n\t\t\treturn {\n\t\t\t\tinvalidate() {\n\t\t\t\t\ttui.requestRender();\n\t\t\t\t},\n\t\t\t\trender(width: number) {\n\t\t\t\t\treturn render_startup_header(\n\t\t\t\t\t\tctx,\n\t\t\t\t\t\ttheme,\n\t\t\t\t\t\twidth,\n\t\t\t\t\t\tcurrent_model_id,\n\t\t\t\t\t);\n\t\t\t\t},\n\t\t\t};\n\t\t});\n\t}\n\n\tpi.on('session_start', async (_event, ctx) => {\n\t\tcurrent_model_id = ctx.model?.id ?? 'no model selected';\n\t\tif (!ctx.hasUI) return;\n\t\tinstall_header(ctx);\n\t});\n\n\tpi.on('model_select', (event) => {\n\t\tcurrent_model_id = event.model.id;\n\t\trequest_render?.();\n\t});\n\n\tpi.on('session_shutdown', (_event, ctx) => {\n\t\tif (ctx.hasUI) ctx.ui.setHeader(undefined);\n\t});\n\n\tpi.registerCommand('builtin-header', {\n\t\tdescription: 'Restore the built-in pi startup header',\n\t\thandler: async (_args, ctx) => {\n\t\t\tctx.ui.setHeader(undefined);\n\t\t\tctx.ui.notify('Built-in startup header restored', 'info');\n\t\t},\n\t});\n}\n"],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "my-pi",
3
- "version": "0.1.31",
3
+ "version": "0.1.33",
4
4
  "description": "Composable pi coding agent with MCP, LSP, prompt presets, and local eval telemetry",
5
5
  "keywords": [
6
6
  "cli",
@@ -43,27 +43,27 @@
43
43
  }
44
44
  },
45
45
  "dependencies": {
46
- "@mariozechner/pi-ai": "^0.72.1",
47
- "@mariozechner/pi-coding-agent": "^0.72.1",
48
- "@mariozechner/pi-tui": "^0.72.1",
46
+ "@mariozechner/pi-ai": "^0.73.0",
47
+ "@mariozechner/pi-coding-agent": "^0.73.0",
48
+ "@mariozechner/pi-tui": "^0.73.0",
49
49
  "citty": "^0.2.2",
50
50
  "typebox": "^1.1.37",
51
51
  "@spences10/pi-child-env": "0.1.3",
52
- "@spences10/pi-confirm-destructive": "0.0.6",
53
- "@spences10/pi-mcp": "0.0.16",
54
- "@spences10/pi-context": "0.0.6",
55
- "@spences10/pi-lsp": "0.0.13",
56
- "@spences10/pi-omnisearch": "0.0.4",
57
- "@spences10/pi-nopeek": "0.0.4",
58
- "@spences10/pi-recall": "0.0.4",
52
+ "@spences10/pi-lsp": "0.0.14",
53
+ "@spences10/pi-confirm-destructive": "0.0.7",
54
+ "@spences10/pi-context": "0.0.7",
55
+ "@spences10/pi-mcp": "0.0.17",
56
+ "@spences10/pi-nopeek": "0.0.5",
59
57
  "@spences10/pi-project-trust": "0.0.5",
60
- "@spences10/pi-skills": "0.0.11",
61
- "@spences10/pi-redact": "0.0.4",
62
- "@spences10/pi-sqlite-tools": "0.0.4",
63
- "@spences10/pi-team-mode": "0.0.12",
58
+ "@spences10/pi-omnisearch": "0.0.5",
59
+ "@spences10/pi-recall": "0.0.5",
60
+ "@spences10/pi-sqlite-tools": "0.0.5",
61
+ "@spences10/pi-redact": "0.0.5",
62
+ "@spences10/pi-team-mode": "0.0.13",
63
+ "@spences10/pi-telemetry": "0.0.7",
64
+ "@spences10/pi-skills": "0.0.12",
64
65
  "@spences10/pi-themes": "0.0.4",
65
- "@spences10/pi-tui-modal": "0.0.6",
66
- "@spences10/pi-telemetry": "0.0.6"
66
+ "@spences10/pi-tui-modal": "0.0.7"
67
67
  },
68
68
  "devDependencies": {
69
69
  "@changesets/cli": "^2.31.0",
@@ -1 +0,0 @@
1
- {"version":3,"file":"builtin-registry-Dwgexb9N.js","names":[],"sources":["../src/extensions/builtin-registry.ts"],"sourcesContent":["import type { ExtensionFactory } from '@mariozechner/pi-coding-agent';\n\nexport type BuiltinExtensionRuntimeMode =\n\t| 'interactive'\n\t| 'print'\n\t| 'json'\n\t| 'rpc';\n\ntype BuiltinExtensionLoader = () => Promise<ExtensionFactory>;\n\nexport interface BuiltinExtensionManifestEntry {\n\tkey: string;\n\tlabel: string;\n\tdocs_label: string;\n\tdescription: string;\n\tdefault_enabled: boolean;\n\toption_name: string;\n\tcli_arg: string;\n\tcli_flag: `--${string}`;\n\tcli_description: string;\n\taliases: readonly string[];\n\tmode_constraints?: {\n\t\tdisabled_in: readonly BuiltinExtensionRuntimeMode[];\n\t\treason: string;\n\t};\n\tload: BuiltinExtensionLoader;\n}\n\nexport const BUILTIN_EXTENSION_REGISTRY = [\n\t{\n\t\tkey: 'context-sidecar',\n\t\tlabel: 'Context sidecar',\n\t\tdocs_label: 'SQLite context sidecar',\n\t\tdescription: 'Local SQLite FTS sidecar for oversized tool output',\n\t\tdefault_enabled: true,\n\t\toption_name: 'context_sidecar',\n\t\tcli_arg: 'no-context-sidecar',\n\t\tcli_flag: '--no-context-sidecar',\n\t\tcli_description:\n\t\t\t'Disable SQLite context sidecar for large tool output',\n\t\taliases: ['context-sidecar', 'context', 'sidecar'],\n\t\tload: async () => (await import('@spences10/pi-context')).default,\n\t},\n\t{\n\t\tkey: 'mcp',\n\t\tlabel: 'MCP',\n\t\tdocs_label: 'MCP',\n\t\tdescription: 'MCP server integration and /mcp command',\n\t\tdefault_enabled: true,\n\t\toption_name: 'mcp',\n\t\tcli_arg: 'no-mcp',\n\t\tcli_flag: '--no-mcp',\n\t\tcli_description: 'Disable built-in MCP extension',\n\t\taliases: ['mcp'],\n\t\tload: async () => (await import('@spences10/pi-mcp')).default,\n\t},\n\t{\n\t\tkey: 'skills',\n\t\tlabel: 'Skills',\n\t\tdocs_label: 'Skills',\n\t\tdescription: 'Managed pi-native skills and /skills command',\n\t\tdefault_enabled: true,\n\t\toption_name: 'skills',\n\t\tcli_arg: 'no-skills',\n\t\tcli_flag: '--no-skills',\n\t\tcli_description: 'Disable built-in skills extension',\n\t\taliases: ['skills', 'skill'],\n\t\tload: async () => (await import('@spences10/pi-skills')).default,\n\t},\n\t{\n\t\tkey: 'filter-output',\n\t\tlabel: 'Secret redaction',\n\t\tdocs_label: 'Secret redaction',\n\t\tdescription:\n\t\t\t'Redacts secrets from tool output before the model sees them',\n\t\tdefault_enabled: true,\n\t\toption_name: 'filter_output',\n\t\tcli_arg: 'no-filter',\n\t\tcli_flag: '--no-filter',\n\t\tcli_description: 'Disable secret redaction in tool output',\n\t\taliases: [\n\t\t\t'filter-output',\n\t\t\t'filter_output',\n\t\t\t'filter',\n\t\t\t'redaction',\n\t\t\t'secret-redaction',\n\t\t\t'output-redaction',\n\t\t],\n\t\tload: async () => (await import('@spences10/pi-redact')).default,\n\t},\n\t{\n\t\tkey: 'recall',\n\t\tlabel: 'Recall',\n\t\tdocs_label: 'Recall',\n\t\tdescription: 'pirecall reminder and background session sync',\n\t\tdefault_enabled: true,\n\t\toption_name: 'recall',\n\t\tcli_arg: 'no-recall',\n\t\tcli_flag: '--no-recall',\n\t\tcli_description: 'Disable recall extension',\n\t\taliases: ['recall', 'pirecall'],\n\t\tload: async () => (await import('@spences10/pi-recall')).default,\n\t},\n\t{\n\t\tkey: 'nopeek',\n\t\tlabel: 'Nopeek',\n\t\tdocs_label: 'Nopeek',\n\t\tdescription:\n\t\t\t'nopeek reminder for secret-safe environment loading',\n\t\tdefault_enabled: true,\n\t\toption_name: 'nopeek',\n\t\tcli_arg: 'no-nopeek',\n\t\tcli_flag: '--no-nopeek',\n\t\tcli_description: 'Disable nopeek reminder extension',\n\t\taliases: ['nopeek', 'secrets', 'secret-loading'],\n\t\tload: async () => (await import('@spences10/pi-nopeek')).default,\n\t},\n\t{\n\t\tkey: 'omnisearch',\n\t\tlabel: 'Omnisearch',\n\t\tdocs_label: 'Omnisearch',\n\t\tdescription: 'mcp-omnisearch reminder for verified web research',\n\t\tdefault_enabled: true,\n\t\toption_name: 'omnisearch',\n\t\tcli_arg: 'no-omnisearch',\n\t\tcli_flag: '--no-omnisearch',\n\t\tcli_description: 'Disable mcp-omnisearch reminder extension',\n\t\taliases: ['omnisearch', 'search', 'web-search', 'research'],\n\t\tload: async () =>\n\t\t\t(await import('@spences10/pi-omnisearch')).default,\n\t},\n\t{\n\t\tkey: 'sqlite-tools',\n\t\tlabel: 'SQLite tools',\n\t\tdocs_label: 'SQLite tools',\n\t\tdescription:\n\t\t\t'mcp-sqlite-tools reminder for safer SQLite database work',\n\t\tdefault_enabled: true,\n\t\toption_name: 'sqlite_tools',\n\t\tcli_arg: 'no-sqlite-tools',\n\t\tcli_flag: '--no-sqlite-tools',\n\t\tcli_description: 'Disable mcp-sqlite-tools reminder extension',\n\t\taliases: ['sqlite-tools', 'sqlite', 'mcp-sqlite-tools'],\n\t\tload: async () =>\n\t\t\t(await import('@spences10/pi-sqlite-tools')).default,\n\t},\n\t{\n\t\tkey: 'prompt-presets',\n\t\tlabel: 'Prompt presets',\n\t\tdocs_label: 'Prompt presets',\n\t\tdescription:\n\t\t\t'Runtime prompt preset selection and /prompt-preset command',\n\t\tdefault_enabled: true,\n\t\toption_name: 'prompt_presets',\n\t\tcli_arg: 'no-prompt-presets',\n\t\tcli_flag: '--no-prompt-presets',\n\t\tcli_description: 'Disable prompt presets extension',\n\t\taliases: ['prompt-preset', 'preset', 'presets'],\n\t\tload: async () =>\n\t\t\t(await import('./prompt-presets/index.js')).default,\n\t},\n\t{\n\t\tkey: 'lsp',\n\t\tlabel: 'LSP',\n\t\tdocs_label: 'LSP',\n\t\tdescription:\n\t\t\t'Language Server Protocol tools (diagnostics, hover, definition, references)',\n\t\tdefault_enabled: true,\n\t\toption_name: 'lsp',\n\t\tcli_arg: 'no-lsp',\n\t\tcli_flag: '--no-lsp',\n\t\tcli_description: 'Disable LSP extension',\n\t\taliases: ['lsp', 'language-server'],\n\t\tload: async () => (await import('@spences10/pi-lsp')).default,\n\t},\n\t{\n\t\tkey: 'session-name',\n\t\tlabel: 'Session name',\n\t\tdocs_label: 'Session auto-naming',\n\t\tdescription:\n\t\t\t'AI-powered session auto-naming and /session-name command',\n\t\tdefault_enabled: true,\n\t\toption_name: 'session_name',\n\t\tcli_arg: 'no-session-name',\n\t\tcli_flag: '--no-session-name',\n\t\tcli_description: 'Disable session name extension',\n\t\taliases: ['session-name', 'session', 'auto-name'],\n\t\tmode_constraints: {\n\t\t\tdisabled_in: ['print', 'json', 'rpc'],\n\t\t\treason:\n\t\t\t\t'UI-only session naming is only useful in interactive mode',\n\t\t},\n\t\tload: async () =>\n\t\t\t(await import('./session-name/index.js')).default,\n\t},\n\t{\n\t\tkey: 'confirm-destructive',\n\t\tlabel: 'Confirm destructive',\n\t\tdocs_label: 'Destructive action confirmation',\n\t\tdescription:\n\t\t\t'Prompt before destructive tool calls like file deletes, overwrites, and hard resets',\n\t\tdefault_enabled: true,\n\t\toption_name: 'confirm_destructive',\n\t\tcli_arg: 'no-confirm-destructive',\n\t\tcli_flag: '--no-confirm-destructive',\n\t\tcli_description: 'Disable destructive action confirmations',\n\t\taliases: ['confirm-destructive', 'confirm'],\n\t\tload: async () =>\n\t\t\t(await import('@spences10/pi-confirm-destructive')).default,\n\t},\n\t{\n\t\tkey: 'hooks-resolution',\n\t\tlabel: 'Hooks resolution',\n\t\tdocs_label: 'Hooks resolution',\n\t\tdescription:\n\t\t\t'Claude Code style PostToolUse hook compatibility from .claude, .rulesync, and .pi configs',\n\t\tdefault_enabled: true,\n\t\toption_name: 'hooks_resolution',\n\t\tcli_arg: 'no-hooks',\n\t\tcli_flag: '--no-hooks',\n\t\tcli_description: 'Disable Claude-style hook execution',\n\t\taliases: ['hooks-resolution', 'hooks'],\n\t\tload: async () =>\n\t\t\t(await import('./hooks-resolution/index.js')).default,\n\t},\n\t{\n\t\tkey: 'team-mode',\n\t\tlabel: 'Team mode',\n\t\tdocs_label: 'Team mode',\n\t\tdescription:\n\t\t\t'Experimental orchestrator/team mode with RPC teammates, tasks, and mailboxes',\n\t\tdefault_enabled: true,\n\t\toption_name: 'team_mode',\n\t\tcli_arg: 'no-team-mode',\n\t\tcli_flag: '--no-team-mode',\n\t\tcli_description: 'Disable experimental team mode extension',\n\t\taliases: ['team-mode', 'team', 'teammates'],\n\t\tload: async () =>\n\t\t\t(await import('@spences10/pi-team-mode')).default,\n\t},\n] as const satisfies readonly BuiltinExtensionManifestEntry[];\n\nexport type BuiltinExtensionKey =\n\t(typeof BUILTIN_EXTENSION_REGISTRY)[number]['key'];\n\nexport type BuiltinExtensionOptionName =\n\t(typeof BUILTIN_EXTENSION_REGISTRY)[number]['option_name'];\n\nexport type BuiltinExtensionInfo = Omit<\n\tBuiltinExtensionManifestEntry,\n\t'load'\n> & {\n\tkey: BuiltinExtensionKey;\n\toption_name: BuiltinExtensionOptionName;\n};\n\nexport const BUILTIN_EXTENSIONS: BuiltinExtensionInfo[] =\n\tBUILTIN_EXTENSION_REGISTRY.map(\n\t\t({ load: _load, ...extension }) => extension,\n\t);\n"],"mappings":"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"}