praxis-agent 0.6.0 → 0.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +10 -1
- package/dist/application/background-agent-manager.d.ts +5 -0
- package/dist/application/background-agent-manager.js +21 -0
- package/dist/application/background-bash-manager.d.ts +14 -0
- package/dist/application/background-bash-manager.js +42 -4
- package/dist/application/background-task-runtime.d.ts +34 -0
- package/dist/application/background-task-runtime.js +59 -0
- package/dist/application/session-service.d.ts +21 -1
- package/dist/application/session-service.js +188 -17
- package/dist/application/session-worktree.d.ts +1 -0
- package/dist/application/session-worktree.js +13 -2
- package/dist/application/subagent-service.d.ts +3 -0
- package/dist/application/subagent-service.js +6 -0
- package/dist/application/workflow-manager.d.ts +70 -2
- package/dist/application/workflow-manager.js +21 -4
- package/dist/cli/agents-dashboard.d.ts +9 -0
- package/dist/cli/agents-dashboard.js +16 -5
- package/dist/cli/interactive.d.ts +44 -3
- package/dist/cli/interactive.js +1431 -189
- package/dist/cli/tui/claude-style.d.ts +41 -3
- package/dist/cli/tui/claude-style.js +227 -54
- package/dist/cli/tui/config-dashboard.d.ts +63 -0
- package/dist/cli/tui/config-dashboard.js +150 -0
- package/dist/cli/tui/config-settings.d.ts +32 -0
- package/dist/cli/tui/config-settings.js +276 -0
- package/dist/cli/tui/custom-themes.d.ts +21 -0
- package/dist/cli/tui/custom-themes.js +284 -0
- package/dist/cli/tui/file-picker.d.ts +3 -1
- package/dist/cli/tui/file-picker.js +8 -2
- package/dist/cli/tui/hook-settings.d.ts +33 -0
- package/dist/cli/tui/hook-settings.js +200 -0
- package/dist/cli/tui/keybindings.js +0 -1
- package/dist/cli/tui/mcp-panel-controller.d.ts +32 -0
- package/dist/cli/tui/mcp-panel-controller.js +80 -0
- package/dist/cli/tui/mcp-panel-projector.d.ts +79 -0
- package/dist/cli/tui/mcp-panel-projector.js +181 -0
- package/dist/cli/tui/mcp-panel.d.ts +8 -0
- package/dist/cli/tui/mcp-panel.js +99 -0
- package/dist/cli/tui/recently-denied.d.ts +15 -0
- package/dist/cli/tui/recently-denied.js +19 -0
- package/dist/cli/tui/runtime-interactions.d.ts +17 -0
- package/dist/cli/tui/runtime-interactions.js +100 -0
- package/dist/cli/tui/runtime-settings.d.ts +40 -0
- package/dist/cli/tui/runtime-settings.js +84 -0
- package/dist/cli/tui/slash-commands.js +15 -0
- package/dist/cli/tui/task-panel.d.ts +53 -0
- package/dist/cli/tui/task-panel.js +204 -0
- package/dist/cli/tui/terminal-notifications.d.ts +10 -0
- package/dist/cli/tui/terminal-notifications.js +48 -0
- package/dist/cli/tui/terminal-setup.d.ts +24 -0
- package/dist/cli/tui/terminal-setup.js +618 -0
- package/dist/cli/tui/theme-settings.d.ts +8 -0
- package/dist/cli/tui/theme-settings.js +132 -0
- package/dist/cli/tui/theme.d.ts +53 -0
- package/dist/cli/tui/theme.js +265 -0
- package/dist/cli.d.ts +12 -0
- package/dist/cli.js +140 -21
- package/dist/compatibility/claude/schema.js +2 -0
- package/dist/compatibility/claude/shared-resources.d.ts +2 -0
- package/dist/core/runtime.d.ts +12 -0
- package/dist/core/runtime.js +24 -0
- package/dist/maintenance/self-update.js +1 -1
- package/dist/mcp/claude-mcp-management.d.ts +6 -1
- package/dist/mcp/claude-mcp-management.js +191 -44
- package/dist/mcp/claude-mcp-oauth.js +2 -0
- package/dist/mcp/claude-mcp-tools.d.ts +31 -3
- package/dist/mcp/claude-mcp-tools.js +116 -34
- package/dist/permissions/claude-permission-resolver.d.ts +3 -0
- package/dist/permissions/claude-permission-resolver.js +42 -20
- package/dist/platform/claude-version.js +2 -1
- package/dist/plugins/claude-plugin-runtime.d.ts +1 -0
- package/dist/plugins/claude-plugin-runtime.js +60 -24
- package/dist/tools/claude-interactive-tools.d.ts +7 -0
- package/dist/tools/claude-interactive-tools.js +21 -8
- package/dist/tools/claude-task-tools.d.ts +4 -0
- package/dist/tools/claude-task-tools.js +7 -0
- package/package.json +2 -1
- package/dist/application/background-agent-manager.d.ts.map +0 -1
- package/dist/application/background-agent-manager.js.map +0 -1
- package/dist/application/background-bash-manager.d.ts.map +0 -1
- package/dist/application/background-bash-manager.js.map +0 -1
- package/dist/application/background-task-id.d.ts.map +0 -1
- package/dist/application/background-task-id.js.map +0 -1
- package/dist/application/claude-project-purge.d.ts.map +0 -1
- package/dist/application/claude-project-purge.js.map +0 -1
- package/dist/application/managed-worktree.d.ts.map +0 -1
- package/dist/application/managed-worktree.js.map +0 -1
- package/dist/application/model-compactor.d.ts.map +0 -1
- package/dist/application/model-compactor.js.map +0 -1
- package/dist/application/scheduled-prompt-manager.d.ts.map +0 -1
- package/dist/application/scheduled-prompt-manager.js.map +0 -1
- package/dist/application/session-service.d.ts.map +0 -1
- package/dist/application/session-service.js.map +0 -1
- package/dist/application/session-worktree.d.ts.map +0 -1
- package/dist/application/session-worktree.js.map +0 -1
- package/dist/application/subagent-service.d.ts.map +0 -1
- package/dist/application/subagent-service.js.map +0 -1
- package/dist/application/tool-use-summary.d.ts.map +0 -1
- package/dist/application/tool-use-summary.js.map +0 -1
- package/dist/application/top-level-agent-manager.d.ts.map +0 -1
- package/dist/application/top-level-agent-manager.js.map +0 -1
- package/dist/application/workflow-manager.d.ts.map +0 -1
- package/dist/application/workflow-manager.js.map +0 -1
- package/dist/application/workflow-meta.d.ts.map +0 -1
- package/dist/application/workflow-meta.js.map +0 -1
- package/dist/application/workflow-runtime.d.ts.map +0 -1
- package/dist/application/workflow-runtime.js.map +0 -1
- package/dist/application/workflow-worktree.d.ts.map +0 -1
- package/dist/application/workflow-worktree.js.map +0 -1
- package/dist/cli/agents-dashboard.d.ts.map +0 -1
- package/dist/cli/agents-dashboard.js.map +0 -1
- package/dist/cli/controls.d.ts.map +0 -1
- package/dist/cli/controls.js.map +0 -1
- package/dist/cli/debug.d.ts.map +0 -1
- package/dist/cli/debug.js.map +0 -1
- package/dist/cli/interactive.d.ts.map +0 -1
- package/dist/cli/interactive.js.map +0 -1
- package/dist/cli/protocol.d.ts.map +0 -1
- package/dist/cli/protocol.js.map +0 -1
- package/dist/cli/tui/claude-style.d.ts.map +0 -1
- package/dist/cli/tui/claude-style.js.map +0 -1
- package/dist/cli/tui/clipboard.d.ts.map +0 -1
- package/dist/cli/tui/clipboard.js.map +0 -1
- package/dist/cli/tui/composer-editor.d.ts.map +0 -1
- package/dist/cli/tui/composer-editor.js.map +0 -1
- package/dist/cli/tui/composer-images.d.ts.map +0 -1
- package/dist/cli/tui/composer-images.js.map +0 -1
- package/dist/cli/tui/conversation-export.d.ts.map +0 -1
- package/dist/cli/tui/conversation-export.js.map +0 -1
- package/dist/cli/tui/external-editor.d.ts.map +0 -1
- package/dist/cli/tui/external-editor.js.map +0 -1
- package/dist/cli/tui/file-picker.d.ts.map +0 -1
- package/dist/cli/tui/file-picker.js.map +0 -1
- package/dist/cli/tui/git-diff.d.ts.map +0 -1
- package/dist/cli/tui/git-diff.js.map +0 -1
- package/dist/cli/tui/keybindings.d.ts.map +0 -1
- package/dist/cli/tui/keybindings.js.map +0 -1
- package/dist/cli/tui/memory-files.d.ts.map +0 -1
- package/dist/cli/tui/memory-files.js.map +0 -1
- package/dist/cli/tui/permission-settings.d.ts.map +0 -1
- package/dist/cli/tui/permission-settings.js.map +0 -1
- package/dist/cli/tui/slash-commands.d.ts.map +0 -1
- package/dist/cli/tui/slash-commands.js.map +0 -1
- package/dist/cli/tui/terminal-suspend.d.ts.map +0 -1
- package/dist/cli/tui/terminal-suspend.js.map +0 -1
- package/dist/cli/tui/workspace-directories.d.ts.map +0 -1
- package/dist/cli/tui/workspace-directories.js.map +0 -1
- package/dist/cli.d.ts.map +0 -1
- package/dist/cli.js.map +0 -1
- package/dist/compatibility/claude/compaction.d.ts.map +0 -1
- package/dist/compatibility/claude/compaction.js.map +0 -1
- package/dist/compatibility/claude/context.d.ts.map +0 -1
- package/dist/compatibility/claude/context.js.map +0 -1
- package/dist/compatibility/claude/dynamic-context.d.ts.map +0 -1
- package/dist/compatibility/claude/dynamic-context.js.map +0 -1
- package/dist/compatibility/claude/file-history.d.ts.map +0 -1
- package/dist/compatibility/claude/file-history.js.map +0 -1
- package/dist/compatibility/claude/file-resources.d.ts.map +0 -1
- package/dist/compatibility/claude/file-resources.js.map +0 -1
- package/dist/compatibility/claude/fork.d.ts.map +0 -1
- package/dist/compatibility/claude/fork.js.map +0 -1
- package/dist/compatibility/claude/history.d.ts.map +0 -1
- package/dist/compatibility/claude/history.js.map +0 -1
- package/dist/compatibility/claude/ownership.d.ts.map +0 -1
- package/dist/compatibility/claude/ownership.js.map +0 -1
- package/dist/compatibility/claude/paths.d.ts.map +0 -1
- package/dist/compatibility/claude/paths.js.map +0 -1
- package/dist/compatibility/claude/pr-links.d.ts.map +0 -1
- package/dist/compatibility/claude/pr-links.js.map +0 -1
- package/dist/compatibility/claude/projection.d.ts.map +0 -1
- package/dist/compatibility/claude/projection.js.map +0 -1
- package/dist/compatibility/claude/schema.d.ts.map +0 -1
- package/dist/compatibility/claude/schema.js.map +0 -1
- package/dist/compatibility/claude/shared-resources.d.ts.map +0 -1
- package/dist/compatibility/claude/shared-resources.js.map +0 -1
- package/dist/compatibility/claude/sidechain.d.ts.map +0 -1
- package/dist/compatibility/claude/sidechain.js.map +0 -1
- package/dist/compatibility/claude/tool-links.d.ts.map +0 -1
- package/dist/compatibility/claude/tool-links.js.map +0 -1
- package/dist/compatibility/claude/translation.d.ts.map +0 -1
- package/dist/compatibility/claude/translation.js.map +0 -1
- package/dist/compatibility/claude/workflow-replay.d.ts.map +0 -1
- package/dist/compatibility/claude/workflow-replay.js.map +0 -1
- package/dist/compatibility/claude/workflow.d.ts.map +0 -1
- package/dist/compatibility/claude/workflow.js.map +0 -1
- package/dist/core/compaction.d.ts.map +0 -1
- package/dist/core/compaction.js.map +0 -1
- package/dist/core/context-budget.d.ts.map +0 -1
- package/dist/core/context-budget.js.map +0 -1
- package/dist/core/context.d.ts.map +0 -1
- package/dist/core/context.js.map +0 -1
- package/dist/core/runtime.d.ts.map +0 -1
- package/dist/core/runtime.js.map +0 -1
- package/dist/core/usage.d.ts.map +0 -1
- package/dist/core/usage.js.map +0 -1
- package/dist/extensions/claude-extension-tools.d.ts.map +0 -1
- package/dist/extensions/claude-extension-tools.js.map +0 -1
- package/dist/extensions/claude-extensions.d.ts.map +0 -1
- package/dist/extensions/claude-extensions.js.map +0 -1
- package/dist/hooks/claude-hook-tools.d.ts.map +0 -1
- package/dist/hooks/claude-hook-tools.js.map +0 -1
- package/dist/hooks/claude-hooks.d.ts.map +0 -1
- package/dist/hooks/claude-hooks.js.map +0 -1
- package/dist/maintenance/doctor.d.ts.map +0 -1
- package/dist/maintenance/doctor.js.map +0 -1
- package/dist/maintenance/self-update.d.ts.map +0 -1
- package/dist/maintenance/self-update.js.map +0 -1
- package/dist/mcp/claude-mcp-management.d.ts.map +0 -1
- package/dist/mcp/claude-mcp-management.js.map +0 -1
- package/dist/mcp/claude-mcp-oauth.d.ts.map +0 -1
- package/dist/mcp/claude-mcp-oauth.js.map +0 -1
- package/dist/mcp/claude-mcp-tools.d.ts.map +0 -1
- package/dist/mcp/claude-mcp-tools.js.map +0 -1
- package/dist/mcp/praxis-mcp-server.d.ts.map +0 -1
- package/dist/mcp/praxis-mcp-server.js.map +0 -1
- package/dist/permissions/claude-auto-classifier.d.ts.map +0 -1
- package/dist/permissions/claude-auto-classifier.js.map +0 -1
- package/dist/permissions/claude-permission-resolver.d.ts.map +0 -1
- package/dist/permissions/claude-permission-resolver.js.map +0 -1
- package/dist/persistence/claude-job-store.d.ts.map +0 -1
- package/dist/persistence/claude-job-store.js.map +0 -1
- package/dist/persistence/claude-scheduled-task-store.d.ts.map +0 -1
- package/dist/persistence/claude-scheduled-task-store.js.map +0 -1
- package/dist/persistence/claude-sidechain-store.d.ts.map +0 -1
- package/dist/persistence/claude-sidechain-store.js.map +0 -1
- package/dist/persistence/claude-task-store.d.ts.map +0 -1
- package/dist/persistence/claude-task-store.js.map +0 -1
- package/dist/persistence/claude-transcript-store.d.ts.map +0 -1
- package/dist/persistence/claude-transcript-store.js.map +0 -1
- package/dist/persistence/claude-workflow-store.d.ts.map +0 -1
- package/dist/persistence/claude-workflow-store.js.map +0 -1
- package/dist/persistence/in-memory-sidechain-store.d.ts.map +0 -1
- package/dist/persistence/in-memory-sidechain-store.js.map +0 -1
- package/dist/persistence/in-memory-transcript-store.d.ts.map +0 -1
- package/dist/persistence/in-memory-transcript-store.js.map +0 -1
- package/dist/platform/atomic-write.d.ts.map +0 -1
- package/dist/platform/atomic-write.js.map +0 -1
- package/dist/platform/bounded-process-runner.d.ts.map +0 -1
- package/dist/platform/bounded-process-runner.js.map +0 -1
- package/dist/platform/claude-version.d.ts.map +0 -1
- package/dist/platform/claude-version.js.map +0 -1
- package/dist/platform/command-shell.d.ts.map +0 -1
- package/dist/platform/command-shell.js.map +0 -1
- package/dist/platform/exclusive-file-lease.d.ts.map +0 -1
- package/dist/platform/exclusive-file-lease.js.map +0 -1
- package/dist/platform/sensitive-data.d.ts.map +0 -1
- package/dist/platform/sensitive-data.js.map +0 -1
- package/dist/platform/tmux-worktree.d.ts.map +0 -1
- package/dist/platform/tmux-worktree.js.map +0 -1
- package/dist/plugins/claude-plugin-eval-discovery.d.ts.map +0 -1
- package/dist/plugins/claude-plugin-eval-discovery.js.map +0 -1
- package/dist/plugins/claude-plugin-eval-graders.d.ts.map +0 -1
- package/dist/plugins/claude-plugin-eval-graders.js.map +0 -1
- package/dist/plugins/claude-plugin-eval-runner.d.ts.map +0 -1
- package/dist/plugins/claude-plugin-eval-runner.js.map +0 -1
- package/dist/plugins/claude-plugin-eval-schema.d.ts.map +0 -1
- package/dist/plugins/claude-plugin-eval-schema.js.map +0 -1
- package/dist/plugins/claude-plugin-eval.d.ts.map +0 -1
- package/dist/plugins/claude-plugin-eval.js.map +0 -1
- package/dist/plugins/claude-plugin-maintenance.d.ts.map +0 -1
- package/dist/plugins/claude-plugin-maintenance.js.map +0 -1
- package/dist/plugins/claude-plugin-marketplace.d.ts.map +0 -1
- package/dist/plugins/claude-plugin-marketplace.js.map +0 -1
- package/dist/plugins/claude-plugin-mcpb.d.ts.map +0 -1
- package/dist/plugins/claude-plugin-mcpb.js.map +0 -1
- package/dist/plugins/claude-plugin-runtime.d.ts.map +0 -1
- package/dist/plugins/claude-plugin-runtime.js.map +0 -1
- package/dist/providers/anthropic-compatible.d.ts.map +0 -1
- package/dist/providers/anthropic-compatible.js.map +0 -1
- package/dist/providers/environment.d.ts.map +0 -1
- package/dist/providers/environment.js.map +0 -1
- package/dist/providers/fallback-provider.d.ts.map +0 -1
- package/dist/providers/fallback-provider.js.map +0 -1
- package/dist/providers/openai-compatible.d.ts.map +0 -1
- package/dist/providers/openai-compatible.js.map +0 -1
- package/dist/tools/claude-interactive-tools.d.ts.map +0 -1
- package/dist/tools/claude-interactive-tools.js.map +0 -1
- package/dist/tools/claude-lsp-formatters.d.ts.map +0 -1
- package/dist/tools/claude-lsp-formatters.js.map +0 -1
- package/dist/tools/claude-lsp-tool.d.ts.map +0 -1
- package/dist/tools/claude-lsp-tool.js.map +0 -1
- package/dist/tools/claude-scheduled-tools.d.ts.map +0 -1
- package/dist/tools/claude-scheduled-tools.js.map +0 -1
- package/dist/tools/claude-task-tools.d.ts.map +0 -1
- package/dist/tools/claude-task-tools.js.map +0 -1
- package/dist/tools/claude-user-message.d.ts.map +0 -1
- package/dist/tools/claude-user-message.js.map +0 -1
- package/dist/tools/claude-workflow-tools.d.ts.map +0 -1
- package/dist/tools/claude-workflow-tools.js.map +0 -1
- package/dist/tools/claude-worktree-tools.d.ts.map +0 -1
- package/dist/tools/claude-worktree-tools.js.map +0 -1
- package/dist/tools/filtered-tool-registry.d.ts.map +0 -1
- package/dist/tools/filtered-tool-registry.js.map +0 -1
- package/dist/tools/glob.d.ts.map +0 -1
- package/dist/tools/glob.js.map +0 -1
- package/dist/tools/local-tools.d.ts.map +0 -1
- package/dist/tools/local-tools.js.map +0 -1
- package/dist/tools/notebook.d.ts.map +0 -1
- package/dist/tools/notebook.js.map +0 -1
- package/dist/tools/pdf.d.ts.map +0 -1
- package/dist/tools/pdf.js.map +0 -1
- package/dist/tools/web.d.ts.map +0 -1
- package/dist/tools/web.js.map +0 -1
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
import type { McpScope, McpServerRecord } from '../../mcp/claude-mcp-management.js';
|
|
2
|
+
export type TuiMcpCapability = 'tools' | 'resources' | 'prompts';
|
|
3
|
+
export type TuiMcpServerStatus = 'connected' | 'failed' | 'disabled' | 'needs-authentication';
|
|
4
|
+
export interface TuiMcpTool {
|
|
5
|
+
name: string;
|
|
6
|
+
fullName: string;
|
|
7
|
+
description?: string;
|
|
8
|
+
}
|
|
9
|
+
export interface TuiMcpRuntimeServer {
|
|
10
|
+
name: string;
|
|
11
|
+
status: Exclude<TuiMcpServerStatus, 'disabled'>;
|
|
12
|
+
statusDetail?: string;
|
|
13
|
+
authDetail?: string;
|
|
14
|
+
capabilities?: readonly TuiMcpCapability[];
|
|
15
|
+
toolCount?: number;
|
|
16
|
+
}
|
|
17
|
+
export interface TuiMcpServer {
|
|
18
|
+
name: string;
|
|
19
|
+
scope: McpScope;
|
|
20
|
+
path: string;
|
|
21
|
+
location: string;
|
|
22
|
+
status: TuiMcpServerStatus;
|
|
23
|
+
statusDetail: string;
|
|
24
|
+
authDetail?: string;
|
|
25
|
+
transport: 'stdio' | 'http' | 'sse';
|
|
26
|
+
command?: string;
|
|
27
|
+
args: readonly string[];
|
|
28
|
+
url?: string;
|
|
29
|
+
capabilities: readonly TuiMcpCapability[];
|
|
30
|
+
toolCount: number;
|
|
31
|
+
tools?: readonly TuiMcpTool[];
|
|
32
|
+
}
|
|
33
|
+
export interface TuiMcpPanelModel {
|
|
34
|
+
cwd: string;
|
|
35
|
+
servers: readonly TuiMcpServer[];
|
|
36
|
+
}
|
|
37
|
+
export type TuiMcpPanelDepth = 'list' | 'detail' | 'tools' | 'tool';
|
|
38
|
+
export interface TuiMcpPanelState {
|
|
39
|
+
depth: TuiMcpPanelDepth;
|
|
40
|
+
serverIndex: number;
|
|
41
|
+
selectedIndex: number;
|
|
42
|
+
}
|
|
43
|
+
export type TuiMcpPanelInput = {
|
|
44
|
+
type: 'up' | 'down' | 'confirm' | 'back';
|
|
45
|
+
} | {
|
|
46
|
+
type: 'select';
|
|
47
|
+
index: number;
|
|
48
|
+
};
|
|
49
|
+
export type TuiMcpPanelCommand = {
|
|
50
|
+
type: 'close';
|
|
51
|
+
} | {
|
|
52
|
+
type: 'view-tools';
|
|
53
|
+
name: string;
|
|
54
|
+
} | {
|
|
55
|
+
type: 'reconnect';
|
|
56
|
+
name: string;
|
|
57
|
+
} | {
|
|
58
|
+
type: 'authenticate';
|
|
59
|
+
name: string;
|
|
60
|
+
} | {
|
|
61
|
+
type: 'set-enabled';
|
|
62
|
+
name: string;
|
|
63
|
+
scope: McpScope;
|
|
64
|
+
enabled: boolean;
|
|
65
|
+
};
|
|
66
|
+
export interface TuiMcpPanelTransition {
|
|
67
|
+
state: TuiMcpPanelState;
|
|
68
|
+
command?: TuiMcpPanelCommand;
|
|
69
|
+
}
|
|
70
|
+
export declare function projectTuiMcpPanel({ cwd, records, disabledNames, runtime, }: {
|
|
71
|
+
cwd: string;
|
|
72
|
+
records: readonly McpServerRecord[];
|
|
73
|
+
disabledNames: readonly string[];
|
|
74
|
+
runtime: readonly TuiMcpRuntimeServer[];
|
|
75
|
+
}): TuiMcpPanelModel;
|
|
76
|
+
export declare function initialTuiMcpPanelState(model: TuiMcpPanelModel): TuiMcpPanelState;
|
|
77
|
+
export declare function tuiMcpServerActions(server: TuiMcpServer): readonly TuiMcpPanelCommand[];
|
|
78
|
+
export declare function reduceTuiMcpPanelState(model: TuiMcpPanelModel, state: TuiMcpPanelState, input: TuiMcpPanelInput): TuiMcpPanelTransition;
|
|
79
|
+
//# sourceMappingURL=mcp-panel-projector.d.ts.map
|
|
@@ -0,0 +1,181 @@
|
|
|
1
|
+
const SCOPE_ORDER = {
|
|
2
|
+
project: 0,
|
|
3
|
+
local: 1,
|
|
4
|
+
user: 2,
|
|
5
|
+
};
|
|
6
|
+
function stringValue(value) {
|
|
7
|
+
return typeof value === 'string' && value.length > 0 ? value : undefined;
|
|
8
|
+
}
|
|
9
|
+
function stringArray(value) {
|
|
10
|
+
return Array.isArray(value)
|
|
11
|
+
? value.filter((item) => typeof item === 'string')
|
|
12
|
+
: [];
|
|
13
|
+
}
|
|
14
|
+
function transport(config) {
|
|
15
|
+
if (config.type === 'sse')
|
|
16
|
+
return 'sse';
|
|
17
|
+
return config.type === 'http' || typeof config.url === 'string'
|
|
18
|
+
? 'http'
|
|
19
|
+
: 'stdio';
|
|
20
|
+
}
|
|
21
|
+
export function projectTuiMcpPanel({ cwd, records, disabledNames, runtime, }) {
|
|
22
|
+
const disabled = new Set(disabledNames);
|
|
23
|
+
const runtimeByName = new Map(runtime.map((server) => [server.name, server]));
|
|
24
|
+
const servers = records
|
|
25
|
+
.map((record) => {
|
|
26
|
+
const active = runtimeByName.get(record.name);
|
|
27
|
+
const status = disabled.has(record.name)
|
|
28
|
+
? 'disabled'
|
|
29
|
+
: (active?.status ?? 'failed');
|
|
30
|
+
const selectedTransport = transport(record.config);
|
|
31
|
+
const command = stringValue(record.config.command);
|
|
32
|
+
const url = stringValue(record.config.url);
|
|
33
|
+
return {
|
|
34
|
+
name: record.name,
|
|
35
|
+
scope: record.scope,
|
|
36
|
+
path: record.path,
|
|
37
|
+
location: record.scope === 'local'
|
|
38
|
+
? `${record.path} [project: ${cwd}]`
|
|
39
|
+
: record.path,
|
|
40
|
+
status,
|
|
41
|
+
statusDetail: status === 'disabled'
|
|
42
|
+
? '◯ disabled'
|
|
43
|
+
: status === 'needs-authentication'
|
|
44
|
+
? '△ needs authentication'
|
|
45
|
+
: status === 'connected'
|
|
46
|
+
? `done: ${active?.statusDetail ?? 'connected'}`
|
|
47
|
+
: `failed: ${active?.statusDetail ?? 'failed'}`,
|
|
48
|
+
...(active?.authDetail ? { authDetail: active.authDetail } : {}),
|
|
49
|
+
transport: selectedTransport,
|
|
50
|
+
...(selectedTransport === 'stdio' && command ? { command } : {}),
|
|
51
|
+
...(selectedTransport !== 'stdio' && url ? { url } : {}),
|
|
52
|
+
args: stringArray(record.config.args),
|
|
53
|
+
capabilities: active?.capabilities ?? [],
|
|
54
|
+
toolCount: active?.toolCount ?? 0,
|
|
55
|
+
};
|
|
56
|
+
})
|
|
57
|
+
.sort((left, right) => SCOPE_ORDER[left.scope] - SCOPE_ORDER[right.scope] ||
|
|
58
|
+
left.location.localeCompare(right.location) ||
|
|
59
|
+
left.name.localeCompare(right.name));
|
|
60
|
+
return { cwd, servers };
|
|
61
|
+
}
|
|
62
|
+
export function initialTuiMcpPanelState(model) {
|
|
63
|
+
return {
|
|
64
|
+
depth: 'list',
|
|
65
|
+
serverIndex: bounded(0, model.servers.length),
|
|
66
|
+
selectedIndex: 0,
|
|
67
|
+
};
|
|
68
|
+
}
|
|
69
|
+
export function tuiMcpServerActions(server) {
|
|
70
|
+
if (server.status === 'disabled') {
|
|
71
|
+
return [
|
|
72
|
+
{
|
|
73
|
+
type: 'set-enabled',
|
|
74
|
+
name: server.name,
|
|
75
|
+
scope: server.scope,
|
|
76
|
+
enabled: true,
|
|
77
|
+
},
|
|
78
|
+
];
|
|
79
|
+
}
|
|
80
|
+
if (server.status === 'needs-authentication') {
|
|
81
|
+
return [
|
|
82
|
+
{ type: 'authenticate', name: server.name },
|
|
83
|
+
{
|
|
84
|
+
type: 'set-enabled',
|
|
85
|
+
name: server.name,
|
|
86
|
+
scope: server.scope,
|
|
87
|
+
enabled: false,
|
|
88
|
+
},
|
|
89
|
+
];
|
|
90
|
+
}
|
|
91
|
+
return [
|
|
92
|
+
...(server.status === 'connected' && server.toolCount > 0
|
|
93
|
+
? [{ type: 'view-tools', name: server.name }]
|
|
94
|
+
: []),
|
|
95
|
+
{ type: 'reconnect', name: server.name },
|
|
96
|
+
{
|
|
97
|
+
type: 'set-enabled',
|
|
98
|
+
name: server.name,
|
|
99
|
+
scope: server.scope,
|
|
100
|
+
enabled: false,
|
|
101
|
+
},
|
|
102
|
+
];
|
|
103
|
+
}
|
|
104
|
+
function bounded(index, length) {
|
|
105
|
+
return Math.min(Math.max(0, index), Math.max(0, length - 1));
|
|
106
|
+
}
|
|
107
|
+
export function reduceTuiMcpPanelState(model, state, input) {
|
|
108
|
+
const serverIndex = bounded(state.serverIndex, model.servers.length);
|
|
109
|
+
const server = model.servers[serverIndex];
|
|
110
|
+
const normalized = { ...state, serverIndex };
|
|
111
|
+
if (input.type === 'back') {
|
|
112
|
+
if (state.depth === 'list') {
|
|
113
|
+
return { state: normalized, command: { type: 'close' } };
|
|
114
|
+
}
|
|
115
|
+
if (state.depth === 'detail') {
|
|
116
|
+
return { state: { depth: 'list', serverIndex, selectedIndex: 0 } };
|
|
117
|
+
}
|
|
118
|
+
if (state.depth === 'tools') {
|
|
119
|
+
return { state: { depth: 'detail', serverIndex, selectedIndex: 0 } };
|
|
120
|
+
}
|
|
121
|
+
return { state: { depth: 'tools', serverIndex, selectedIndex: 0 } };
|
|
122
|
+
}
|
|
123
|
+
if (!server)
|
|
124
|
+
return { state: normalized };
|
|
125
|
+
if (state.depth === 'list') {
|
|
126
|
+
if (input.type === 'confirm') {
|
|
127
|
+
return {
|
|
128
|
+
state: { depth: 'detail', serverIndex, selectedIndex: 0 },
|
|
129
|
+
};
|
|
130
|
+
}
|
|
131
|
+
const offset = input.type === 'up' ? -1 : input.type === 'down' ? 1 : 0;
|
|
132
|
+
const requested = input.type === 'select' ? input.index : serverIndex + offset;
|
|
133
|
+
return {
|
|
134
|
+
state: {
|
|
135
|
+
depth: 'list',
|
|
136
|
+
serverIndex: bounded(requested, model.servers.length),
|
|
137
|
+
selectedIndex: 0,
|
|
138
|
+
},
|
|
139
|
+
};
|
|
140
|
+
}
|
|
141
|
+
if (state.depth === 'detail') {
|
|
142
|
+
const actions = tuiMcpServerActions(server);
|
|
143
|
+
const selectedIndex = bounded(state.selectedIndex, actions.length);
|
|
144
|
+
if (input.type === 'confirm') {
|
|
145
|
+
const command = actions[selectedIndex];
|
|
146
|
+
if (command?.type === 'view-tools') {
|
|
147
|
+
return {
|
|
148
|
+
state: { depth: 'tools', serverIndex, selectedIndex: 0 },
|
|
149
|
+
command,
|
|
150
|
+
};
|
|
151
|
+
}
|
|
152
|
+
return command
|
|
153
|
+
? { state: { ...normalized, selectedIndex }, command }
|
|
154
|
+
: { state: { ...normalized, selectedIndex } };
|
|
155
|
+
}
|
|
156
|
+
const offset = input.type === 'up' ? -1 : input.type === 'down' ? 1 : 0;
|
|
157
|
+
const requested = input.type === 'select' ? input.index : selectedIndex + offset;
|
|
158
|
+
return {
|
|
159
|
+
state: {
|
|
160
|
+
...normalized,
|
|
161
|
+
selectedIndex: bounded(requested, actions.length),
|
|
162
|
+
},
|
|
163
|
+
};
|
|
164
|
+
}
|
|
165
|
+
if (state.depth === 'tool')
|
|
166
|
+
return { state: normalized };
|
|
167
|
+
const tools = server.tools ?? [];
|
|
168
|
+
const selectedIndex = bounded(state.selectedIndex, tools.length);
|
|
169
|
+
if (state.depth === 'tools' && input.type === 'confirm' && tools.length > 0) {
|
|
170
|
+
return { state: { depth: 'tool', serverIndex, selectedIndex } };
|
|
171
|
+
}
|
|
172
|
+
const offset = input.type === 'up' ? -1 : input.type === 'down' ? 1 : 0;
|
|
173
|
+
const requested = input.type === 'select' ? input.index : selectedIndex + offset;
|
|
174
|
+
return {
|
|
175
|
+
state: {
|
|
176
|
+
...normalized,
|
|
177
|
+
selectedIndex: bounded(requested, tools.length),
|
|
178
|
+
},
|
|
179
|
+
};
|
|
180
|
+
}
|
|
181
|
+
//# sourceMappingURL=mcp-panel-projector.js.map
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { type TuiMcpPanelModel, type TuiMcpPanelState } from './mcp-panel-projector.js';
|
|
2
|
+
export declare function McpPanel({ model, state, screenReader, width, }: {
|
|
3
|
+
model: TuiMcpPanelModel;
|
|
4
|
+
state: TuiMcpPanelState;
|
|
5
|
+
screenReader?: boolean;
|
|
6
|
+
width?: number;
|
|
7
|
+
}): import("react").JSX.Element;
|
|
8
|
+
//# sourceMappingURL=mcp-panel.d.ts.map
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
+
import { Box, Text } from 'ink';
|
|
3
|
+
import { useTerminalWidth } from './claude-style.js';
|
|
4
|
+
import { tuiMcpServerActions, } from './mcp-panel-projector.js';
|
|
5
|
+
const EMPTY_MESSAGE = 'No MCP servers configured. Run claude doctor if this is unexpected — it lists MCP config files that failed validation. Otherwise, run claude mcp --help or visit https://code.claude.com/docs/en/mcp to learn more.';
|
|
6
|
+
const SCOPE_LABELS = {
|
|
7
|
+
project: 'Project MCPs',
|
|
8
|
+
local: 'Local MCPs',
|
|
9
|
+
user: 'User MCPs',
|
|
10
|
+
};
|
|
11
|
+
function capitalized(value) {
|
|
12
|
+
return `${value.slice(0, 1).toUpperCase()}${value.slice(1)}`;
|
|
13
|
+
}
|
|
14
|
+
function serverStatus(server) {
|
|
15
|
+
if (server.status === 'connected') {
|
|
16
|
+
return `✔ connected${server.toolCount > 0
|
|
17
|
+
? ` · ${server.toolCount} ${server.toolCount === 1 ? 'tool' : 'tools'}`
|
|
18
|
+
: ''}`;
|
|
19
|
+
}
|
|
20
|
+
if (server.status === 'needs-authentication') {
|
|
21
|
+
return '△ needs authentication';
|
|
22
|
+
}
|
|
23
|
+
return server.status === 'failed' ? '✘ failed' : '◯ disabled';
|
|
24
|
+
}
|
|
25
|
+
function actionLabel(command) {
|
|
26
|
+
if (command.type === 'view-tools')
|
|
27
|
+
return 'View tools';
|
|
28
|
+
if (command.type === 'reconnect')
|
|
29
|
+
return 'Reconnect';
|
|
30
|
+
if (command.type === 'authenticate')
|
|
31
|
+
return 'Authenticate';
|
|
32
|
+
if (command.type === 'set-enabled') {
|
|
33
|
+
return command.enabled ? 'Enable' : 'Disable';
|
|
34
|
+
}
|
|
35
|
+
return 'Close';
|
|
36
|
+
}
|
|
37
|
+
function ListPanel({ model, state, screenReader, }) {
|
|
38
|
+
return (_jsxs(Box, { flexDirection: "column", children: [_jsx(Text, { bold: true, children: "Manage MCP servers" }), _jsxs(Text, { children: [model.servers.length, ' ', model.servers.length === 1 ? 'server' : 'servers'] }), ['project', 'local', 'user'].flatMap((scope) => {
|
|
39
|
+
const scoped = model.servers
|
|
40
|
+
.map((server, index) => ({ server, index }))
|
|
41
|
+
.filter(({ server }) => server.scope === scope);
|
|
42
|
+
if (scoped.length === 0)
|
|
43
|
+
return null;
|
|
44
|
+
const locations = [
|
|
45
|
+
...new Set(scoped.map(({ server }) => server.location)),
|
|
46
|
+
];
|
|
47
|
+
return locations.map((location) => (_jsxs(Box, { flexDirection: "column", marginTop: 1, children: [_jsxs(Text, { children: [SCOPE_LABELS[scope], " ", ' ', "(", location, ")"] }), scoped
|
|
48
|
+
.filter(({ server }) => server.location === location)
|
|
49
|
+
.map(({ server, index }) => {
|
|
50
|
+
const selected = index === state.serverIndex;
|
|
51
|
+
return (_jsxs(Text, { inverse: !screenReader && selected, children: [screenReader && selected
|
|
52
|
+
? 'Selected server: '
|
|
53
|
+
: selected
|
|
54
|
+
? '❯ '
|
|
55
|
+
: ' ', server.name, " ", ' · ', serverStatus(server)] }, `${scope}:${server.name}`));
|
|
56
|
+
})] }, `${scope}:${location}`)));
|
|
57
|
+
}), _jsx(Text, { children: "\u203B Run claude --debug to see error logs" }), _jsx(Text, { children: "https://code.claude.com/docs/en/mcp for help" }), _jsx(Text, { dimColor: true, children: "\u2191/\u2193 to navigate \u00B7 Enter to confirm \u00B7 Esc to cancel" })] }));
|
|
58
|
+
}
|
|
59
|
+
function DetailPanel({ server, state, screenReader, }) {
|
|
60
|
+
const actions = tuiMcpServerActions(server);
|
|
61
|
+
return (_jsxs(Box, { flexDirection: "column", children: [_jsxs(Text, { bold: true, children: [capitalized(server.name), " MCP Server"] }), _jsxs(Text, { children: ["Status: ", server.statusDetail] }), server.authDetail ? _jsxs(Text, { children: ["Auth: ", server.authDetail] }) : null, server.transport === 'stdio' ? (_jsxs(_Fragment, { children: [_jsxs(Text, { children: ["Command: ", server.command ?? ''] }), server.args.length > 0 ? (_jsxs(Text, { children: ["Args: ", server.args.join(' ')] })) : null] })) : (_jsxs(Text, { children: ["URL: ", server.url ?? ''] })), _jsxs(Text, { children: ["Config location: ", server.location] }), server.status === 'connected' && server.capabilities.length > 0 ? (_jsxs(Text, { children: ["Capabilities: ", ' ' + server.capabilities.join(' · ')] })) : null, server.status === 'connected' && server.toolCount > 0 ? (_jsx(Text, { children: `Tools: ${server.toolCount} ${server.toolCount === 1 ? 'tool' : 'tools'}` })) : null, actions.map((action, index) => (_jsxs(Text, { inverse: !screenReader && index === state.selectedIndex, children: [screenReader && index === state.selectedIndex
|
|
62
|
+
? 'Selected action: '
|
|
63
|
+
: `${index + 1}. `, actionLabel(action)] }, `${action.type}:${index}`))), _jsxs(Text, { children: ["Enter selection [1-", actions.length, "], or Escape to cancel:"] }), _jsx(Text, { dimColor: true, children: "\u2191/\u2193 to navigate \u00B7 Enter to select \u00B7 Esc to back" })] }));
|
|
64
|
+
}
|
|
65
|
+
function ToolsPanel({ server, state, screenReader, }) {
|
|
66
|
+
const tools = server.tools ?? [];
|
|
67
|
+
return (_jsxs(Box, { flexDirection: "column", children: [_jsxs(Text, { bold: true, children: ["Tools for ", server.name] }), _jsxs(Text, { children: [tools.length, " ", tools.length === 1 ? 'tool' : 'tools'] }), tools.map((tool, index) => (_jsxs(Text, { inverse: !screenReader && index === state.selectedIndex, children: [screenReader && index === state.selectedIndex
|
|
68
|
+
? 'Selected tool: '
|
|
69
|
+
: `${index + 1}. `, tool.name] }, tool.fullName))), _jsxs(Text, { children: ["Enter selection [1-", tools.length, "], or Escape to cancel:"] }), _jsx(Text, { dimColor: true, children: "\u2191/\u2193 to navigate \u00B7 Enter to select \u00B7 Esc to back" })] }));
|
|
70
|
+
}
|
|
71
|
+
function ToolPanel({ server, state, }) {
|
|
72
|
+
const tool = server.tools?.[state.selectedIndex];
|
|
73
|
+
if (!tool)
|
|
74
|
+
return null;
|
|
75
|
+
return (_jsxs(Box, { flexDirection: "column", children: [_jsx(Text, { bold: true, children: tool.name }), _jsx(Text, { children: server.name }), _jsxs(Text, { children: ["Tool name: ", ' ' + tool.name] }), _jsxs(Text, { children: ["Full name: ", ' ' + tool.fullName] }), _jsx(Text, { children: "Description:" }), _jsx(Text, { children: tool.description ?? '' }), _jsx(Text, { dimColor: true, children: "Esc to go back" })] }));
|
|
76
|
+
}
|
|
77
|
+
export function McpPanel({ model, state, screenReader = false, width, }) {
|
|
78
|
+
const terminalWidth = useTerminalWidth(width);
|
|
79
|
+
const server = model.servers[state.serverIndex];
|
|
80
|
+
let content;
|
|
81
|
+
if (model.servers.length === 0)
|
|
82
|
+
content = _jsx(Text, { children: EMPTY_MESSAGE });
|
|
83
|
+
else if (!server)
|
|
84
|
+
content = null;
|
|
85
|
+
else if (state.depth === 'detail') {
|
|
86
|
+
content = (_jsx(DetailPanel, { server: server, state: state, screenReader: screenReader }));
|
|
87
|
+
}
|
|
88
|
+
else if (state.depth === 'tools') {
|
|
89
|
+
content = (_jsx(ToolsPanel, { server: server, state: state, screenReader: screenReader }));
|
|
90
|
+
}
|
|
91
|
+
else if (state.depth === 'tool') {
|
|
92
|
+
content = _jsx(ToolPanel, { server: server, state: state });
|
|
93
|
+
}
|
|
94
|
+
else {
|
|
95
|
+
content = (_jsx(ListPanel, { model: model, state: state, screenReader: screenReader }));
|
|
96
|
+
}
|
|
97
|
+
return (_jsx(Box, { flexDirection: "column", width: terminalWidth, children: content }));
|
|
98
|
+
}
|
|
99
|
+
//# sourceMappingURL=mcp-panel.js.map
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import type { ModelToolCall } from '../../core/runtime.js';
|
|
2
|
+
export interface RecentlyDeniedAction {
|
|
3
|
+
id: string;
|
|
4
|
+
call: ModelToolCall;
|
|
5
|
+
display: string;
|
|
6
|
+
reason: string;
|
|
7
|
+
sessionId: string;
|
|
8
|
+
}
|
|
9
|
+
export interface RecentlyDeniedStore {
|
|
10
|
+
load(): Promise<readonly RecentlyDeniedAction[]>;
|
|
11
|
+
record(action: RecentlyDeniedAction): Promise<readonly RecentlyDeniedAction[]>;
|
|
12
|
+
remove(id: string): Promise<readonly RecentlyDeniedAction[]>;
|
|
13
|
+
}
|
|
14
|
+
export declare function createRecentlyDeniedStore(): RecentlyDeniedStore;
|
|
15
|
+
//# sourceMappingURL=recently-denied.d.ts.map
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
export function createRecentlyDeniedStore() {
|
|
2
|
+
let entries = [];
|
|
3
|
+
return {
|
|
4
|
+
async load() {
|
|
5
|
+
return entries;
|
|
6
|
+
},
|
|
7
|
+
async record(action) {
|
|
8
|
+
entries = [action, ...entries];
|
|
9
|
+
return entries;
|
|
10
|
+
},
|
|
11
|
+
async remove(id) {
|
|
12
|
+
const index = entries.findIndex((entry) => entry.id === id);
|
|
13
|
+
if (index >= 0)
|
|
14
|
+
entries = entries.toSpliced(index, 1);
|
|
15
|
+
return entries;
|
|
16
|
+
},
|
|
17
|
+
};
|
|
18
|
+
}
|
|
19
|
+
//# sourceMappingURL=recently-denied.js.map
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { TranscriptItem } from './claude-style.js';
|
|
2
|
+
import type { PraxisRuntimeSettings } from './runtime-settings.js';
|
|
3
|
+
export type CopyCandidate = {
|
|
4
|
+
label: string;
|
|
5
|
+
description: string;
|
|
6
|
+
text: string;
|
|
7
|
+
};
|
|
8
|
+
export declare function spinnerTip(settings: Pick<PraxisRuntimeSettings, 'tips'>): string | undefined;
|
|
9
|
+
export declare function questionTimeoutMilliseconds(value: PraxisRuntimeSettings['askUserQuestionTimeout']): number | undefined;
|
|
10
|
+
export declare function workflowRuntimeInstructions(settings: Pick<PraxisRuntimeSettings, 'workflows' | 'workflowKeywordTriggerEnabled' | 'workflowSizeGuideline'>): string | undefined;
|
|
11
|
+
export declare function copyCandidates(response: string): readonly CopyCandidate[];
|
|
12
|
+
export declare function shouldShowCopyPicker(response: string): boolean;
|
|
13
|
+
export declare function externalEditorInitialContent(prompt: string, history: readonly TranscriptItem[], enabled: boolean): string;
|
|
14
|
+
export declare function sessionRecap(history: readonly TranscriptItem[]): string | undefined;
|
|
15
|
+
export declare function formatTurnDuration(milliseconds: number | undefined): string | undefined;
|
|
16
|
+
export declare function autoUpdateTarget(channel: PraxisRuntimeSettings['autoUpdatesChannel']): 'latest' | 'stable';
|
|
17
|
+
//# sourceMappingURL=runtime-interactions.d.ts.map
|
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
const SPINNER_TIPS = [
|
|
2
|
+
'Tip: use /help to browse local commands.',
|
|
3
|
+
'Tip: use @ to attach a file or an agent definition.',
|
|
4
|
+
'Tip: press ctrl+o to expand the detailed transcript.',
|
|
5
|
+
'Tip: use /compact to summarize a long conversation.',
|
|
6
|
+
];
|
|
7
|
+
export function spinnerTip(settings) {
|
|
8
|
+
if (!settings.tips)
|
|
9
|
+
return undefined;
|
|
10
|
+
return SPINNER_TIPS[Math.floor(Date.now() / 8_000) % SPINNER_TIPS.length];
|
|
11
|
+
}
|
|
12
|
+
export function questionTimeoutMilliseconds(value) {
|
|
13
|
+
switch (value) {
|
|
14
|
+
case '60s':
|
|
15
|
+
return 60_000;
|
|
16
|
+
case '5m':
|
|
17
|
+
return 5 * 60_000;
|
|
18
|
+
case '10m':
|
|
19
|
+
return 10 * 60_000;
|
|
20
|
+
case 'never':
|
|
21
|
+
return undefined;
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
export function workflowRuntimeInstructions(settings) {
|
|
25
|
+
if (!settings.workflows)
|
|
26
|
+
return undefined;
|
|
27
|
+
const keyword = settings.workflowKeywordTriggerEnabled
|
|
28
|
+
? 'Treat an explicit "ultracode" request as a request to consider a dynamic workflow.'
|
|
29
|
+
: 'Do not infer a dynamic workflow from an "ultracode" keyword alone; require an explicit workflow request.';
|
|
30
|
+
const size = settings.workflowSizeGuideline === 'unrestricted'
|
|
31
|
+
? 'No workflow size guideline is configured.'
|
|
32
|
+
: `Prefer a ${settings.workflowSizeGuideline} workflow when creating a dynamic workflow unless the user explicitly asks otherwise.`;
|
|
33
|
+
return `Dynamic workflows are available for explicitly requested multi-step automation. ${keyword} ${size}`;
|
|
34
|
+
}
|
|
35
|
+
export function copyCandidates(response) {
|
|
36
|
+
const candidates = [
|
|
37
|
+
{
|
|
38
|
+
label: 'Full response',
|
|
39
|
+
description: 'Copy the complete assistant response.',
|
|
40
|
+
text: response,
|
|
41
|
+
},
|
|
42
|
+
];
|
|
43
|
+
const blocks = response.matchAll(/```[^\n]*\n([\s\S]*?)```/gu);
|
|
44
|
+
let index = 0;
|
|
45
|
+
for (const block of blocks) {
|
|
46
|
+
const text = block[1] ?? '';
|
|
47
|
+
if (!text)
|
|
48
|
+
continue;
|
|
49
|
+
index += 1;
|
|
50
|
+
candidates.push({
|
|
51
|
+
label: `Code block ${index}`,
|
|
52
|
+
description: `Copy code block ${index} only.`,
|
|
53
|
+
text,
|
|
54
|
+
});
|
|
55
|
+
}
|
|
56
|
+
return candidates;
|
|
57
|
+
}
|
|
58
|
+
export function shouldShowCopyPicker(response) {
|
|
59
|
+
return copyCandidates(response).length > 1;
|
|
60
|
+
}
|
|
61
|
+
export function externalEditorInitialContent(prompt, history, enabled) {
|
|
62
|
+
if (!enabled)
|
|
63
|
+
return prompt;
|
|
64
|
+
const response = [...history]
|
|
65
|
+
.reverse()
|
|
66
|
+
.find((item) => item.kind === 'assistant');
|
|
67
|
+
if (!response?.text)
|
|
68
|
+
return prompt;
|
|
69
|
+
return `${prompt}\n\n--- Last response (context only; remove before sending) ---\n${response.text}`;
|
|
70
|
+
}
|
|
71
|
+
export function sessionRecap(history) {
|
|
72
|
+
const lastUser = [...history]
|
|
73
|
+
.reverse()
|
|
74
|
+
.find((item) => item.kind === 'user');
|
|
75
|
+
const lastAssistant = [...history]
|
|
76
|
+
.reverse()
|
|
77
|
+
.find((item) => item.kind === 'assistant');
|
|
78
|
+
if (!lastUser && !lastAssistant)
|
|
79
|
+
return undefined;
|
|
80
|
+
const compact = (text) => text.replace(/\s+/gu, ' ').trim().slice(0, 160);
|
|
81
|
+
return [
|
|
82
|
+
'Session recap',
|
|
83
|
+
...(lastUser ? [`Last request: ${compact(lastUser.text)}`] : []),
|
|
84
|
+
...(lastAssistant ? [`Last response: ${compact(lastAssistant.text)}`] : []),
|
|
85
|
+
].join(' · ');
|
|
86
|
+
}
|
|
87
|
+
export function formatTurnDuration(milliseconds) {
|
|
88
|
+
if (milliseconds === undefined || milliseconds < 0)
|
|
89
|
+
return undefined;
|
|
90
|
+
if (milliseconds < 1_000)
|
|
91
|
+
return `${milliseconds}ms`;
|
|
92
|
+
const seconds = Math.floor(milliseconds / 1_000);
|
|
93
|
+
if (seconds < 60)
|
|
94
|
+
return `${seconds}s`;
|
|
95
|
+
return `${Math.floor(seconds / 60)}m ${seconds % 60}s`;
|
|
96
|
+
}
|
|
97
|
+
export function autoUpdateTarget(channel) {
|
|
98
|
+
return channel === 'stable' ? 'stable' : 'latest';
|
|
99
|
+
}
|
|
100
|
+
//# sourceMappingURL=runtime-interactions.js.map
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import { type ConfigSettingsTarget, type ConfigSettingsSnapshot } from './config-settings.js';
|
|
2
|
+
import type { CliControls } from '../protocol.js';
|
|
3
|
+
export interface PraxisRuntimeSettings {
|
|
4
|
+
tui: 'default' | 'fullscreen';
|
|
5
|
+
autoCompact: boolean;
|
|
6
|
+
switchModelsOnFlag: boolean;
|
|
7
|
+
tips: boolean;
|
|
8
|
+
reduceMotion: boolean;
|
|
9
|
+
thinking: boolean;
|
|
10
|
+
recap: boolean;
|
|
11
|
+
checkpoints: boolean;
|
|
12
|
+
workflows: boolean;
|
|
13
|
+
workflowKeywordTriggerEnabled: boolean;
|
|
14
|
+
workflowSizeGuideline: 'unrestricted' | 'small' | 'medium' | 'large';
|
|
15
|
+
verbose: boolean;
|
|
16
|
+
progressBar: boolean;
|
|
17
|
+
turnDuration: boolean;
|
|
18
|
+
permissionMode: 'default' | 'plan' | 'acceptEdits' | 'auto' | 'dontAsk';
|
|
19
|
+
worktreeBaseRef: 'fresh' | 'head';
|
|
20
|
+
useAutoModeDuringPlan: boolean;
|
|
21
|
+
gitignore: boolean;
|
|
22
|
+
copyFullResponse: boolean;
|
|
23
|
+
defaultToAgentsView: boolean;
|
|
24
|
+
leftArrowOpensAgents: boolean;
|
|
25
|
+
autoUpdatesChannel: 'latest' | 'stable';
|
|
26
|
+
theme: string;
|
|
27
|
+
notifChannel: string;
|
|
28
|
+
outputStyle: 'default' | 'Proactive' | 'Explanatory' | 'Learning';
|
|
29
|
+
language: string;
|
|
30
|
+
editor: 'normal' | 'vim';
|
|
31
|
+
askUserQuestionTimeout: 'never' | '60s' | '5m' | '10m';
|
|
32
|
+
externalEditorContext: boolean;
|
|
33
|
+
prStatus: boolean;
|
|
34
|
+
model: string;
|
|
35
|
+
}
|
|
36
|
+
export declare function projectRuntimeSettings(snapshot: ConfigSettingsSnapshot): PraxisRuntimeSettings;
|
|
37
|
+
export declare function loadRuntimeSettings(target?: ConfigSettingsTarget): Promise<PraxisRuntimeSettings>;
|
|
38
|
+
export declare function runtimeSettingsSystemPrompt(settings: PraxisRuntimeSettings | undefined): string | undefined;
|
|
39
|
+
export declare function applyRuntimeSettingDefaults(controls: CliControls, settings: PraxisRuntimeSettings | undefined): CliControls;
|
|
40
|
+
//# sourceMappingURL=runtime-settings.d.ts.map
|
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
import { CLAUDE_2_1_208_CONFIG_SETTINGS, configSettingValue, loadConfigSettings, } from './config-settings.js';
|
|
2
|
+
function value(snapshot, id) {
|
|
3
|
+
const definition = CLAUDE_2_1_208_CONFIG_SETTINGS.find((candidate) => candidate.id === id);
|
|
4
|
+
if (!definition)
|
|
5
|
+
throw new Error(`Unknown runtime setting: ${id}`);
|
|
6
|
+
return configSettingValue(snapshot, definition);
|
|
7
|
+
}
|
|
8
|
+
export function projectRuntimeSettings(snapshot) {
|
|
9
|
+
return {
|
|
10
|
+
tui: value(snapshot, 'tui'),
|
|
11
|
+
autoCompact: value(snapshot, 'autoCompact'),
|
|
12
|
+
switchModelsOnFlag: value(snapshot, 'switchModelsOnFlag'),
|
|
13
|
+
tips: value(snapshot, 'tips'),
|
|
14
|
+
reduceMotion: value(snapshot, 'reduceMotion'),
|
|
15
|
+
thinking: value(snapshot, 'thinking'),
|
|
16
|
+
recap: value(snapshot, 'recap'),
|
|
17
|
+
checkpoints: value(snapshot, 'checkpoints'),
|
|
18
|
+
workflows: value(snapshot, 'workflows'),
|
|
19
|
+
workflowKeywordTriggerEnabled: value(snapshot, 'workflowKeywordTriggerEnabled'),
|
|
20
|
+
workflowSizeGuideline: value(snapshot, 'workflowSizeGuideline'),
|
|
21
|
+
verbose: value(snapshot, 'verbose'),
|
|
22
|
+
progressBar: value(snapshot, 'progressBar'),
|
|
23
|
+
turnDuration: value(snapshot, 'turnDuration'),
|
|
24
|
+
permissionMode: value(snapshot, 'permissionMode'),
|
|
25
|
+
worktreeBaseRef: value(snapshot, 'worktreeBaseRef'),
|
|
26
|
+
useAutoModeDuringPlan: value(snapshot, 'useAutoModeDuringPlan'),
|
|
27
|
+
gitignore: value(snapshot, 'gitignore'),
|
|
28
|
+
copyFullResponse: value(snapshot, 'copyFullResponse'),
|
|
29
|
+
defaultToAgentsView: value(snapshot, 'defaultToAgentsView'),
|
|
30
|
+
leftArrowOpensAgents: value(snapshot, 'leftArrowOpensAgents'),
|
|
31
|
+
autoUpdatesChannel: value(snapshot, 'autoUpdatesChannel'),
|
|
32
|
+
theme: value(snapshot, 'theme'),
|
|
33
|
+
notifChannel: value(snapshot, 'notifChannel'),
|
|
34
|
+
outputStyle: value(snapshot, 'outputStyle'),
|
|
35
|
+
language: value(snapshot, 'language'),
|
|
36
|
+
editor: value(snapshot, 'editor'),
|
|
37
|
+
askUserQuestionTimeout: value(snapshot, 'askUserQuestionTimeout'),
|
|
38
|
+
externalEditorContext: value(snapshot, 'externalEditorContext'),
|
|
39
|
+
prStatus: value(snapshot, 'prStatus'),
|
|
40
|
+
model: value(snapshot, 'model'),
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
export async function loadRuntimeSettings(target) {
|
|
44
|
+
return projectRuntimeSettings(await loadConfigSettings(target));
|
|
45
|
+
}
|
|
46
|
+
export function runtimeSettingsSystemPrompt(settings) {
|
|
47
|
+
if (!settings)
|
|
48
|
+
return undefined;
|
|
49
|
+
const sections = [
|
|
50
|
+
settings.outputStyle === 'default'
|
|
51
|
+
? null
|
|
52
|
+
: `Output style: ${settings.outputStyle}. Adapt explanations and initiative to this style.`,
|
|
53
|
+
settings.language === 'default'
|
|
54
|
+
? null
|
|
55
|
+
: `Respond in the user's configured language: ${settings.language}.`,
|
|
56
|
+
settings.verbose
|
|
57
|
+
? 'Provide enough operational detail for the interactive verbose transcript; include exact tool and implementation outcomes when useful.'
|
|
58
|
+
: null,
|
|
59
|
+
settings.workflowKeywordTriggerEnabled
|
|
60
|
+
? null
|
|
61
|
+
: 'Do not treat "ultracode" as a dynamic-workflow trigger unless the user explicitly requests a workflow.',
|
|
62
|
+
settings.workflowSizeGuideline === 'unrestricted'
|
|
63
|
+
? null
|
|
64
|
+
: `When creating a dynamic workflow, prefer a ${settings.workflowSizeGuideline} workflow unless the user explicitly requests otherwise.`,
|
|
65
|
+
].filter((section) => section !== null);
|
|
66
|
+
return sections.length > 0 ? sections.join('\n') : undefined;
|
|
67
|
+
}
|
|
68
|
+
export function applyRuntimeSettingDefaults(controls, settings) {
|
|
69
|
+
if (!settings)
|
|
70
|
+
return controls;
|
|
71
|
+
return {
|
|
72
|
+
...controls,
|
|
73
|
+
...(settings.model !== 'default' && controls.model === undefined
|
|
74
|
+
? { model: settings.model }
|
|
75
|
+
: {}),
|
|
76
|
+
...(controls.permissionMode === 'default'
|
|
77
|
+
? { permissionMode: settings.permissionMode }
|
|
78
|
+
: {}),
|
|
79
|
+
...(controls.thinking === undefined
|
|
80
|
+
? { thinking: settings.thinking ? 'enabled' : 'disabled' }
|
|
81
|
+
: {}),
|
|
82
|
+
};
|
|
83
|
+
}
|
|
84
|
+
//# sourceMappingURL=runtime-settings.js.map
|