mirror of
https://github.com/QwenLM/qwen-code.git
synced 2025-12-19 09:33:53 +00:00
feat: subagent feature wip
This commit is contained in:
@@ -44,7 +44,7 @@ import { FolderTrustDialog } from './components/FolderTrustDialog.js';
|
||||
import { ShellConfirmationDialog } from './components/ShellConfirmationDialog.js';
|
||||
import { RadioButtonSelect } from './components/shared/RadioButtonSelect.js';
|
||||
import {
|
||||
SubagentCreationWizard,
|
||||
AgentCreationWizard,
|
||||
AgentsManagerDialog,
|
||||
} from './components/subagents/index.js';
|
||||
import { Colors } from './colors.js';
|
||||
@@ -1093,7 +1093,7 @@ const App = ({ config, settings, startupWarnings = [], version }: AppProps) => {
|
||||
</Box>
|
||||
) : isSubagentCreateDialogOpen ? (
|
||||
<Box flexDirection="column">
|
||||
<SubagentCreationWizard
|
||||
<AgentCreationWizard
|
||||
onClose={closeSubagentCreateDialog}
|
||||
config={config}
|
||||
/>
|
||||
|
||||
@@ -40,7 +40,7 @@ vi.mock('../../utils/MarkdownDisplay.js', () => ({
|
||||
},
|
||||
}));
|
||||
vi.mock('../subagents/index.js', () => ({
|
||||
SubagentExecutionDisplay: function MockSubagentExecutionDisplay({
|
||||
AgentExecutionDisplay: function MockAgentExecutionDisplay({
|
||||
data,
|
||||
}: {
|
||||
data: { subagentName: string; taskDescription: string };
|
||||
|
||||
@@ -17,7 +17,7 @@ import {
|
||||
TodoResultDisplay,
|
||||
TaskResultDisplay,
|
||||
} from '@qwen-code/qwen-code-core';
|
||||
import { SubagentExecutionDisplay } from '../subagents/index.js';
|
||||
import { AgentExecutionDisplay } from '../subagents/index.js';
|
||||
|
||||
const STATIC_HEIGHT = 1;
|
||||
const RESERVED_LINE_COUNT = 5; // for tool name, status, padding etc.
|
||||
@@ -106,7 +106,7 @@ const SubagentExecutionRenderer: React.FC<{
|
||||
data: TaskResultDisplay;
|
||||
availableHeight?: number;
|
||||
childWidth: number;
|
||||
}> = ({ data }) => <SubagentExecutionDisplay data={data} />;
|
||||
}> = ({ data }) => <AgentExecutionDisplay data={data} />;
|
||||
|
||||
/**
|
||||
* Component to render string results (markdown or plain text)
|
||||
|
||||
@@ -6,20 +6,20 @@
|
||||
|
||||
import { useReducer, useCallback, useMemo } from 'react';
|
||||
import { Box, Text, useInput } from 'ink';
|
||||
import { wizardReducer, initialWizardState } from './reducers.js';
|
||||
import { wizardReducer, initialWizardState } from '../reducers.js';
|
||||
import { LocationSelector } from './LocationSelector.js';
|
||||
import { GenerationMethodSelector } from './GenerationMethodSelector.js';
|
||||
import { DescriptionInput } from './DescriptionInput.js';
|
||||
import { ToolSelector } from './ToolSelector.js';
|
||||
import { ColorSelector } from './ColorSelector.js';
|
||||
import { CreationSummary } from './CreationSummary.js';
|
||||
import { WizardStepProps } from './types.js';
|
||||
import { WIZARD_STEPS } from './constants.js';
|
||||
import { WizardStepProps } from '../types.js';
|
||||
import { WIZARD_STEPS } from '../constants.js';
|
||||
import { Config } from '@qwen-code/qwen-code-core';
|
||||
import { Colors } from '../../colors.js';
|
||||
import { theme } from '../../semantic-colors.js';
|
||||
import { Colors } from '../../../colors.js';
|
||||
import { theme } from '../../../semantic-colors.js';
|
||||
|
||||
interface SubagentCreationWizardProps {
|
||||
interface AgentCreationWizardProps {
|
||||
onClose: () => void;
|
||||
config: Config | null;
|
||||
}
|
||||
@@ -27,10 +27,10 @@ interface SubagentCreationWizardProps {
|
||||
/**
|
||||
* Main orchestrator component for the subagent creation wizard.
|
||||
*/
|
||||
export function SubagentCreationWizard({
|
||||
export function AgentCreationWizard({
|
||||
onClose,
|
||||
config,
|
||||
}: SubagentCreationWizardProps) {
|
||||
}: AgentCreationWizardProps) {
|
||||
const [state, dispatch] = useReducer(wizardReducer, initialWizardState);
|
||||
|
||||
const handleNext = useCallback(() => {
|
||||
@@ -6,10 +6,10 @@
|
||||
|
||||
import { useState, useEffect } from 'react';
|
||||
import { Box, Text } from 'ink';
|
||||
import { RadioButtonSelect } from '../shared/RadioButtonSelect.js';
|
||||
import { ColorOption } from './types.js';
|
||||
import { Colors } from '../../colors.js';
|
||||
import { COLOR_OPTIONS } from './constants.js';
|
||||
import { RadioButtonSelect } from '../../shared/RadioButtonSelect.js';
|
||||
import { ColorOption } from '../types.js';
|
||||
import { Colors } from '../../../colors.js';
|
||||
import { COLOR_OPTIONS } from '../constants.js';
|
||||
|
||||
const colorOptions: ColorOption[] = COLOR_OPTIONS;
|
||||
|
||||
@@ -6,11 +6,11 @@
|
||||
|
||||
import { useCallback, useState, useEffect } from 'react';
|
||||
import { Box, Text, useInput } from 'ink';
|
||||
import { WizardStepProps } from './types.js';
|
||||
import { WizardStepProps } from '../types.js';
|
||||
import { SubagentManager, SubagentConfig } from '@qwen-code/qwen-code-core';
|
||||
import { theme } from '../../semantic-colors.js';
|
||||
import { shouldShowColor, getColorForDisplay } from './utils.js';
|
||||
import { useLaunchEditor } from './useLaunchEditor.js';
|
||||
import { theme } from '../../../semantic-colors.js';
|
||||
import { shouldShowColor, getColorForDisplay } from '../utils.js';
|
||||
import { useLaunchEditor } from '../../../hooks/useLaunchEditor.js';
|
||||
|
||||
/**
|
||||
* Step 6: Final confirmation and actions.
|
||||
@@ -6,17 +6,17 @@
|
||||
|
||||
import { useState, useCallback, useRef } from 'react';
|
||||
import { Box, Text } from 'ink';
|
||||
import { WizardStepProps, WizardAction } from './types.js';
|
||||
import { sanitizeInput } from './utils.js';
|
||||
import { WizardStepProps, WizardAction } from '../types.js';
|
||||
import { sanitizeInput } from '../utils.js';
|
||||
import { Config, subagentGenerator } from '@qwen-code/qwen-code-core';
|
||||
import { useTextBuffer } from '../shared/text-buffer.js';
|
||||
import { useKeypress, Key } from '../../hooks/useKeypress.js';
|
||||
import { keyMatchers, Command } from '../../keyMatchers.js';
|
||||
import { theme } from '../../semantic-colors.js';
|
||||
import { cpSlice, cpLen } from '../../utils/textUtils.js';
|
||||
import { useTextBuffer } from '../../shared/text-buffer.js';
|
||||
import { useKeypress, Key } from '../../../hooks/useKeypress.js';
|
||||
import { keyMatchers, Command } from '../../../keyMatchers.js';
|
||||
import { theme } from '../../../semantic-colors.js';
|
||||
import { cpSlice, cpLen } from '../../../utils/textUtils.js';
|
||||
import chalk from 'chalk';
|
||||
import stringWidth from 'string-width';
|
||||
import { Colors } from '../../colors.js';
|
||||
import { Colors } from '../../../colors.js';
|
||||
|
||||
/**
|
||||
* Step 3: Description input with LLM generation.
|
||||
@@ -5,8 +5,8 @@
|
||||
*/
|
||||
|
||||
import { Box } from 'ink';
|
||||
import { RadioButtonSelect } from '../shared/RadioButtonSelect.js';
|
||||
import { WizardStepProps } from './types.js';
|
||||
import { RadioButtonSelect } from '../../shared/RadioButtonSelect.js';
|
||||
import { WizardStepProps } from '../types.js';
|
||||
|
||||
interface GenerationOption {
|
||||
label: string;
|
||||
@@ -5,8 +5,8 @@
|
||||
*/
|
||||
|
||||
import { Box } from 'ink';
|
||||
import { RadioButtonSelect } from '../shared/RadioButtonSelect.js';
|
||||
import { WizardStepProps } from './types.js';
|
||||
import { RadioButtonSelect } from '../../shared/RadioButtonSelect.js';
|
||||
import { WizardStepProps } from '../types.js';
|
||||
|
||||
interface LocationOption {
|
||||
label: string;
|
||||
@@ -6,10 +6,10 @@
|
||||
|
||||
import { useState, useMemo, useEffect } from 'react';
|
||||
import { Box, Text } from 'ink';
|
||||
import { RadioButtonSelect } from '../shared/RadioButtonSelect.js';
|
||||
import { ToolCategory } from './types.js';
|
||||
import { RadioButtonSelect } from '../../shared/RadioButtonSelect.js';
|
||||
import { ToolCategory } from '../types.js';
|
||||
import { Kind, Config } from '@qwen-code/qwen-code-core';
|
||||
import { Colors } from '../../colors.js';
|
||||
import { Colors } from '../../../colors.js';
|
||||
|
||||
interface ToolOption {
|
||||
label: string;
|
||||
@@ -4,33 +4,11 @@
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
// Creation Wizard Components
|
||||
export { SubagentCreationWizard } from './SubagentCreationWizard.js';
|
||||
export { LocationSelector } from './LocationSelector.js';
|
||||
export { GenerationMethodSelector } from './GenerationMethodSelector.js';
|
||||
export { DescriptionInput } from './DescriptionInput.js';
|
||||
export { ToolSelector } from './ToolSelector.js';
|
||||
export { ColorSelector } from './ColorSelector.js';
|
||||
export { CreationSummary } from './CreationSummary.js';
|
||||
// Creation Wizard
|
||||
export { AgentCreationWizard } from './create/AgentCreationWizard.js';
|
||||
|
||||
// Management Dialog Components
|
||||
export { AgentsManagerDialog } from './AgentsManagerDialog.js';
|
||||
export { AgentSelectionStep } from './AgentSelectionStep.js';
|
||||
export { ActionSelectionStep } from './ActionSelectionStep.js';
|
||||
export { AgentViewerStep } from './AgentViewerStep.js';
|
||||
export { AgentDeleteStep } from './AgentDeleteStep.js';
|
||||
// Management Dialog
|
||||
export { AgentsManagerDialog } from './view/AgentsManagerDialog.js';
|
||||
|
||||
// Execution Display Components
|
||||
export { SubagentExecutionDisplay } from './SubagentExecutionDisplay.js';
|
||||
|
||||
// Creation Wizard Types and State
|
||||
export type {
|
||||
CreationWizardState,
|
||||
WizardAction,
|
||||
WizardStepProps,
|
||||
WizardResult,
|
||||
ToolCategory,
|
||||
ColorOption,
|
||||
} from './types.js';
|
||||
|
||||
export { wizardReducer, initialWizardState } from './reducers.js';
|
||||
// Execution Display
|
||||
export { AgentExecutionDisplay } from './runtime/AgentExecutionDisplay.js';
|
||||
|
||||
@@ -6,19 +6,19 @@
|
||||
|
||||
import React, { useMemo } from 'react';
|
||||
import { Box, Text } from 'ink';
|
||||
import { Colors } from '../../colors.js';
|
||||
import { Colors } from '../../../colors.js';
|
||||
import {
|
||||
TaskResultDisplay,
|
||||
SubagentStatsSummary,
|
||||
} from '@qwen-code/qwen-code-core';
|
||||
import { theme } from '../../semantic-colors.js';
|
||||
import { useKeypress } from '../../hooks/useKeypress.js';
|
||||
import { COLOR_OPTIONS } from './constants.js';
|
||||
import { fmtDuration } from './utils.js';
|
||||
import { theme } from '../../../semantic-colors.js';
|
||||
import { useKeypress } from '../../../hooks/useKeypress.js';
|
||||
import { COLOR_OPTIONS } from '../constants.js';
|
||||
import { fmtDuration } from '../utils.js';
|
||||
|
||||
export type DisplayMode = 'compact' | 'default' | 'verbose';
|
||||
export type DisplayMode = 'default' | 'verbose';
|
||||
|
||||
export interface SubagentExecutionDisplayProps {
|
||||
export interface AgentExecutionDisplayProps {
|
||||
data: TaskResultDisplay;
|
||||
}
|
||||
|
||||
@@ -32,6 +32,8 @@ const getStatusColor = (
|
||||
case 'completed':
|
||||
case 'success':
|
||||
return theme.status.success;
|
||||
case 'cancelled':
|
||||
return theme.status.warning;
|
||||
case 'failed':
|
||||
return theme.status.error;
|
||||
default:
|
||||
@@ -45,6 +47,8 @@ const getStatusText = (status: TaskResultDisplay['status']) => {
|
||||
return 'Running';
|
||||
case 'completed':
|
||||
return 'Completed';
|
||||
case 'cancelled':
|
||||
return 'User Cancelled';
|
||||
case 'failed':
|
||||
return 'Failed';
|
||||
default:
|
||||
@@ -52,14 +56,17 @@ const getStatusText = (status: TaskResultDisplay['status']) => {
|
||||
}
|
||||
};
|
||||
|
||||
const MAX_TOOL_CALLS = 5;
|
||||
const MAX_TASK_PROMPT_LINES = 5;
|
||||
|
||||
/**
|
||||
* Component to display subagent execution progress and results.
|
||||
* This is now a pure component that renders the provided SubagentExecutionResultDisplay data.
|
||||
* Real-time updates are handled by the parent component updating the data prop.
|
||||
*/
|
||||
export const SubagentExecutionDisplay: React.FC<
|
||||
SubagentExecutionDisplayProps
|
||||
> = ({ data }) => {
|
||||
export const AgentExecutionDisplay: React.FC<AgentExecutionDisplayProps> = ({
|
||||
data,
|
||||
}) => {
|
||||
const [displayMode, setDisplayMode] = React.useState<DisplayMode>('default');
|
||||
|
||||
const agentColor = useMemo(() => {
|
||||
@@ -76,27 +83,25 @@ export const SubagentExecutionDisplay: React.FC<
|
||||
if (displayMode === 'verbose') return 'Press ctrl+r to show less.';
|
||||
|
||||
if (displayMode === 'default') {
|
||||
const hasMoreLines = data.taskPrompt.split('\n').length > 10;
|
||||
const hasMoreToolCalls = data.toolCalls && data.toolCalls.length > 5;
|
||||
const hasMoreLines =
|
||||
data.taskPrompt.split('\n').length > MAX_TASK_PROMPT_LINES;
|
||||
const hasMoreToolCalls =
|
||||
data.toolCalls && data.toolCalls.length > MAX_TOOL_CALLS;
|
||||
|
||||
if (hasMoreToolCalls || hasMoreLines) {
|
||||
return 'Press ctrl+s to show more.';
|
||||
return 'Press ctrl+r to show more.';
|
||||
}
|
||||
return '';
|
||||
}
|
||||
return '';
|
||||
}, [displayMode, data.toolCalls, data.taskPrompt, data.status]);
|
||||
|
||||
// Handle ctrl+s and ctrl+r keypresses to control display mode
|
||||
// Handle ctrl+r keypresses to control display mode
|
||||
useKeypress(
|
||||
(key) => {
|
||||
if (key.ctrl && key.name === 's') {
|
||||
if (key.ctrl && key.name === 'r') {
|
||||
setDisplayMode((current) =>
|
||||
current === 'default' ? 'verbose' : 'verbose',
|
||||
);
|
||||
} else if (key.ctrl && key.name === 'r') {
|
||||
setDisplayMode((current) =>
|
||||
current === 'verbose' ? 'default' : 'default',
|
||||
current === 'default' ? 'verbose' : 'default',
|
||||
);
|
||||
}
|
||||
},
|
||||
@@ -133,7 +138,9 @@ export const SubagentExecutionDisplay: React.FC<
|
||||
)}
|
||||
|
||||
{/* Results section for completed/failed tasks */}
|
||||
{(data.status === 'completed' || data.status === 'failed') && (
|
||||
{(data.status === 'completed' ||
|
||||
data.status === 'failed' ||
|
||||
data.status === 'cancelled') && (
|
||||
<ResultsSection data={data} displayMode={displayMode} />
|
||||
)}
|
||||
|
||||
@@ -157,7 +164,7 @@ const TaskPromptSection: React.FC<{
|
||||
const lines = taskPrompt.split('\n');
|
||||
const shouldTruncate = lines.length > 10;
|
||||
const showFull = displayMode === 'verbose';
|
||||
const displayLines = showFull ? lines : lines.slice(0, 10);
|
||||
const displayLines = showFull ? lines : lines.slice(0, MAX_TASK_PROMPT_LINES);
|
||||
|
||||
return (
|
||||
<Box flexDirection="column" gap={1}>
|
||||
@@ -206,9 +213,9 @@ const ToolCallsList: React.FC<{
|
||||
displayMode: DisplayMode;
|
||||
}> = ({ toolCalls, displayMode }) => {
|
||||
const calls = toolCalls || [];
|
||||
const shouldTruncate = calls.length > 5;
|
||||
const shouldTruncate = calls.length > MAX_TOOL_CALLS;
|
||||
const showAll = displayMode === 'verbose';
|
||||
const displayCalls = showAll ? calls : calls.slice(-5); // Show last 5
|
||||
const displayCalls = showAll ? calls : calls.slice(-MAX_TOOL_CALLS); // Show last 5
|
||||
|
||||
// Reverse the order to show most recent first
|
||||
const reversedDisplayCalls = [...displayCalls].reverse();
|
||||
@@ -220,7 +227,7 @@ const ToolCallsList: React.FC<{
|
||||
{shouldTruncate && displayMode === 'default' && (
|
||||
<Text color={Colors.Gray}>
|
||||
{' '}
|
||||
Showing the last 5 of {calls.length} tools.
|
||||
Showing the last {MAX_TOOL_CALLS} of {calls.length} tools.
|
||||
</Text>
|
||||
)}
|
||||
</Box>
|
||||
@@ -390,16 +397,18 @@ const ResultsSection: React.FC<{
|
||||
<ToolCallsList toolCalls={data.toolCalls} displayMode={displayMode} />
|
||||
)}
|
||||
|
||||
{/* Execution Summary section */}
|
||||
<Box flexDirection="column">
|
||||
<Box flexDirection="row" marginBottom={1}>
|
||||
<Text color={theme.text.primary}>Execution Summary:</Text>
|
||||
{/* Execution Summary section - hide when cancelled */}
|
||||
{data.status !== 'cancelled' && (
|
||||
<Box flexDirection="column">
|
||||
<Box flexDirection="row" marginBottom={1}>
|
||||
<Text color={theme.text.primary}>Execution Summary:</Text>
|
||||
</Box>
|
||||
<ExecutionSummaryDetails data={data} displayMode={displayMode} />
|
||||
</Box>
|
||||
<ExecutionSummaryDetails data={data} displayMode={displayMode} />
|
||||
</Box>
|
||||
)}
|
||||
|
||||
{/* Tool Usage section */}
|
||||
{data.executionSummary && (
|
||||
{/* Tool Usage section - hide when cancelled */}
|
||||
{data.status !== 'cancelled' && data.executionSummary && (
|
||||
<Box flexDirection="column">
|
||||
<Box flexDirection="row" marginBottom={1}>
|
||||
<Text color={theme.text.primary}>Tool Usage:</Text>
|
||||
@@ -409,11 +418,18 @@ const ResultsSection: React.FC<{
|
||||
)}
|
||||
|
||||
{/* Error reason for failed tasks */}
|
||||
{data.status === 'failed' && data.terminateReason && (
|
||||
{data.status === 'cancelled' && (
|
||||
<Box flexDirection="row">
|
||||
<Text color={Colors.AccentRed}>❌ Failed: </Text>
|
||||
<Text color={Colors.Gray}>{data.terminateReason}</Text>
|
||||
<Text color={theme.status.warning}>⏹ User Cancelled</Text>
|
||||
</Box>
|
||||
)}
|
||||
{data.status === 'failed' &&
|
||||
data.terminateReason &&
|
||||
data.terminateReason !== 'CANCELLED' && (
|
||||
<Box flexDirection="row">
|
||||
<Text color={Colors.AccentRed}>❌ Failed: </Text>
|
||||
<Text color={Colors.Gray}>{data.terminateReason}</Text>
|
||||
</Box>
|
||||
)}
|
||||
</Box>
|
||||
);
|
||||
@@ -6,8 +6,8 @@
|
||||
|
||||
import { useState } from 'react';
|
||||
import { Box } from 'ink';
|
||||
import { RadioButtonSelect } from '../shared/RadioButtonSelect.js';
|
||||
import { MANAGEMENT_STEPS } from './types.js';
|
||||
import { RadioButtonSelect } from '../../shared/RadioButtonSelect.js';
|
||||
import { MANAGEMENT_STEPS } from '../types.js';
|
||||
import { SubagentConfig } from '@qwen-code/qwen-code-core';
|
||||
|
||||
interface ActionSelectionStepProps {
|
||||
@@ -6,9 +6,9 @@
|
||||
|
||||
import { Box, Text } from 'ink';
|
||||
import { SubagentConfig } from '@qwen-code/qwen-code-core';
|
||||
import { StepNavigationProps } from './types.js';
|
||||
import { theme } from '../../semantic-colors.js';
|
||||
import { useKeypress } from '../../hooks/useKeypress.js';
|
||||
import { StepNavigationProps } from '../types.js';
|
||||
import { theme } from '../../../semantic-colors.js';
|
||||
import { useKeypress } from '../../../hooks/useKeypress.js';
|
||||
|
||||
interface AgentDeleteStepProps extends StepNavigationProps {
|
||||
selectedAgent: SubagentConfig | null;
|
||||
@@ -6,10 +6,10 @@
|
||||
|
||||
import { useState, useCallback } from 'react';
|
||||
import { Box, Text } from 'ink';
|
||||
import { RadioButtonSelect } from '../shared/RadioButtonSelect.js';
|
||||
import { MANAGEMENT_STEPS } from './types.js';
|
||||
import { theme } from '../../semantic-colors.js';
|
||||
import { useLaunchEditor } from './useLaunchEditor.js';
|
||||
import { RadioButtonSelect } from '../../shared/RadioButtonSelect.js';
|
||||
import { MANAGEMENT_STEPS } from '../types.js';
|
||||
import { theme } from '../../../semantic-colors.js';
|
||||
import { useLaunchEditor } from '../../../hooks/useLaunchEditor.js';
|
||||
import { SubagentConfig } from '@qwen-code/qwen-code-core';
|
||||
|
||||
interface EditOption {
|
||||
@@ -6,9 +6,9 @@
|
||||
|
||||
import { useState, useEffect, useMemo } from 'react';
|
||||
import { Box, Text } from 'ink';
|
||||
import { theme } from '../../semantic-colors.js';
|
||||
import { Colors } from '../../colors.js';
|
||||
import { useKeypress } from '../../hooks/useKeypress.js';
|
||||
import { theme } from '../../../semantic-colors.js';
|
||||
import { Colors } from '../../../colors.js';
|
||||
import { useKeypress } from '../../../hooks/useKeypress.js';
|
||||
import { SubagentConfig } from '@qwen-code/qwen-code-core';
|
||||
|
||||
interface NavigationState {
|
||||
@@ -5,8 +5,8 @@
|
||||
*/
|
||||
|
||||
import { Box, Text } from 'ink';
|
||||
import { theme } from '../../semantic-colors.js';
|
||||
import { shouldShowColor, getColorForDisplay } from './utils.js';
|
||||
import { theme } from '../../../semantic-colors.js';
|
||||
import { shouldShowColor, getColorForDisplay } from '../utils.js';
|
||||
import { SubagentConfig } from '@qwen-code/qwen-code-core';
|
||||
|
||||
interface AgentViewerStepProps {
|
||||
@@ -11,11 +11,11 @@ import { ActionSelectionStep } from './ActionSelectionStep.js';
|
||||
import { AgentViewerStep } from './AgentViewerStep.js';
|
||||
import { EditOptionsStep } from './AgentEditStep.js';
|
||||
import { AgentDeleteStep } from './AgentDeleteStep.js';
|
||||
import { ToolSelector } from './ToolSelector.js';
|
||||
import { ColorSelector } from './ColorSelector.js';
|
||||
import { MANAGEMENT_STEPS } from './types.js';
|
||||
import { Colors } from '../../colors.js';
|
||||
import { theme } from '../../semantic-colors.js';
|
||||
import { ToolSelector } from '../create/ToolSelector.js';
|
||||
import { ColorSelector } from '../create/ColorSelector.js';
|
||||
import { MANAGEMENT_STEPS } from '../types.js';
|
||||
import { Colors } from '../../../colors.js';
|
||||
import { theme } from '../../../semantic-colors.js';
|
||||
import { Config, SubagentConfig } from '@qwen-code/qwen-code-core';
|
||||
|
||||
interface AgentsManagerDialogProps {
|
||||
@@ -8,7 +8,7 @@ import { useCallback } from 'react';
|
||||
import { useStdin } from 'ink';
|
||||
import { EditorType } from '@qwen-code/qwen-code-core';
|
||||
import { spawnSync } from 'child_process';
|
||||
import { useSettings } from '../../contexts/SettingsContext.js';
|
||||
import { useSettings } from '../contexts/SettingsContext.js';
|
||||
|
||||
/**
|
||||
* Determines the editor command to use based on user preferences and platform.
|
||||
Reference in New Issue
Block a user