更新大量 tsx 原始文件; 已经迁移 login panel; 部分 (#121)

* style(B1-1): 格式化 ink/buddy/cli/context/screens/tasks/services/keybindings/state (43 files)

纯格式化:移除分号、React Compiler import、import 多行展开。
修复了 Box.tsx 和 ScrollBox.tsx 中无效的 global.d.ts import。

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* style(B1-2): 格式化 commands (79 files)

纯格式化:移除分号、React Compiler import、import 多行展开。

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* style(B1-3): 格式化 components/messages,permissions,mcp,sandbox,shell (104 files)

纯格式化:移除分号、React Compiler import、import 多行展开。

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* style(B1-4): 格式化 components/PromptInput,FeedbackSurvey,tasks,agents,skills,design-system,wizard (73 files)

纯格式化:移除分号、React Compiler import、import 多行展开。

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* style(B1-5): 格式化 components其余 + hooks + tools (232 files)

纯格式化:移除分号、React Compiler import、import 多行展开。

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* style(B1-6): 格式化 main/entrypoints/utils/moreright (21 files)

纯格式化:移除分号、React Compiler import、import 多行展开。

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* docs: 更新 README,新增 Run.ps1/TODO.md,删除 V6.md

- README.md: 大幅重写,更详细版本历史和配置示例
- Run.ps1: 新增 Windows 启动脚本
- TODO.md: 新增包完成清单
- V6.md: 删除(架构重构规划已不适用)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix: 修复以前的问题

* fix: 修复 login 面板的问题

---------

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
claude-code-best
2026-04-04 23:24:27 +08:00
committed by GitHub
parent 02694918b5
commit 5b1a52b8e0
559 changed files with 103807 additions and 101817 deletions

View File

@@ -1,83 +1,64 @@
import { c as _c } from "react/compiler-runtime";
import React, { type ReactNode } from 'react';
import { Box } from '../../../../ink.js';
import { useKeybinding } from '../../../../keybindings/useKeybinding.js';
import type { AgentColorName } from '../../../../tools/AgentTool/agentColorManager.js';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Byline } from '../../../design-system/Byline.js';
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import { ColorPicker } from '../../ColorPicker.js';
import type { AgentWizardData } from '../types.js';
export function ColorStep() {
const $ = _c(14);
const {
goNext,
goBack,
updateWizardData,
wizardData
} = useWizard();
let t0;
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
t0 = {
context: "Confirmation"
};
$[0] = t0;
} else {
t0 = $[0];
import React, { type ReactNode } from 'react'
import { Box } from '../../../../ink.js'
import { useKeybinding } from '../../../../keybindings/useKeybinding.js'
import type { AgentColorName } from '../../../../tools/AgentTool/agentColorManager.js'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Byline } from '../../../design-system/Byline.js'
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import { ColorPicker } from '../../ColorPicker.js'
import type { AgentWizardData } from '../types.js'
export function ColorStep(): ReactNode {
const { goNext, goBack, updateWizardData, wizardData } =
useWizard<AgentWizardData>()
// Handle escape key - ColorPicker handles its own escape internally
useKeybinding('confirm:no', goBack, { context: 'Confirmation' })
const handleConfirm = (color?: string): void => {
updateWizardData({
selectedColor: color,
// Prepare final agent for confirmation
finalAgent: {
agentType: wizardData.agentType!,
whenToUse: wizardData.whenToUse!,
getSystemPrompt: () => wizardData.systemPrompt!,
tools: wizardData.selectedTools,
...(wizardData.selectedModel
? { model: wizardData.selectedModel }
: {}),
...(color ? { color: color as AgentColorName } : {}),
source: wizardData.location!,
},
})
goNext()
}
useKeybinding("confirm:no", goBack, t0);
let t1;
if ($[1] !== goNext || $[2] !== updateWizardData || $[3] !== wizardData.agentType || $[4] !== wizardData.location || $[5] !== wizardData.selectedModel || $[6] !== wizardData.selectedTools || $[7] !== wizardData.systemPrompt || $[8] !== wizardData.whenToUse) {
t1 = color => {
updateWizardData({
selectedColor: color,
finalAgent: {
agentType: wizardData.agentType,
whenToUse: wizardData.whenToUse,
getSystemPrompt: () => wizardData.systemPrompt,
tools: wizardData.selectedTools,
...(wizardData.selectedModel ? {
model: wizardData.selectedModel
} : {}),
...(color ? {
color: color as AgentColorName
} : {}),
source: wizardData.location
}
});
goNext();
};
$[1] = goNext;
$[2] = updateWizardData;
$[3] = wizardData.agentType;
$[4] = wizardData.location;
$[5] = wizardData.selectedModel;
$[6] = wizardData.selectedTools;
$[7] = wizardData.systemPrompt;
$[8] = wizardData.whenToUse;
$[9] = t1;
} else {
t1 = $[9];
}
const handleConfirm = t1;
let t2;
if ($[10] === Symbol.for("react.memo_cache_sentinel")) {
t2 = <Byline><KeyboardShortcutHint shortcut={"\u2191\u2193"} action="navigate" /><KeyboardShortcutHint shortcut="Enter" action="select" /><ConfigurableShortcutHint action="confirm:no" context="Confirmation" fallback="Esc" description="go back" /></Byline>;
$[10] = t2;
} else {
t2 = $[10];
}
const t3 = wizardData.agentType || "agent";
let t4;
if ($[11] !== handleConfirm || $[12] !== t3) {
t4 = <WizardDialogLayout subtitle="Choose background color" footerText={t2}><Box><ColorPicker agentName={t3} currentColor="automatic" onConfirm={handleConfirm} /></Box></WizardDialogLayout>;
$[11] = handleConfirm;
$[12] = t3;
$[13] = t4;
} else {
t4 = $[13];
}
return t4;
return (
<WizardDialogLayout
subtitle="Choose background color"
footerText={
<Byline>
<KeyboardShortcutHint shortcut="↑↓" action="navigate" />
<KeyboardShortcutHint shortcut="Enter" action="select" />
<ConfigurableShortcutHint
action="confirm:no"
context="Confirmation"
fallback="Esc"
description="go back"
/>
</Byline>
}
>
<Box>
<ColorPicker
agentName={wizardData.agentType || 'agent'}
currentColor="automatic"
onConfirm={handleConfirm}
/>
</Box>
</WizardDialogLayout>
)
}

View File

@@ -1,377 +1,168 @@
import { c as _c } from "react/compiler-runtime";
import React, { type ReactNode } from 'react';
import type { KeyboardEvent } from '../../../../ink/events/keyboard-event.js';
import { Box, Text } from '../../../../ink.js';
import { useKeybinding } from '../../../../keybindings/useKeybinding.js';
import { isAutoMemoryEnabled } from '../../../../memdir/paths.js';
import type { Tools } from '../../../../Tool.js';
import { getMemoryScopeDisplay } from '../../../../tools/AgentTool/agentMemory.js';
import type { AgentDefinition } from '../../../../tools/AgentTool/loadAgentsDir.js';
import { truncateToWidth } from '../../../../utils/format.js';
import { getAgentModelDisplay } from '../../../../utils/model/agent.js';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Byline } from '../../../design-system/Byline.js';
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import { getNewRelativeAgentFilePath } from '../../agentFileUtils.js';
import { validateAgent } from '../../validateAgent.js';
import type { AgentWizardData } from '../types.js';
import React, { type ReactNode } from 'react'
import type { KeyboardEvent } from '../../../../ink/events/keyboard-event.js'
import { Box, Text } from '../../../../ink.js'
import { useKeybinding } from '../../../../keybindings/useKeybinding.js'
import { isAutoMemoryEnabled } from '../../../../memdir/paths.js'
import type { Tools } from '../../../../Tool.js'
import { getMemoryScopeDisplay } from '../../../../tools/AgentTool/agentMemory.js'
import type { AgentDefinition } from '../../../../tools/AgentTool/loadAgentsDir.js'
import { truncateToWidth } from '../../../../utils/format.js'
import { getAgentModelDisplay } from '../../../../utils/model/agent.js'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Byline } from '../../../design-system/Byline.js'
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import { getNewRelativeAgentFilePath } from '../../agentFileUtils.js'
import { validateAgent } from '../../validateAgent.js'
import type { AgentWizardData } from '../types.js'
type Props = {
tools: Tools;
existingAgents: AgentDefinition[];
onSave: () => void;
onSaveAndEdit: () => void;
error?: string | null;
};
export function ConfirmStep(t0) {
const $ = _c(88);
const {
tools,
existingAgents,
onSave,
onSaveAndEdit,
error
} = t0;
const {
goBack,
wizardData
} = useWizard();
let t1;
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
t1 = {
context: "Confirmation"
};
$[0] = t1;
} else {
t1 = $[0];
tools: Tools
existingAgents: AgentDefinition[]
onSave: () => void
onSaveAndEdit: () => void
error?: string | null
}
export function ConfirmStep({
tools,
existingAgents,
onSave,
onSaveAndEdit,
error,
}: Props): ReactNode {
const { goBack, wizardData } = useWizard<AgentWizardData>()
useKeybinding('confirm:no', goBack, { context: 'Confirmation' })
const handleKeyDown = (e: KeyboardEvent) => {
if (e.key === 's' || e.key === 'return') {
e.preventDefault()
onSave()
} else if (e.key === 'e') {
e.preventDefault()
onSaveAndEdit()
}
}
useKeybinding("confirm:no", goBack, t1);
let t2;
if ($[1] !== onSave || $[2] !== onSaveAndEdit) {
t2 = e => {
if (e.key === "s" || e.key === "return") {
e.preventDefault();
onSave();
} else {
if (e.key === "e") {
e.preventDefault();
onSaveAndEdit();
}
const agent = wizardData.finalAgent!
const validation = validateAgent(agent, tools, existingAgents)
const systemPromptPreview = truncateToWidth(agent.getSystemPrompt(), 240)
const whenToUsePreview = truncateToWidth(agent.whenToUse, 240)
const getToolsDisplay = (toolNames: string[] | undefined): string => {
// undefined means "all tools" per PR semantic
if (toolNames === undefined) return 'All tools'
if (toolNames.length === 0) return 'None'
if (toolNames.length === 1) return toolNames[0] || 'None'
if (toolNames.length === 2) return toolNames.join(' and ')
return `${toolNames.slice(0, -1).join(', ')}, and ${toolNames[toolNames.length - 1]}`
}
// Compute memory display outside JSX
const memoryDisplayElement = isAutoMemoryEnabled() ? (
<Text>
<Text bold>Memory</Text>: {getMemoryScopeDisplay(agent.memory)}
</Text>
) : null
return (
<WizardDialogLayout
subtitle="Confirm and save"
footerText={
<Byline>
<KeyboardShortcutHint shortcut="s/Enter" action="save" />
<KeyboardShortcutHint shortcut="e" action="edit in your editor" />
<ConfigurableShortcutHint
action="confirm:no"
context="Confirmation"
fallback="Esc"
description="cancel"
/>
</Byline>
}
};
$[1] = onSave;
$[2] = onSaveAndEdit;
$[3] = t2;
} else {
t2 = $[3];
}
const handleKeyDown = t2;
const agent = wizardData.finalAgent;
let T0;
let T1;
let t10;
let t11;
let t12;
let t13;
let t14;
let t15;
let t16;
let t17;
let t18;
let t19;
let t3;
let t4;
let t5;
let t6;
let t7;
let t8;
let t9;
if ($[4] !== agent || $[5] !== existingAgents || $[6] !== handleKeyDown || $[7] !== tools || $[8] !== wizardData.location) {
const validation = validateAgent(agent, tools, existingAgents);
let t20;
if ($[28] !== agent) {
t20 = truncateToWidth(agent.getSystemPrompt(), 240);
$[28] = agent;
$[29] = t20;
} else {
t20 = $[29];
}
const systemPromptPreview = t20;
let t21;
if ($[30] !== agent.whenToUse) {
t21 = truncateToWidth(agent.whenToUse, 240);
$[30] = agent.whenToUse;
$[31] = t21;
} else {
t21 = $[31];
}
const whenToUsePreview = t21;
const getToolsDisplay = _temp;
let t22;
if ($[32] !== agent.memory) {
t22 = isAutoMemoryEnabled() ? <Text><Text bold={true}>Memory</Text>: {getMemoryScopeDisplay(agent.memory)}</Text> : null;
$[32] = agent.memory;
$[33] = t22;
} else {
t22 = $[33];
}
const memoryDisplayElement = t22;
T1 = WizardDialogLayout;
t18 = "Confirm and save";
if ($[34] === Symbol.for("react.memo_cache_sentinel")) {
t19 = <Byline><KeyboardShortcutHint shortcut="s/Enter" action="save" /><KeyboardShortcutHint shortcut="e" action="edit in your editor" /><ConfigurableShortcutHint action="confirm:no" context="Confirmation" fallback="Esc" description="cancel" /></Byline>;
$[34] = t19;
} else {
t19 = $[34];
}
T0 = Box;
t3 = "column";
t4 = 0;
t5 = true;
t6 = handleKeyDown;
let t23;
if ($[35] === Symbol.for("react.memo_cache_sentinel")) {
t23 = <Text bold={true}>Name</Text>;
$[35] = t23;
} else {
t23 = $[35];
}
if ($[36] !== agent.agentType) {
t7 = <Text>{t23}: {agent.agentType}</Text>;
$[36] = agent.agentType;
$[37] = t7;
} else {
t7 = $[37];
}
let t24;
if ($[38] === Symbol.for("react.memo_cache_sentinel")) {
t24 = <Text bold={true}>Location</Text>;
$[38] = t24;
} else {
t24 = $[38];
}
let t25;
if ($[39] !== agent.agentType || $[40] !== wizardData.location) {
t25 = getNewRelativeAgentFilePath({
source: wizardData.location,
agentType: agent.agentType
});
$[39] = agent.agentType;
$[40] = wizardData.location;
$[41] = t25;
} else {
t25 = $[41];
}
if ($[42] !== t25) {
t8 = <Text>{t24}:{" "}{t25}</Text>;
$[42] = t25;
$[43] = t8;
} else {
t8 = $[43];
}
let t26;
if ($[44] === Symbol.for("react.memo_cache_sentinel")) {
t26 = <Text bold={true}>Tools</Text>;
$[44] = t26;
} else {
t26 = $[44];
}
let t27;
if ($[45] !== agent.tools) {
t27 = getToolsDisplay(agent.tools);
$[45] = agent.tools;
$[46] = t27;
} else {
t27 = $[46];
}
if ($[47] !== t27) {
t9 = <Text>{t26}: {t27}</Text>;
$[47] = t27;
$[48] = t9;
} else {
t9 = $[48];
}
let t28;
if ($[49] === Symbol.for("react.memo_cache_sentinel")) {
t28 = <Text bold={true}>Model</Text>;
$[49] = t28;
} else {
t28 = $[49];
}
let t29;
if ($[50] !== agent.model) {
t29 = getAgentModelDisplay(agent.model);
$[50] = agent.model;
$[51] = t29;
} else {
t29 = $[51];
}
if ($[52] !== t29) {
t10 = <Text>{t28}: {t29}</Text>;
$[52] = t29;
$[53] = t10;
} else {
t10 = $[53];
}
t11 = memoryDisplayElement;
if ($[54] === Symbol.for("react.memo_cache_sentinel")) {
t12 = <Box marginTop={1}><Text><Text bold={true}>Description</Text> (tells Claude when to use this agent):</Text></Box>;
$[54] = t12;
} else {
t12 = $[54];
}
if ($[55] !== whenToUsePreview) {
t13 = <Box marginLeft={2} marginTop={1}><Text>{whenToUsePreview}</Text></Box>;
$[55] = whenToUsePreview;
$[56] = t13;
} else {
t13 = $[56];
}
if ($[57] === Symbol.for("react.memo_cache_sentinel")) {
t14 = <Box marginTop={1}><Text><Text bold={true}>System prompt</Text>:</Text></Box>;
$[57] = t14;
} else {
t14 = $[57];
}
if ($[58] !== systemPromptPreview) {
t15 = <Box marginLeft={2} marginTop={1}><Text>{systemPromptPreview}</Text></Box>;
$[58] = systemPromptPreview;
$[59] = t15;
} else {
t15 = $[59];
}
t16 = validation.warnings.length > 0 && <Box marginTop={1} flexDirection="column"><Text color="warning">Warnings:</Text>{validation.warnings.map(_temp2)}</Box>;
t17 = validation.errors.length > 0 && <Box marginTop={1} flexDirection="column"><Text color="error">Errors:</Text>{validation.errors.map(_temp3)}</Box>;
$[4] = agent;
$[5] = existingAgents;
$[6] = handleKeyDown;
$[7] = tools;
$[8] = wizardData.location;
$[9] = T0;
$[10] = T1;
$[11] = t10;
$[12] = t11;
$[13] = t12;
$[14] = t13;
$[15] = t14;
$[16] = t15;
$[17] = t16;
$[18] = t17;
$[19] = t18;
$[20] = t19;
$[21] = t3;
$[22] = t4;
$[23] = t5;
$[24] = t6;
$[25] = t7;
$[26] = t8;
$[27] = t9;
} else {
T0 = $[9];
T1 = $[10];
t10 = $[11];
t11 = $[12];
t12 = $[13];
t13 = $[14];
t14 = $[15];
t15 = $[16];
t16 = $[17];
t17 = $[18];
t18 = $[19];
t19 = $[20];
t3 = $[21];
t4 = $[22];
t5 = $[23];
t6 = $[24];
t7 = $[25];
t8 = $[26];
t9 = $[27];
}
let t20;
if ($[60] !== error) {
t20 = error && <Box marginTop={1}><Text color="error">{error}</Text></Box>;
$[60] = error;
$[61] = t20;
} else {
t20 = $[61];
}
let t21;
if ($[62] === Symbol.for("react.memo_cache_sentinel")) {
t21 = <Text bold={true}>s</Text>;
$[62] = t21;
} else {
t21 = $[62];
}
let t22;
if ($[63] === Symbol.for("react.memo_cache_sentinel")) {
t22 = <Text bold={true}>Enter</Text>;
$[63] = t22;
} else {
t22 = $[63];
}
let t23;
if ($[64] === Symbol.for("react.memo_cache_sentinel")) {
t23 = <Box marginTop={2}><Text color="success">Press {t21} or {t22} to save,{" "}<Text bold={true}>e</Text> to save and edit</Text></Box>;
$[64] = t23;
} else {
t23 = $[64];
}
let t24;
if ($[65] !== T0 || $[66] !== t10 || $[67] !== t11 || $[68] !== t12 || $[69] !== t13 || $[70] !== t14 || $[71] !== t15 || $[72] !== t16 || $[73] !== t17 || $[74] !== t20 || $[75] !== t3 || $[76] !== t4 || $[77] !== t5 || $[78] !== t6 || $[79] !== t7 || $[80] !== t8 || $[81] !== t9) {
t24 = <T0 flexDirection={t3} tabIndex={t4} autoFocus={t5} onKeyDown={t6}>{t7}{t8}{t9}{t10}{t11}{t12}{t13}{t14}{t15}{t16}{t17}{t20}{t23}</T0>;
$[65] = T0;
$[66] = t10;
$[67] = t11;
$[68] = t12;
$[69] = t13;
$[70] = t14;
$[71] = t15;
$[72] = t16;
$[73] = t17;
$[74] = t20;
$[75] = t3;
$[76] = t4;
$[77] = t5;
$[78] = t6;
$[79] = t7;
$[80] = t8;
$[81] = t9;
$[82] = t24;
} else {
t24 = $[82];
}
let t25;
if ($[83] !== T1 || $[84] !== t18 || $[85] !== t19 || $[86] !== t24) {
t25 = <T1 subtitle={t18} footerText={t19}>{t24}</T1>;
$[83] = T1;
$[84] = t18;
$[85] = t19;
$[86] = t24;
$[87] = t25;
} else {
t25 = $[87];
}
return t25;
}
function _temp3(err, i_0) {
return <Text key={i_0} color="error">{" "} {err}</Text>;
}
function _temp2(warning, i) {
return <Text key={i} dimColor={true}>{" "} {warning}</Text>;
}
function _temp(toolNames) {
if (toolNames === undefined) {
return "All tools";
}
if (toolNames.length === 0) {
return "None";
}
if (toolNames.length === 1) {
return toolNames[0] || "None";
}
if (toolNames.length === 2) {
return toolNames.join(" and ");
}
return `${toolNames.slice(0, -1).join(", ")}, and ${toolNames[toolNames.length - 1]}`;
>
<Box
flexDirection="column"
tabIndex={0}
autoFocus
onKeyDown={handleKeyDown}
>
<Text>
<Text bold>Name</Text>: {agent.agentType}
</Text>
<Text>
<Text bold>Location</Text>:{' '}
{getNewRelativeAgentFilePath({
source: wizardData.location!,
agentType: agent.agentType,
})}
</Text>
<Text>
<Text bold>Tools</Text>: {getToolsDisplay(agent.tools)}
</Text>
<Text>
<Text bold>Model</Text>: {getAgentModelDisplay(agent.model)}
</Text>
{memoryDisplayElement}
<Box marginTop={1}>
<Text>
<Text bold>Description</Text> (tells Claude when to use this agent):
</Text>
</Box>
<Box marginLeft={2} marginTop={1}>
<Text>{whenToUsePreview}</Text>
</Box>
<Box marginTop={1}>
<Text>
<Text bold>System prompt</Text>:
</Text>
</Box>
<Box marginLeft={2} marginTop={1}>
<Text>{systemPromptPreview}</Text>
</Box>
{validation.warnings.length > 0 && (
<Box marginTop={1} flexDirection="column">
<Text color="warning">Warnings:</Text>
{validation.warnings.map((warning, i) => (
<Text key={i} dimColor>
{' '}
{warning}
</Text>
))}
</Box>
)}
{validation.errors.length > 0 && (
<Box marginTop={1} flexDirection="column">
<Text color="error">Errors:</Text>
{validation.errors.map((err, i) => (
<Text key={i} color="error">
{' '}
{err}
</Text>
))}
</Box>
)}
{error && (
<Box marginTop={1}>
<Text color="error">{error}</Text>
</Box>
)}
<Box marginTop={2}>
<Text color="success">
Press <Text bold>s</Text> or <Text bold>Enter</Text> to save,{' '}
<Text bold>e</Text> to save and edit
</Text>
</Box>
</Box>
</WizardDialogLayout>
)
}

View File

@@ -1,73 +1,112 @@
import chalk from 'chalk';
import React, { type ReactNode, useCallback, useState } from 'react';
import { type AnalyticsMetadata_I_VERIFIED_THIS_IS_NOT_CODE_OR_FILEPATHS, logEvent } from 'src/services/analytics/index.js';
import { useSetAppState } from 'src/state/AppState.js';
import type { Tools } from '../../../../Tool.js';
import type { AgentDefinition } from '../../../../tools/AgentTool/loadAgentsDir.js';
import { getActiveAgentsFromList } from '../../../../tools/AgentTool/loadAgentsDir.js';
import { editFileInEditor } from '../../../../utils/promptEditor.js';
import { useWizard } from '../../../wizard/index.js';
import { getNewAgentFilePath, saveAgentToFile } from '../../agentFileUtils.js';
import type { AgentWizardData } from '../types.js';
import { ConfirmStep } from './ConfirmStep.js';
import chalk from 'chalk'
import React, { type ReactNode, useCallback, useState } from 'react'
import {
type AnalyticsMetadata_I_VERIFIED_THIS_IS_NOT_CODE_OR_FILEPATHS,
logEvent,
} from 'src/services/analytics/index.js'
import { useSetAppState } from 'src/state/AppState.js'
import type { Tools } from '../../../../Tool.js'
import type { AgentDefinition } from '../../../../tools/AgentTool/loadAgentsDir.js'
import { getActiveAgentsFromList } from '../../../../tools/AgentTool/loadAgentsDir.js'
import { editFileInEditor } from '../../../../utils/promptEditor.js'
import { useWizard } from '../../../wizard/index.js'
import { getNewAgentFilePath, saveAgentToFile } from '../../agentFileUtils.js'
import type { AgentWizardData } from '../types.js'
import { ConfirmStep } from './ConfirmStep.js'
type Props = {
tools: Tools;
existingAgents: AgentDefinition[];
onComplete: (message: string) => void;
};
tools: Tools
existingAgents: AgentDefinition[]
onComplete: (message: string) => void
}
export function ConfirmStepWrapper({
tools,
existingAgents,
onComplete
onComplete,
}: Props): ReactNode {
const {
wizardData
} = useWizard<AgentWizardData>();
const [saveError, setSaveError] = useState<string | null>(null);
const setAppState = useSetAppState();
const saveAgent = useCallback(async (openInEditor: boolean): Promise<void> => {
if (!wizardData?.finalAgent) return;
try {
await saveAgentToFile(wizardData.location!, wizardData.finalAgent.agentType, wizardData.finalAgent.whenToUse, wizardData.finalAgent.tools, wizardData.finalAgent.getSystemPrompt(), true, wizardData.finalAgent.color, wizardData.finalAgent.model, wizardData.finalAgent.memory);
setAppState(state => {
if (!wizardData.finalAgent) return state;
const allAgents = state.agentDefinitions.allAgents.concat(wizardData.finalAgent);
return {
...state,
agentDefinitions: {
...state.agentDefinitions,
activeAgents: getActiveAgentsFromList(allAgents),
allAgents
const { wizardData } = useWizard<AgentWizardData>()
const [saveError, setSaveError] = useState<string | null>(null)
const setAppState = useSetAppState()
const saveAgent = useCallback(
async (openInEditor: boolean): Promise<void> => {
if (!wizardData?.finalAgent) return
try {
await saveAgentToFile(
wizardData.location!,
wizardData.finalAgent.agentType,
wizardData.finalAgent.whenToUse,
wizardData.finalAgent.tools,
wizardData.finalAgent.getSystemPrompt(),
true,
wizardData.finalAgent.color,
wizardData.finalAgent.model,
wizardData.finalAgent.memory,
)
setAppState(state => {
if (!wizardData.finalAgent) return state
const allAgents = state.agentDefinitions.allAgents.concat(
wizardData.finalAgent,
)
return {
...state,
agentDefinitions: {
...state.agentDefinitions,
activeAgents: getActiveAgentsFromList(allAgents),
allAgents,
},
}
};
});
if (openInEditor) {
const filePath = getNewAgentFilePath({
})
if (openInEditor) {
const filePath = getNewAgentFilePath({
source: wizardData.location!,
agentType: wizardData.finalAgent.agentType,
})
await editFileInEditor(filePath)
}
logEvent('tengu_agent_created', {
agent_type: wizardData.finalAgent.agentType,
generation_method: wizardData.wasGenerated ? 'generated' : 'manual',
source: wizardData.location!,
agentType: wizardData.finalAgent.agentType
});
await editFileInEditor(filePath);
tool_count: wizardData.finalAgent.tools?.length ?? 'all',
has_custom_model: !!wizardData.finalAgent.model,
has_custom_color: !!wizardData.finalAgent.color,
has_memory: !!wizardData.finalAgent.memory,
memory_scope: wizardData.finalAgent.memory ?? 'none',
...(openInEditor ? { opened_in_editor: true } : {}),
} as AnalyticsMetadata_I_VERIFIED_THIS_IS_NOT_CODE_OR_FILEPATHS)
const message = openInEditor
? `Created agent: ${chalk.bold(wizardData.finalAgent.agentType)} and opened in editor. ` +
`If you made edits, restart to load the latest version.`
: `Created agent: ${chalk.bold(wizardData.finalAgent.agentType)}`
onComplete(message)
} catch (err) {
setSaveError(
err instanceof Error ? err.message : 'Failed to save agent',
)
}
logEvent('tengu_agent_created', {
agent_type: wizardData.finalAgent.agentType,
generation_method: wizardData.wasGenerated ? 'generated' : 'manual',
source: wizardData.location!,
tool_count: wizardData.finalAgent.tools?.length ?? 'all',
has_custom_model: !!wizardData.finalAgent.model,
has_custom_color: !!wizardData.finalAgent.color,
has_memory: !!wizardData.finalAgent.memory,
memory_scope: wizardData.finalAgent.memory ?? 'none',
...(openInEditor ? {
opened_in_editor: true
} : {})
} as AnalyticsMetadata_I_VERIFIED_THIS_IS_NOT_CODE_OR_FILEPATHS);
const message = openInEditor ? `Created agent: ${chalk.bold(wizardData.finalAgent.agentType)} and opened in editor. ` + `If you made edits, restart to load the latest version.` : `Created agent: ${chalk.bold(wizardData.finalAgent.agentType)}`;
onComplete(message);
} catch (err) {
setSaveError(err instanceof Error ? err.message : 'Failed to save agent');
}
}, [wizardData, onComplete, setAppState]);
const handleSave = useCallback(() => saveAgent(false), [saveAgent]);
const handleSaveAndEdit = useCallback(() => saveAgent(true), [saveAgent]);
return <ConfirmStep tools={tools} existingAgents={existingAgents} onSave={handleSave} onSaveAndEdit={handleSaveAndEdit} error={saveError} />;
},
[wizardData, onComplete, setAppState],
)
const handleSave = useCallback(() => saveAgent(false), [saveAgent])
const handleSaveAndEdit = useCallback(() => saveAgent(true), [saveAgent])
return (
<ConfirmStep
tools={tools}
existingAgents={existingAgents}
onSave={handleSave}
onSaveAndEdit={handleSaveAndEdit}
error={saveError}
/>
)
}

View File

@@ -1,122 +1,94 @@
import { c as _c } from "react/compiler-runtime";
import React, { type ReactNode, useCallback, useState } from 'react';
import { Box, Text } from '../../../../ink.js';
import { useKeybinding } from '../../../../keybindings/useKeybinding.js';
import { editPromptInEditor } from '../../../../utils/promptEditor.js';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Byline } from '../../../design-system/Byline.js';
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js';
import TextInput from '../../../TextInput.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import type { AgentWizardData } from '../types.js';
export function DescriptionStep() {
const $ = _c(18);
const {
goNext,
goBack,
updateWizardData,
wizardData
} = useWizard();
const [whenToUse, setWhenToUse] = useState(wizardData.whenToUse || "");
const [cursorOffset, setCursorOffset] = useState(whenToUse.length);
const [error, setError] = useState(null);
let t0;
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
t0 = {
context: "Settings"
};
$[0] = t0;
} else {
t0 = $[0];
import React, { type ReactNode, useCallback, useState } from 'react'
import { Box, Text } from '../../../../ink.js'
import { useKeybinding } from '../../../../keybindings/useKeybinding.js'
import { editPromptInEditor } from '../../../../utils/promptEditor.js'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Byline } from '../../../design-system/Byline.js'
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js'
import TextInput from '../../../TextInput.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import type { AgentWizardData } from '../types.js'
export function DescriptionStep(): ReactNode {
const { goNext, goBack, updateWizardData, wizardData } =
useWizard<AgentWizardData>()
const [whenToUse, setWhenToUse] = useState(wizardData.whenToUse || '')
const [cursorOffset, setCursorOffset] = useState(whenToUse.length)
const [error, setError] = useState<string | null>(null)
// Handle escape key - use Settings context so 'n' key doesn't cancel (allows typing 'n' in input)
useKeybinding('confirm:no', goBack, { context: 'Settings' })
const handleExternalEditor = useCallback(async () => {
const result = await editPromptInEditor(whenToUse)
if (result.content !== null) {
setWhenToUse(result.content)
setCursorOffset(result.content.length)
}
}, [whenToUse])
useKeybinding('chat:externalEditor', handleExternalEditor, {
context: 'Chat',
})
const handleSubmit = (value: string): void => {
const trimmedValue = value.trim()
if (!trimmedValue) {
setError('Description is required')
return
}
setError(null)
updateWizardData({ whenToUse: trimmedValue })
goNext()
}
useKeybinding("confirm:no", goBack, t0);
let t1;
if ($[1] !== whenToUse) {
t1 = async () => {
const result = await editPromptInEditor(whenToUse);
if (result.content !== null) {
setWhenToUse(result.content);
setCursorOffset(result.content.length);
return (
<WizardDialogLayout
subtitle="Description (tell Claude when to use this agent)"
footerText={
<Byline>
<KeyboardShortcutHint shortcut="Type" action="enter text" />
<KeyboardShortcutHint shortcut="Enter" action="continue" />
<ConfigurableShortcutHint
action="chat:externalEditor"
context="Chat"
fallback="ctrl+g"
description="open in editor"
/>
<ConfigurableShortcutHint
action="confirm:no"
context="Settings"
fallback="Esc"
description="go back"
/>
</Byline>
}
};
$[1] = whenToUse;
$[2] = t1;
} else {
t1 = $[2];
}
const handleExternalEditor = t1;
let t2;
if ($[3] === Symbol.for("react.memo_cache_sentinel")) {
t2 = {
context: "Chat"
};
$[3] = t2;
} else {
t2 = $[3];
}
useKeybinding("chat:externalEditor", handleExternalEditor, t2);
let t3;
if ($[4] !== goNext || $[5] !== updateWizardData) {
t3 = value => {
const trimmedValue = value.trim();
if (!trimmedValue) {
setError("Description is required");
return;
}
setError(null);
updateWizardData({
whenToUse: trimmedValue
});
goNext();
};
$[4] = goNext;
$[5] = updateWizardData;
$[6] = t3;
} else {
t3 = $[6];
}
const handleSubmit = t3;
let t4;
if ($[7] === Symbol.for("react.memo_cache_sentinel")) {
t4 = <Byline><KeyboardShortcutHint shortcut="Type" action="enter text" /><KeyboardShortcutHint shortcut="Enter" action="continue" /><ConfigurableShortcutHint action="chat:externalEditor" context="Chat" fallback="ctrl+g" description="open in editor" /><ConfigurableShortcutHint action="confirm:no" context="Settings" fallback="Esc" description="go back" /></Byline>;
$[7] = t4;
} else {
t4 = $[7];
}
let t5;
if ($[8] === Symbol.for("react.memo_cache_sentinel")) {
t5 = <Text>When should Claude use this agent?</Text>;
$[8] = t5;
} else {
t5 = $[8];
}
let t6;
if ($[9] !== cursorOffset || $[10] !== handleSubmit || $[11] !== whenToUse) {
t6 = <Box marginTop={1}><TextInput value={whenToUse} onChange={setWhenToUse} onSubmit={handleSubmit} placeholder="e.g., use this agent after you're done writing code..." columns={80} cursorOffset={cursorOffset} onChangeCursorOffset={setCursorOffset} focus={true} showCursor={true} /></Box>;
$[9] = cursorOffset;
$[10] = handleSubmit;
$[11] = whenToUse;
$[12] = t6;
} else {
t6 = $[12];
}
let t7;
if ($[13] !== error) {
t7 = error && <Box marginTop={1}><Text color="error">{error}</Text></Box>;
$[13] = error;
$[14] = t7;
} else {
t7 = $[14];
}
let t8;
if ($[15] !== t6 || $[16] !== t7) {
t8 = <WizardDialogLayout subtitle="Description (tell Claude when to use this agent)" footerText={t4}><Box flexDirection="column">{t5}{t6}{t7}</Box></WizardDialogLayout>;
$[15] = t6;
$[16] = t7;
$[17] = t8;
} else {
t8 = $[17];
}
return t8;
>
<Box flexDirection="column">
<Text>When should Claude use this agent?</Text>
<Box marginTop={1}>
<TextInput
value={whenToUse}
onChange={setWhenToUse}
onSubmit={handleSubmit}
placeholder="e.g., use this agent after you're done writing code..."
columns={80}
cursorOffset={cursorOffset}
onChangeCursorOffset={setCursorOffset}
focus
showCursor
/>
</Box>
{error && (
<Box marginTop={1}>
<Text color="error">{error}</Text>
</Box>
)}
</Box>
</WizardDialogLayout>
)
}

View File

@@ -1,58 +1,57 @@
import { APIUserAbortError } from '@anthropic-ai/sdk';
import React, { type ReactNode, useCallback, useRef, useState } from 'react';
import { useMainLoopModel } from '../../../../hooks/useMainLoopModel.js';
import { Box, Text } from '../../../../ink.js';
import { useKeybinding } from '../../../../keybindings/useKeybinding.js';
import { createAbortController } from '../../../../utils/abortController.js';
import { editPromptInEditor } from '../../../../utils/promptEditor.js';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Byline } from '../../../design-system/Byline.js';
import { Spinner } from '../../../Spinner.js';
import TextInput from '../../../TextInput.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import { generateAgent } from '../../generateAgent.js';
import type { AgentWizardData } from '../types.js';
import { APIUserAbortError } from '@anthropic-ai/sdk'
import React, { type ReactNode, useCallback, useRef, useState } from 'react'
import { useMainLoopModel } from '../../../../hooks/useMainLoopModel.js'
import { Box, Text } from '../../../../ink.js'
import { useKeybinding } from '../../../../keybindings/useKeybinding.js'
import { createAbortController } from '../../../../utils/abortController.js'
import { editPromptInEditor } from '../../../../utils/promptEditor.js'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Byline } from '../../../design-system/Byline.js'
import { Spinner } from '../../../Spinner.js'
import TextInput from '../../../TextInput.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import { generateAgent } from '../../generateAgent.js'
import type { AgentWizardData } from '../types.js'
export function GenerateStep(): ReactNode {
const {
updateWizardData,
goBack,
goToStep,
wizardData
} = useWizard<AgentWizardData>();
const [prompt, setPrompt] = useState(wizardData.generationPrompt || '');
const [isGenerating, setIsGenerating] = useState(false);
const [error, setError] = useState<string | null>(null);
const [cursorOffset, setCursorOffset] = useState(prompt.length);
const model = useMainLoopModel();
const abortControllerRef = useRef<AbortController | null>(null);
const { updateWizardData, goBack, goToStep, wizardData } =
useWizard<AgentWizardData>()
const [prompt, setPrompt] = useState(wizardData.generationPrompt || '')
const [isGenerating, setIsGenerating] = useState(false)
const [error, setError] = useState<string | null>(null)
const [cursorOffset, setCursorOffset] = useState(prompt.length)
const model = useMainLoopModel()
const abortControllerRef = useRef<AbortController | null>(null)
// Cancel generation when escape pressed during generation
const handleCancelGeneration = useCallback(() => {
if (abortControllerRef.current) {
abortControllerRef.current.abort();
abortControllerRef.current = null;
setIsGenerating(false);
setError('Generation cancelled');
abortControllerRef.current.abort()
abortControllerRef.current = null
setIsGenerating(false)
setError('Generation cancelled')
}
}, []);
}, [])
// Use Settings context so 'n' key doesn't cancel (allows typing 'n' in prompt input)
useKeybinding('confirm:no', handleCancelGeneration, {
context: 'Settings',
isActive: isGenerating
});
isActive: isGenerating,
})
const handleExternalEditor = useCallback(async () => {
const result = await editPromptInEditor(prompt);
const result = await editPromptInEditor(prompt)
if (result.content !== null) {
setPrompt(result.content);
setCursorOffset(result.content.length);
setPrompt(result.content)
setCursorOffset(result.content.length)
}
}, [prompt]);
}, [prompt])
useKeybinding('chat:externalEditor', handleExternalEditor, {
context: 'Chat',
isActive: !isGenerating
});
isActive: !isGenerating,
})
// Go back when escape pressed while not generating
const handleGoBack = useCallback(() => {
@@ -62,81 +61,141 @@ export function GenerateStep(): ReactNode {
systemPrompt: '',
whenToUse: '',
generatedAgent: undefined,
wasGenerated: false
});
setPrompt('');
setError(null);
goBack();
}, [updateWizardData, goBack]);
wasGenerated: false,
})
setPrompt('')
setError(null)
goBack()
}, [updateWizardData, goBack])
// Use Settings context so 'n' key doesn't cancel (allows typing 'n' in prompt input)
useKeybinding('confirm:no', handleGoBack, {
context: 'Settings',
isActive: !isGenerating
});
isActive: !isGenerating,
})
const handleGenerate = async (): Promise<void> => {
const trimmedPrompt = prompt.trim();
const trimmedPrompt = prompt.trim()
if (!trimmedPrompt) {
setError('Please describe what the agent should do');
return;
setError('Please describe what the agent should do')
return
}
setError(null);
setIsGenerating(true);
setError(null)
setIsGenerating(true)
updateWizardData({
generationPrompt: trimmedPrompt,
isGenerating: true
});
isGenerating: true,
})
// Create abort controller for this generation
const controller = createAbortController();
abortControllerRef.current = controller;
const controller = createAbortController()
abortControllerRef.current = controller
try {
const generated = await generateAgent(trimmedPrompt, model, [], controller.signal);
const generated = await generateAgent(
trimmedPrompt,
model,
[],
controller.signal,
)
updateWizardData({
agentType: generated.identifier,
whenToUse: generated.whenToUse,
systemPrompt: generated.systemPrompt,
generatedAgent: generated,
isGenerating: false,
wasGenerated: true
});
wasGenerated: true,
})
// Skip directly to ToolsStep (index 6) - matching original flow
goToStep(6);
goToStep(6)
} catch (err) {
// Don't show error if it was cancelled (already set in escape handler)
if (err instanceof APIUserAbortError) {
// User cancelled - no error to show
} else if (err instanceof Error && !err.message.includes('No assistant message found')) {
setError(err.message || 'Failed to generate agent');
} else if (
err instanceof Error &&
!err.message.includes('No assistant message found')
) {
setError(err.message || 'Failed to generate agent')
}
updateWizardData({
isGenerating: false
});
updateWizardData({ isGenerating: false })
} finally {
setIsGenerating(false);
abortControllerRef.current = null;
setIsGenerating(false)
abortControllerRef.current = null
}
};
const subtitle = 'Describe what this agent should do and when it should be used (be comprehensive for best results)';
}
const subtitle =
'Describe what this agent should do and when it should be used (be comprehensive for best results)'
if (isGenerating) {
return <WizardDialogLayout subtitle={subtitle} footerText={<ConfigurableShortcutHint action="confirm:no" context="Settings" fallback="Esc" description="cancel" />}>
return (
<WizardDialogLayout
subtitle={subtitle}
footerText={
<ConfigurableShortcutHint
action="confirm:no"
context="Settings"
fallback="Esc"
description="cancel"
/>
}
>
<Box flexDirection="row" alignItems="center">
<Spinner />
<Text color="suggestion"> Generating agent from description...</Text>
</Box>
</WizardDialogLayout>;
</WizardDialogLayout>
)
}
return <WizardDialogLayout subtitle={subtitle} footerText={<Byline>
<ConfigurableShortcutHint action="confirm:yes" context="Confirmation" fallback="Enter" description="submit" />
<ConfigurableShortcutHint action="chat:externalEditor" context="Chat" fallback="ctrl+g" description="open in editor" />
<ConfigurableShortcutHint action="confirm:no" context="Settings" fallback="Esc" description="go back" />
</Byline>}>
return (
<WizardDialogLayout
subtitle={subtitle}
footerText={
<Byline>
<ConfigurableShortcutHint
action="confirm:yes"
context="Confirmation"
fallback="Enter"
description="submit"
/>
<ConfigurableShortcutHint
action="chat:externalEditor"
context="Chat"
fallback="ctrl+g"
description="open in editor"
/>
<ConfigurableShortcutHint
action="confirm:no"
context="Settings"
fallback="Esc"
description="go back"
/>
</Byline>
}
>
<Box flexDirection="column">
{error && <Box marginBottom={1}>
{error && (
<Box marginBottom={1}>
<Text color="error">{error}</Text>
</Box>}
<TextInput value={prompt} onChange={setPrompt} onSubmit={handleGenerate} placeholder="e.g., Help me write unit tests for my code..." columns={80} cursorOffset={cursorOffset} onChangeCursorOffset={setCursorOffset} focus showCursor />
</Box>
)}
<TextInput
value={prompt}
onChange={setPrompt}
onSubmit={handleGenerate}
placeholder="e.g., Help me write unit tests for my code..."
columns={80}
cursorOffset={cursorOffset}
onChangeCursorOffset={setCursorOffset}
focus
showCursor
/>
</Box>
</WizardDialogLayout>;
</WizardDialogLayout>
)
}

View File

@@ -1,79 +1,55 @@
import { c as _c } from "react/compiler-runtime";
import React, { type ReactNode } from 'react';
import { Box } from '../../../../ink.js';
import type { SettingSource } from '../../../../utils/settings/constants.js';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Select } from '../../../CustomSelect/select.js';
import { Byline } from '../../../design-system/Byline.js';
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import type { AgentWizardData } from '../types.js';
export function LocationStep() {
const $ = _c(11);
const {
goNext,
updateWizardData,
cancel
} = useWizard();
let t0;
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
t0 = {
label: "Project (.claude/agents/)",
value: "projectSettings" as SettingSource
};
$[0] = t0;
} else {
t0 = $[0];
}
let t1;
if ($[1] === Symbol.for("react.memo_cache_sentinel")) {
t1 = [t0, {
label: "Personal (~/.claude/agents/)",
value: "userSettings" as SettingSource
}];
$[1] = t1;
} else {
t1 = $[1];
}
const locationOptions = t1;
let t2;
if ($[2] === Symbol.for("react.memo_cache_sentinel")) {
t2 = <Byline><KeyboardShortcutHint shortcut={"\u2191\u2193"} action="navigate" /><KeyboardShortcutHint shortcut="Enter" action="select" /><ConfigurableShortcutHint action="confirm:no" context="Confirmation" fallback="Esc" description="cancel" /></Byline>;
$[2] = t2;
} else {
t2 = $[2];
}
let t3;
if ($[3] !== goNext || $[4] !== updateWizardData) {
t3 = value => {
updateWizardData({
location: value as SettingSource
});
goNext();
};
$[3] = goNext;
$[4] = updateWizardData;
$[5] = t3;
} else {
t3 = $[5];
}
let t4;
if ($[6] !== cancel) {
t4 = () => cancel();
$[6] = cancel;
$[7] = t4;
} else {
t4 = $[7];
}
let t5;
if ($[8] !== t3 || $[9] !== t4) {
t5 = <WizardDialogLayout subtitle="Choose location" footerText={t2}><Box><Select key="location-select" options={locationOptions} onChange={t3} onCancel={t4} /></Box></WizardDialogLayout>;
$[8] = t3;
$[9] = t4;
$[10] = t5;
} else {
t5 = $[10];
}
return t5;
import React, { type ReactNode } from 'react'
import { Box } from '../../../../ink.js'
import type { SettingSource } from '../../../../utils/settings/constants.js'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Select } from '../../../CustomSelect/select.js'
import { Byline } from '../../../design-system/Byline.js'
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import type { AgentWizardData } from '../types.js'
export function LocationStep(): ReactNode {
const { goNext, updateWizardData, cancel } = useWizard<AgentWizardData>()
const locationOptions = [
{
label: 'Project (.claude/agents/)',
value: 'projectSettings' as SettingSource,
},
{
label: 'Personal (~/.claude/agents/)',
value: 'userSettings' as SettingSource,
},
]
return (
<WizardDialogLayout
subtitle="Choose location"
footerText={
<Byline>
<KeyboardShortcutHint shortcut="↑↓" action="navigate" />
<KeyboardShortcutHint shortcut="Enter" action="select" />
<ConfigurableShortcutHint
action="confirm:no"
context="Confirmation"
fallback="Esc"
description="cancel"
/>
</Byline>
}
>
<Box>
<Select
key="location-select"
options={locationOptions}
onChange={(value: string) => {
updateWizardData({ location: value as SettingSource })
goNext()
}}
onCancel={() => cancel()}
/>
</Box>
</WizardDialogLayout>
)
}

View File

@@ -1,112 +1,102 @@
import { c as _c } from "react/compiler-runtime";
import React, { type ReactNode } from 'react';
import { Box } from '../../../../ink.js';
import { useKeybinding } from '../../../../keybindings/useKeybinding.js';
import { isAutoMemoryEnabled } from '../../../../memdir/paths.js';
import { type AgentMemoryScope, loadAgentMemoryPrompt } from '../../../../tools/AgentTool/agentMemory.js';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Select } from '../../../CustomSelect/select.js';
import { Byline } from '../../../design-system/Byline.js';
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import type { AgentWizardData } from '../types.js';
import React, { type ReactNode } from 'react'
import { Box } from '../../../../ink.js'
import { useKeybinding } from '../../../../keybindings/useKeybinding.js'
import { isAutoMemoryEnabled } from '../../../../memdir/paths.js'
import {
type AgentMemoryScope,
loadAgentMemoryPrompt,
} from '../../../../tools/AgentTool/agentMemory.js'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Select } from '../../../CustomSelect/select.js'
import { Byline } from '../../../design-system/Byline.js'
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import type { AgentWizardData } from '../types.js'
type MemoryOption = {
label: string;
value: AgentMemoryScope | 'none';
};
export function MemoryStep() {
const $ = _c(13);
const {
goNext,
goBack,
updateWizardData,
wizardData
} = useWizard();
let t0;
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
t0 = {
context: "Confirmation"
};
$[0] = t0;
} else {
t0 = $[0];
}
useKeybinding("confirm:no", goBack, t0);
const isUserScope = wizardData.location === "userSettings";
let t1;
if ($[1] !== isUserScope) {
t1 = isUserScope ? [{
label: "User scope (~/.claude/agent-memory/) (Recommended)",
value: "user"
}, {
label: "None (no persistent memory)",
value: "none"
}, {
label: "Project scope (.claude/agent-memory/)",
value: "project"
}, {
label: "Local scope (.claude/agent-memory-local/)",
value: "local"
}] : [{
label: "Project scope (.claude/agent-memory/) (Recommended)",
value: "project"
}, {
label: "None (no persistent memory)",
value: "none"
}, {
label: "User scope (~/.claude/agent-memory/)",
value: "user"
}, {
label: "Local scope (.claude/agent-memory-local/)",
value: "local"
}];
$[1] = isUserScope;
$[2] = t1;
} else {
t1 = $[2];
}
const memoryOptions = t1;
let t2;
if ($[3] !== goNext || $[4] !== updateWizardData || $[5] !== wizardData.finalAgent || $[6] !== wizardData.systemPrompt) {
t2 = value => {
const memory = value === "none" ? undefined : value as AgentMemoryScope;
const agentType = wizardData.finalAgent?.agentType;
updateWizardData({
selectedMemory: memory,
finalAgent: wizardData.finalAgent ? {
...wizardData.finalAgent,
memory,
getSystemPrompt: isAutoMemoryEnabled() && memory && agentType ? () => wizardData.systemPrompt + "\n\n" + loadAgentMemoryPrompt(agentType, memory) : () => wizardData.systemPrompt
} : undefined
});
goNext();
};
$[3] = goNext;
$[4] = updateWizardData;
$[5] = wizardData.finalAgent;
$[6] = wizardData.systemPrompt;
$[7] = t2;
} else {
t2 = $[7];
}
const handleSelect = t2;
let t3;
if ($[8] === Symbol.for("react.memo_cache_sentinel")) {
t3 = <Byline><KeyboardShortcutHint shortcut={"\u2191\u2193"} action="navigate" /><KeyboardShortcutHint shortcut="Enter" action="select" /><ConfigurableShortcutHint action="confirm:no" context="Confirmation" fallback="Esc" description="go back" /></Byline>;
$[8] = t3;
} else {
t3 = $[8];
}
let t4;
if ($[9] !== goBack || $[10] !== handleSelect || $[11] !== memoryOptions) {
t4 = <WizardDialogLayout subtitle="Configure agent memory" footerText={t3}><Box><Select key="memory-select" options={memoryOptions} onChange={handleSelect} onCancel={goBack} /></Box></WizardDialogLayout>;
$[9] = goBack;
$[10] = handleSelect;
$[11] = memoryOptions;
$[12] = t4;
} else {
t4 = $[12];
}
return t4;
label: string
value: AgentMemoryScope | 'none'
}
export function MemoryStep(): ReactNode {
const { goNext, goBack, updateWizardData, wizardData } =
useWizard<AgentWizardData>()
useKeybinding('confirm:no', goBack, { context: 'Confirmation' })
const isUserScope = wizardData.location === 'userSettings'
// Build options with the recommended default first, then alternatives
// The recommended scope matches the agent's location (project agent → project memory, user agent → user memory)
const memoryOptions: MemoryOption[] = isUserScope
? [
{
label: 'User scope (~/.claude/agent-memory/) (Recommended)',
value: 'user',
},
{ label: 'None (no persistent memory)', value: 'none' },
{ label: 'Project scope (.claude/agent-memory/)', value: 'project' },
{ label: 'Local scope (.claude/agent-memory-local/)', value: 'local' },
]
: [
{
label: 'Project scope (.claude/agent-memory/) (Recommended)',
value: 'project',
},
{ label: 'None (no persistent memory)', value: 'none' },
{ label: 'User scope (~/.claude/agent-memory/)', value: 'user' },
{ label: 'Local scope (.claude/agent-memory-local/)', value: 'local' },
]
const handleSelect = (value: string): void => {
const memory = value === 'none' ? undefined : (value as AgentMemoryScope)
const agentType = wizardData.finalAgent?.agentType
updateWizardData({
selectedMemory: memory,
// Update finalAgent with memory and rewire getSystemPrompt to include memory loading.
// Explicitly set memory (not conditional spread) so selecting 'none' after going back clears it.
finalAgent: wizardData.finalAgent
? {
...wizardData.finalAgent,
memory,
getSystemPrompt:
isAutoMemoryEnabled() && memory && agentType
? () =>
wizardData.systemPrompt! +
'\n\n' +
loadAgentMemoryPrompt(agentType, memory)
: () => wizardData.systemPrompt!,
}
: undefined,
})
goNext()
}
return (
<WizardDialogLayout
subtitle="Configure agent memory"
footerText={
<Byline>
<KeyboardShortcutHint shortcut="↑↓" action="navigate" />
<KeyboardShortcutHint shortcut="Enter" action="select" />
<ConfigurableShortcutHint
action="confirm:no"
context="Confirmation"
fallback="Esc"
description="go back"
/>
</Byline>
}
>
<Box>
<Select
key="memory-select"
options={memoryOptions}
onChange={handleSelect}
onCancel={goBack}
/>
</Box>
</WizardDialogLayout>
)
}

View File

@@ -1,79 +1,65 @@
import { c as _c } from "react/compiler-runtime";
import React, { type ReactNode } from 'react';
import { Box } from '../../../../ink.js';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Select } from '../../../CustomSelect/select.js';
import { Byline } from '../../../design-system/Byline.js';
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import type { AgentWizardData } from '../types.js';
export function MethodStep() {
const $ = _c(11);
const {
goNext,
goBack,
updateWizardData,
goToStep
} = useWizard();
let t0;
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
t0 = [{
label: "Generate with Claude (recommended)",
value: "generate"
}, {
label: "Manual configuration",
value: "manual"
}];
$[0] = t0;
} else {
t0 = $[0];
}
const methodOptions = t0;
let t1;
if ($[1] === Symbol.for("react.memo_cache_sentinel")) {
t1 = <Byline><KeyboardShortcutHint shortcut={"\u2191\u2193"} action="navigate" /><KeyboardShortcutHint shortcut="Enter" action="select" /><ConfigurableShortcutHint action="confirm:no" context="Confirmation" fallback="Esc" description="go back" /></Byline>;
$[1] = t1;
} else {
t1 = $[1];
}
let t2;
if ($[2] !== goNext || $[3] !== goToStep || $[4] !== updateWizardData) {
t2 = value => {
const method = value as 'generate' | 'manual';
updateWizardData({
method,
wasGenerated: method === "generate"
});
if (method === "generate") {
goNext();
} else {
goToStep(3);
import React, { type ReactNode } from 'react'
import { Box } from '../../../../ink.js'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Select } from '../../../CustomSelect/select.js'
import { Byline } from '../../../design-system/Byline.js'
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import type { AgentWizardData } from '../types.js'
export function MethodStep(): ReactNode {
const { goNext, goBack, updateWizardData, goToStep } =
useWizard<AgentWizardData>()
const methodOptions = [
{
label: 'Generate with Claude (recommended)',
value: 'generate',
},
{
label: 'Manual configuration',
value: 'manual',
},
]
return (
<WizardDialogLayout
subtitle="Creation method"
footerText={
<Byline>
<KeyboardShortcutHint shortcut="↑↓" action="navigate" />
<KeyboardShortcutHint shortcut="Enter" action="select" />
<ConfigurableShortcutHint
action="confirm:no"
context="Confirmation"
fallback="Esc"
description="go back"
/>
</Byline>
}
};
$[2] = goNext;
$[3] = goToStep;
$[4] = updateWizardData;
$[5] = t2;
} else {
t2 = $[5];
}
let t3;
if ($[6] !== goBack) {
t3 = () => goBack();
$[6] = goBack;
$[7] = t3;
} else {
t3 = $[7];
}
let t4;
if ($[8] !== t2 || $[9] !== t3) {
t4 = <WizardDialogLayout subtitle="Creation method" footerText={t1}><Box><Select key="method-select" options={methodOptions} onChange={t2} onCancel={t3} /></Box></WizardDialogLayout>;
$[8] = t2;
$[9] = t3;
$[10] = t4;
} else {
t4 = $[10];
}
return t4;
>
<Box>
<Select
key="method-select"
options={methodOptions}
onChange={(value: string) => {
const method = value as 'generate' | 'manual'
updateWizardData({
method,
wasGenerated: method === 'generate',
})
// Dynamic navigation based on method
if (method === 'generate') {
goNext() // Go to GenerateStep (index 2)
} else {
goToStep(3) // Skip to TypeStep (index 3)
}
}}
onCancel={() => goBack()}
/>
</Box>
</WizardDialogLayout>
)
}

View File

@@ -1,51 +1,42 @@
import { c as _c } from "react/compiler-runtime";
import React, { type ReactNode } from 'react';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Byline } from '../../../design-system/Byline.js';
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import { ModelSelector } from '../../ModelSelector.js';
import type { AgentWizardData } from '../types.js';
export function ModelStep() {
const $ = _c(8);
const {
goNext,
goBack,
updateWizardData,
wizardData
} = useWizard();
let t0;
if ($[0] !== goNext || $[1] !== updateWizardData) {
t0 = model => {
updateWizardData({
selectedModel: model
});
goNext();
};
$[0] = goNext;
$[1] = updateWizardData;
$[2] = t0;
} else {
t0 = $[2];
import React, { type ReactNode } from 'react'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Byline } from '../../../design-system/Byline.js'
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import { ModelSelector } from '../../ModelSelector.js'
import type { AgentWizardData } from '../types.js'
export function ModelStep(): ReactNode {
const { goNext, goBack, updateWizardData, wizardData } =
useWizard<AgentWizardData>()
const handleComplete = (model?: string): void => {
updateWizardData({ selectedModel: model })
goNext()
}
const handleComplete = t0;
let t1;
if ($[3] === Symbol.for("react.memo_cache_sentinel")) {
t1 = <Byline><KeyboardShortcutHint shortcut={"\u2191\u2193"} action="navigate" /><KeyboardShortcutHint shortcut="Enter" action="select" /><ConfigurableShortcutHint action="confirm:no" context="Confirmation" fallback="Esc" description="go back" /></Byline>;
$[3] = t1;
} else {
t1 = $[3];
}
let t2;
if ($[4] !== goBack || $[5] !== handleComplete || $[6] !== wizardData.selectedModel) {
t2 = <WizardDialogLayout subtitle="Select model" footerText={t1}><ModelSelector initialModel={wizardData.selectedModel} onComplete={handleComplete} onCancel={goBack} /></WizardDialogLayout>;
$[4] = goBack;
$[5] = handleComplete;
$[6] = wizardData.selectedModel;
$[7] = t2;
} else {
t2 = $[7];
}
return t2;
return (
<WizardDialogLayout
subtitle="Select model"
footerText={
<Byline>
<KeyboardShortcutHint shortcut="↑↓" action="navigate" />
<KeyboardShortcutHint shortcut="Enter" action="select" />
<ConfigurableShortcutHint
action="confirm:no"
context="Confirmation"
fallback="Esc"
description="go back"
/>
</Byline>
}
>
<ModelSelector
initialModel={wizardData.selectedModel}
onComplete={handleComplete}
onCancel={goBack}
/>
</WizardDialogLayout>
)
}

View File

@@ -1,127 +1,97 @@
import { c as _c } from "react/compiler-runtime";
import React, { type ReactNode, useCallback, useState } from 'react';
import { Box, Text } from '../../../../ink.js';
import { useKeybinding } from '../../../../keybindings/useKeybinding.js';
import { editPromptInEditor } from '../../../../utils/promptEditor.js';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Byline } from '../../../design-system/Byline.js';
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js';
import TextInput from '../../../TextInput.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import type { AgentWizardData } from '../types.js';
export function PromptStep() {
const $ = _c(20);
const {
goNext,
goBack,
updateWizardData,
wizardData
} = useWizard();
const [systemPrompt, setSystemPrompt] = useState(wizardData.systemPrompt || "");
const [cursorOffset, setCursorOffset] = useState(systemPrompt.length);
const [error, setError] = useState(null);
let t0;
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
t0 = {
context: "Settings"
};
$[0] = t0;
} else {
t0 = $[0];
import React, { type ReactNode, useCallback, useState } from 'react'
import { Box, Text } from '../../../../ink.js'
import { useKeybinding } from '../../../../keybindings/useKeybinding.js'
import { editPromptInEditor } from '../../../../utils/promptEditor.js'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Byline } from '../../../design-system/Byline.js'
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js'
import TextInput from '../../../TextInput.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import type { AgentWizardData } from '../types.js'
export function PromptStep(): ReactNode {
const { goNext, goBack, updateWizardData, wizardData } =
useWizard<AgentWizardData>()
const [systemPrompt, setSystemPrompt] = useState(
wizardData.systemPrompt || '',
)
const [cursorOffset, setCursorOffset] = useState(systemPrompt.length)
const [error, setError] = useState<string | null>(null)
// Handle escape key - use Settings context so 'n' key doesn't cancel (allows typing 'n' in input)
useKeybinding('confirm:no', goBack, { context: 'Settings' })
const handleExternalEditor = useCallback(async () => {
const result = await editPromptInEditor(systemPrompt)
if (result.content !== null) {
setSystemPrompt(result.content)
setCursorOffset(result.content.length)
}
}, [systemPrompt])
useKeybinding('chat:externalEditor', handleExternalEditor, {
context: 'Chat',
})
const handleSubmit = (): void => {
const trimmedPrompt = systemPrompt.trim()
if (!trimmedPrompt) {
setError('System prompt is required')
return
}
setError(null)
updateWizardData({ systemPrompt: trimmedPrompt })
goNext()
}
useKeybinding("confirm:no", goBack, t0);
let t1;
if ($[1] !== systemPrompt) {
t1 = async () => {
const result = await editPromptInEditor(systemPrompt);
if (result.content !== null) {
setSystemPrompt(result.content);
setCursorOffset(result.content.length);
return (
<WizardDialogLayout
subtitle="System prompt"
footerText={
<Byline>
<KeyboardShortcutHint shortcut="Type" action="enter text" />
<KeyboardShortcutHint shortcut="Enter" action="continue" />
<ConfigurableShortcutHint
action="chat:externalEditor"
context="Chat"
fallback="ctrl+g"
description="open in editor"
/>
<ConfigurableShortcutHint
action="confirm:no"
context="Settings"
fallback="Esc"
description="go back"
/>
</Byline>
}
};
$[1] = systemPrompt;
$[2] = t1;
} else {
t1 = $[2];
}
const handleExternalEditor = t1;
let t2;
if ($[3] === Symbol.for("react.memo_cache_sentinel")) {
t2 = {
context: "Chat"
};
$[3] = t2;
} else {
t2 = $[3];
}
useKeybinding("chat:externalEditor", handleExternalEditor, t2);
let t3;
if ($[4] !== goNext || $[5] !== systemPrompt || $[6] !== updateWizardData) {
t3 = () => {
const trimmedPrompt = systemPrompt.trim();
if (!trimmedPrompt) {
setError("System prompt is required");
return;
}
setError(null);
updateWizardData({
systemPrompt: trimmedPrompt
});
goNext();
};
$[4] = goNext;
$[5] = systemPrompt;
$[6] = updateWizardData;
$[7] = t3;
} else {
t3 = $[7];
}
const handleSubmit = t3;
let t4;
if ($[8] === Symbol.for("react.memo_cache_sentinel")) {
t4 = <Byline><KeyboardShortcutHint shortcut="Type" action="enter text" /><KeyboardShortcutHint shortcut="Enter" action="continue" /><ConfigurableShortcutHint action="chat:externalEditor" context="Chat" fallback="ctrl+g" description="open in editor" /><ConfigurableShortcutHint action="confirm:no" context="Settings" fallback="Esc" description="go back" /></Byline>;
$[8] = t4;
} else {
t4 = $[8];
}
let t5;
let t6;
if ($[9] === Symbol.for("react.memo_cache_sentinel")) {
t5 = <Text>Enter the system prompt for your agent:</Text>;
t6 = <Text dimColor={true}>Be comprehensive for best results</Text>;
$[9] = t5;
$[10] = t6;
} else {
t5 = $[9];
t6 = $[10];
}
let t7;
if ($[11] !== cursorOffset || $[12] !== handleSubmit || $[13] !== systemPrompt) {
t7 = <Box marginTop={1}><TextInput value={systemPrompt} onChange={setSystemPrompt} onSubmit={handleSubmit} placeholder="You are a helpful code reviewer who..." columns={80} cursorOffset={cursorOffset} onChangeCursorOffset={setCursorOffset} focus={true} showCursor={true} /></Box>;
$[11] = cursorOffset;
$[12] = handleSubmit;
$[13] = systemPrompt;
$[14] = t7;
} else {
t7 = $[14];
}
let t8;
if ($[15] !== error) {
t8 = error && <Box marginTop={1}><Text color="error">{error}</Text></Box>;
$[15] = error;
$[16] = t8;
} else {
t8 = $[16];
}
let t9;
if ($[17] !== t7 || $[18] !== t8) {
t9 = <WizardDialogLayout subtitle="System prompt" footerText={t4}><Box flexDirection="column">{t5}{t6}{t7}{t8}</Box></WizardDialogLayout>;
$[17] = t7;
$[18] = t8;
$[19] = t9;
} else {
t9 = $[19];
}
return t9;
>
<Box flexDirection="column">
<Text>Enter the system prompt for your agent:</Text>
<Text dimColor>Be comprehensive for best results</Text>
<Box marginTop={1}>
<TextInput
value={systemPrompt}
onChange={setSystemPrompt}
onSubmit={handleSubmit}
placeholder="You are a helpful code reviewer who..."
columns={80}
cursorOffset={cursorOffset}
onChangeCursorOffset={setCursorOffset}
focus
showCursor
/>
</Box>
{error && (
<Box marginTop={1}>
<Text color="error">{error}</Text>
</Box>
)}
</Box>
</WizardDialogLayout>
)
}

View File

@@ -1,60 +1,52 @@
import { c as _c } from "react/compiler-runtime";
import React, { type ReactNode } from 'react';
import type { Tools } from '../../../../Tool.js';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Byline } from '../../../design-system/Byline.js';
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import { ToolSelector } from '../../ToolSelector.js';
import type { AgentWizardData } from '../types.js';
import React, { type ReactNode } from 'react'
import type { Tools } from '../../../../Tool.js'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Byline } from '../../../design-system/Byline.js'
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import { ToolSelector } from '../../ToolSelector.js'
import type { AgentWizardData } from '../types.js'
type Props = {
tools: Tools;
};
export function ToolsStep(t0) {
const $ = _c(9);
const {
tools
} = t0;
const {
goNext,
goBack,
updateWizardData,
wizardData
} = useWizard();
let t1;
if ($[0] !== goNext || $[1] !== updateWizardData) {
t1 = selectedTools => {
updateWizardData({
selectedTools
});
goNext();
};
$[0] = goNext;
$[1] = updateWizardData;
$[2] = t1;
} else {
t1 = $[2];
}
const handleComplete = t1;
const initialTools = wizardData.selectedTools;
let t2;
if ($[3] === Symbol.for("react.memo_cache_sentinel")) {
t2 = <Byline><KeyboardShortcutHint shortcut="Enter" action="toggle selection" /><KeyboardShortcutHint shortcut={"\u2191\u2193"} action="navigate" /><ConfigurableShortcutHint action="confirm:no" context="Confirmation" fallback="Esc" description="go back" /></Byline>;
$[3] = t2;
} else {
t2 = $[3];
}
let t3;
if ($[4] !== goBack || $[5] !== handleComplete || $[6] !== initialTools || $[7] !== tools) {
t3 = <WizardDialogLayout subtitle="Select tools" footerText={t2}><ToolSelector tools={tools} initialTools={initialTools} onComplete={handleComplete} onCancel={goBack} /></WizardDialogLayout>;
$[4] = goBack;
$[5] = handleComplete;
$[6] = initialTools;
$[7] = tools;
$[8] = t3;
} else {
t3 = $[8];
}
return t3;
tools: Tools
}
export function ToolsStep({ tools }: Props): ReactNode {
const { goNext, goBack, updateWizardData, wizardData } =
useWizard<AgentWizardData>()
const handleComplete = (selectedTools: string[] | undefined): void => {
updateWizardData({ selectedTools })
goNext()
}
// Pass through undefined to preserve "all tools" semantic
// ToolSelector will expand it internally for display purposes
const initialTools = wizardData.selectedTools
return (
<WizardDialogLayout
subtitle="Select tools"
footerText={
<Byline>
<KeyboardShortcutHint shortcut="Enter" action="toggle selection" />
<KeyboardShortcutHint shortcut="↑↓" action="navigate" />
<ConfigurableShortcutHint
action="confirm:no"
context="Confirmation"
fallback="Esc"
description="go back"
/>
</Byline>
}
>
<ToolSelector
tools={tools}
initialTools={initialTools}
onComplete={handleComplete}
onCancel={goBack}
/>
</WizardDialogLayout>
)
}

View File

@@ -1,102 +1,83 @@
import { c as _c } from "react/compiler-runtime";
import React, { type ReactNode, useState } from 'react';
import { Box, Text } from '../../../../ink.js';
import { useKeybinding } from '../../../../keybindings/useKeybinding.js';
import type { AgentDefinition } from '../../../../tools/AgentTool/loadAgentsDir.js';
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js';
import { Byline } from '../../../design-system/Byline.js';
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js';
import TextInput from '../../../TextInput.js';
import { useWizard } from '../../../wizard/index.js';
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js';
import { validateAgentType } from '../../validateAgent.js';
import type { AgentWizardData } from '../types.js';
import React, { type ReactNode, useState } from 'react'
import { Box, Text } from '../../../../ink.js'
import { useKeybinding } from '../../../../keybindings/useKeybinding.js'
import type { AgentDefinition } from '../../../../tools/AgentTool/loadAgentsDir.js'
import { ConfigurableShortcutHint } from '../../../ConfigurableShortcutHint.js'
import { Byline } from '../../../design-system/Byline.js'
import { KeyboardShortcutHint } from '../../../design-system/KeyboardShortcutHint.js'
import TextInput from '../../../TextInput.js'
import { useWizard } from '../../../wizard/index.js'
import { WizardDialogLayout } from '../../../wizard/WizardDialogLayout.js'
import { validateAgentType } from '../../validateAgent.js'
import type { AgentWizardData } from '../types.js'
type Props = {
existingAgents: AgentDefinition[];
};
export function TypeStep(_props) {
const $ = _c(15);
const {
goNext,
goBack,
updateWizardData,
wizardData
} = useWizard();
const [agentType, setAgentType] = useState(wizardData.agentType || "");
const [error, setError] = useState(null);
const [cursorOffset, setCursorOffset] = useState(agentType.length);
let t0;
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
t0 = {
context: "Settings"
};
$[0] = t0;
} else {
t0 = $[0];
}
useKeybinding("confirm:no", goBack, t0);
let t1;
if ($[1] !== goNext || $[2] !== updateWizardData) {
t1 = value => {
const trimmedValue = value.trim();
const validationError = validateAgentType(trimmedValue);
if (validationError) {
setError(validationError);
return;
}
setError(null);
updateWizardData({
agentType: trimmedValue
});
goNext();
};
$[1] = goNext;
$[2] = updateWizardData;
$[3] = t1;
} else {
t1 = $[3];
}
const handleSubmit = t1;
let t2;
if ($[4] === Symbol.for("react.memo_cache_sentinel")) {
t2 = <Byline><KeyboardShortcutHint shortcut="Type" action="enter text" /><KeyboardShortcutHint shortcut="Enter" action="continue" /><ConfigurableShortcutHint action="confirm:no" context="Settings" fallback="Esc" description="go back" /></Byline>;
$[4] = t2;
} else {
t2 = $[4];
}
let t3;
if ($[5] === Symbol.for("react.memo_cache_sentinel")) {
t3 = <Text>Enter a unique identifier for your agent:</Text>;
$[5] = t3;
} else {
t3 = $[5];
}
let t4;
if ($[6] !== agentType || $[7] !== cursorOffset || $[8] !== handleSubmit) {
t4 = <Box marginTop={1}><TextInput value={agentType} onChange={setAgentType} onSubmit={handleSubmit} placeholder="e.g., test-runner, tech-lead, etc" columns={60} cursorOffset={cursorOffset} onChangeCursorOffset={setCursorOffset} focus={true} showCursor={true} /></Box>;
$[6] = agentType;
$[7] = cursorOffset;
$[8] = handleSubmit;
$[9] = t4;
} else {
t4 = $[9];
}
let t5;
if ($[10] !== error) {
t5 = error && <Box marginTop={1}><Text color="error">{error}</Text></Box>;
$[10] = error;
$[11] = t5;
} else {
t5 = $[11];
}
let t6;
if ($[12] !== t4 || $[13] !== t5) {
t6 = <WizardDialogLayout subtitle="Agent type (identifier)" footerText={t2}><Box flexDirection="column">{t3}{t4}{t5}</Box></WizardDialogLayout>;
$[12] = t4;
$[13] = t5;
$[14] = t6;
} else {
t6 = $[14];
}
return t6;
existingAgents: AgentDefinition[]
}
export function TypeStep(_props: Props): ReactNode {
const { goNext, goBack, updateWizardData, wizardData } =
useWizard<AgentWizardData>()
const [agentType, setAgentType] = useState(wizardData.agentType || '')
const [error, setError] = useState<string | null>(null)
const [cursorOffset, setCursorOffset] = useState(agentType.length)
// Handle escape key - Go back to MethodStep
// Use Settings context so 'n' key doesn't cancel (allows typing 'n' in input)
useKeybinding('confirm:no', goBack, { context: 'Settings' })
const handleSubmit = (value: string): void => {
const trimmedValue = value.trim()
const validationError = validateAgentType(trimmedValue)
if (validationError) {
setError(validationError)
return
}
setError(null)
updateWizardData({ agentType: trimmedValue })
goNext()
}
return (
<WizardDialogLayout
subtitle="Agent type (identifier)"
footerText={
<Byline>
<KeyboardShortcutHint shortcut="Type" action="enter text" />
<KeyboardShortcutHint shortcut="Enter" action="continue" />
<ConfigurableShortcutHint
action="confirm:no"
context="Settings"
fallback="Esc"
description="go back"
/>
</Byline>
}
>
<Box flexDirection="column">
<Text>Enter a unique identifier for your agent:</Text>
<Box marginTop={1}>
<TextInput
value={agentType}
onChange={setAgentType}
onSubmit={handleSubmit}
placeholder="e.g., test-runner, tech-lead, etc"
columns={60}
cursorOffset={cursorOffset}
onChangeCursorOffset={setCursorOffset}
focus
showCursor
/>
</Box>
{error && (
<Box marginTop={1}>
<Text color="error">{error}</Text>
</Box>
)}
</Box>
</WizardDialogLayout>
)
}