praxis-agent 0.14.0 → 0.16.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.
Files changed (33) hide show
  1. package/README.md +5 -2
  2. package/dist/application/session-service.d.ts +18 -0
  3. package/dist/application/session-service.js +180 -41
  4. package/dist/application/subagent-service.d.ts +7 -1
  5. package/dist/application/subagent-service.js +238 -53
  6. package/dist/cli/interactive.d.ts +7 -1
  7. package/dist/cli/interactive.js +77 -3
  8. package/dist/cli/protocol.d.ts +13 -0
  9. package/dist/cli/protocol.js +34 -0
  10. package/dist/cli/tui/claude-command-inventory.d.ts +1 -2
  11. package/dist/cli/tui/claude-command-inventory.js +1 -6
  12. package/dist/cli/tui/claude-style.d.ts +4 -1
  13. package/dist/cli/tui/claude-style.js +8 -3
  14. package/dist/cli/tui/slash-commands.d.ts +1 -0
  15. package/dist/cli/tui/slash-commands.js +11 -0
  16. package/dist/cli/tui/theme.d.ts +2 -0
  17. package/dist/cli/tui/theme.js +69 -0
  18. package/dist/cli.d.ts +6 -0
  19. package/dist/cli.js +95 -27
  20. package/dist/compatibility/claude/agent-color.d.ts +25 -0
  21. package/dist/compatibility/claude/agent-color.js +79 -0
  22. package/dist/compatibility/claude/fork.js +5 -1
  23. package/dist/compatibility/claude/schema.js +13 -1
  24. package/dist/extensions/claude-extensions.d.ts +19 -1
  25. package/dist/extensions/claude-extensions.js +126 -1
  26. package/dist/hooks/claude-hooks.d.ts +3 -1
  27. package/dist/hooks/claude-hooks.js +14 -0
  28. package/dist/mcp/claude-mcp-tools.d.ts +18 -0
  29. package/dist/mcp/claude-mcp-tools.js +46 -0
  30. package/dist/persistence/claude-transcript-store.js +1 -0
  31. package/dist/tools/claude-interactive-tools.d.ts +1 -0
  32. package/dist/tools/claude-interactive-tools.js +3 -0
  33. package/package.json +2 -1
@@ -35,6 +35,15 @@ export interface ClaudeMcpRuntime {
35
35
  authenticate(name: string): Promise<void>;
36
36
  reload(): Promise<void>;
37
37
  tools(name: string): Promise<readonly ClaudeMcpToolInspection[]>;
38
+ connectAgent?(options: {
39
+ specs: readonly unknown[];
40
+ base: ToolRegistry;
41
+ cwd: string;
42
+ signal?: AbortSignal;
43
+ }): Promise<{
44
+ tools: ToolRegistry;
45
+ close(): Promise<void>;
46
+ } | null>;
38
47
  /** Release MCP transports and child processes owned by this runtime. */
39
48
  close?(): Promise<void>;
40
49
  }
@@ -99,6 +108,15 @@ export declare class ClaudeMcpToolRegistry implements ToolRegistry, ClaudeMcpRun
99
108
  authenticate(name: string): Promise<void>;
100
109
  reload(): Promise<void>;
101
110
  tools(name: string): Promise<readonly ClaudeMcpToolInspection[]>;
111
+ connectAgent(options: {
112
+ specs: readonly unknown[];
113
+ base: ToolRegistry;
114
+ cwd: string;
115
+ signal?: AbortSignal;
116
+ }): Promise<{
117
+ tools: ToolRegistry;
118
+ close(): Promise<void>;
119
+ } | null>;
102
120
  private runtimeStatuses;
103
121
  private configure;
104
122
  prompts(): readonly ClaudeMcpPromptDefinition[];
@@ -744,6 +744,52 @@ export class ClaudeMcpToolRegistry {
744
744
  }))
745
745
  .sort((left, right) => left.name.localeCompare(right.name));
746
746
  }
747
+ async connectAgent(options) {
748
+ const resources = [];
749
+ for (const spec of options.specs) {
750
+ if (typeof spec === 'string') {
751
+ if (!this.statuses.has(spec)) {
752
+ this.options.onWarning?.(`Agent MCP server not found: ${spec}`);
753
+ }
754
+ continue;
755
+ }
756
+ if (!isRecord(spec))
757
+ continue;
758
+ const entries = Object.entries(spec);
759
+ if (entries.length !== 1) {
760
+ this.options.onWarning?.('Agent MCP server definitions must contain exactly one server');
761
+ continue;
762
+ }
763
+ const [name, config] = entries[0];
764
+ if (this.statuses.has(name))
765
+ continue;
766
+ resources.push({
767
+ path: `agent-mcp:${name}`,
768
+ scope: 'local',
769
+ value: { mcpServers: { [name]: config } },
770
+ });
771
+ }
772
+ if (resources.length === 0)
773
+ return null;
774
+ const tools = await ClaudeMcpToolRegistry.connect({
775
+ base: options.base,
776
+ resources,
777
+ cwd: options.cwd,
778
+ ...(this.options.configRoot
779
+ ? { configRoot: this.options.configRoot }
780
+ : {}),
781
+ ...(this.options.onWarning ? { onWarning: this.options.onWarning } : {}),
782
+ ...(this.options.eventSink ? { eventSink: this.options.eventSink } : {}),
783
+ ...(this.options.authenticateServer
784
+ ? { authenticateServer: this.options.authenticateServer }
785
+ : {}),
786
+ ...(this.options.onElicitation
787
+ ? { onElicitation: this.options.onElicitation }
788
+ : {}),
789
+ ...(options.signal ? { signal: options.signal } : {}),
790
+ });
791
+ return { tools, close: () => tools.close() };
792
+ }
747
793
  runtimeStatuses() {
748
794
  return [...this.statuses.values()].map((status) => {
749
795
  const capabilities = this.serverCapabilities.get(status.name) ?? [];
@@ -16,6 +16,7 @@ export class ClaudeTranscriptParseError extends Error {
16
16
  }
17
17
  const UTF8_DECODER = new TextDecoder('utf-8', { fatal: true });
18
18
  const NON_TAIL_ENTRY_TYPES = new Set([
19
+ 'agent-color',
19
20
  'agent-name',
20
21
  'agent-setting',
21
22
  'custom-title',
@@ -59,6 +59,7 @@ export declare class ClaudeInteractiveToolManager {
59
59
  restore(sessionId: string, entries: readonly ClaudeTranscriptEntry[]): void;
60
60
  setMode(sessionId: string, mode: ClaudePermissionMode): Promise<void>;
61
61
  permissions(sessionId: string): PermissionResolver;
62
+ mode(sessionId: string): ClaudePermissionMode;
62
63
  contextMessage(sessionId: string): string | null;
63
64
  isPlanFile(sessionId: string, requestedPath: string): Promise<boolean>;
64
65
  consumeTransition(callId: string): ClaudePermissionMode | undefined;
@@ -269,6 +269,9 @@ export class ClaudeInteractiveToolManager {
269
269
  resolve: (call, context) => this.resolve(sessionId, call, context),
270
270
  };
271
271
  }
272
+ mode(sessionId) {
273
+ return this.state(sessionId).mode;
274
+ }
272
275
  contextMessage(sessionId) {
273
276
  const state = this.state(sessionId);
274
277
  if (state.mode !== 'plan')
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "praxis-agent",
3
- "version": "0.14.0",
3
+ "version": "0.16.0",
4
4
  "description": "Local-first, single-user general agent for the command line.",
5
5
  "license": "MIT",
6
6
  "author": "wuqisen",
@@ -93,6 +93,7 @@
93
93
  "test:subagent-compat": "npm run build && node scripts/verify-subagent-compatibility.mjs",
94
94
  "test:background-agent-compat": "npm run build && node scripts/verify-background-agent-compatibility.mjs",
95
95
  "test:background-command-compat": "npm run build && node scripts/verify-background-command-compatibility.mjs",
96
+ "test:color-command-compat": "npm run build && node scripts/verify-color-command-compatibility.mjs",
96
97
  "test:task-compat": "npm run build && node scripts/verify-task-compatibility.mjs",
97
98
  "test:scheduled-compat": "npm run build && node scripts/verify-scheduled-tools-compatibility.mjs",
98
99
  "test:top-level-agent-compat": "npm run build && node scripts/verify-top-level-agent-compatibility.mjs",