xiaotime 0.2.1 → 0.3.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 (37) hide show
  1. package/dist/__tests__/approval_menu.test.d.ts +15 -0
  2. package/dist/__tests__/approval_menu.test.d.ts.map +1 -0
  3. package/dist/__tests__/approval_menu.test.js +107 -0
  4. package/dist/__tests__/approval_menu.test.js.map +1 -0
  5. package/dist/__tests__/server_tool_render.test.d.ts +17 -0
  6. package/dist/__tests__/server_tool_render.test.d.ts.map +1 -0
  7. package/dist/__tests__/server_tool_render.test.js +74 -0
  8. package/dist/__tests__/server_tool_render.test.js.map +1 -0
  9. package/dist/__tests__/settings.test.d.ts +16 -0
  10. package/dist/__tests__/settings.test.d.ts.map +1 -0
  11. package/dist/__tests__/settings.test.js +289 -0
  12. package/dist/__tests__/settings.test.js.map +1 -0
  13. package/dist/__tests__/tools.test.d.ts +17 -0
  14. package/dist/__tests__/tools.test.d.ts.map +1 -0
  15. package/dist/__tests__/tools.test.js +381 -0
  16. package/dist/__tests__/tools.test.js.map +1 -0
  17. package/dist/display.d.ts +19 -0
  18. package/dist/display.d.ts.map +1 -1
  19. package/dist/display.js +23 -0
  20. package/dist/display.js.map +1 -1
  21. package/dist/settings.d.ts +109 -0
  22. package/dist/settings.d.ts.map +1 -0
  23. package/dist/settings.js +332 -0
  24. package/dist/settings.js.map +1 -0
  25. package/dist/tools.d.ts +11 -3
  26. package/dist/tools.d.ts.map +1 -1
  27. package/dist/tools.js +96 -33
  28. package/dist/tools.js.map +1 -1
  29. package/dist/ui_state.d.ts +134 -0
  30. package/dist/ui_state.d.ts.map +1 -0
  31. package/dist/ui_state.js +460 -0
  32. package/dist/ui_state.js.map +1 -0
  33. package/dist/ws.d.ts +5 -0
  34. package/dist/ws.d.ts.map +1 -1
  35. package/dist/ws.js +99 -66
  36. package/dist/ws.js.map +1 -1
  37. package/package.json +5 -2
package/dist/ws.js CHANGED
@@ -1,64 +1,40 @@
1
1
  "use strict";
2
2
  /**
3
3
  * WebSocket connection and main message loop.
4
+ *
5
+ * SPRINT-CLI-STATE-MACHINE-1 (#6163 / closes #6127) — drives the
6
+ * SessionUI state machine from incoming WS events so the user gets
7
+ * a spinner while the model is generating / a tool is running, and
8
+ * approval prompts don't race the main rl on keystrokes.
4
9
  */
5
- var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
6
- if (k2 === undefined) k2 = k;
7
- var desc = Object.getOwnPropertyDescriptor(m, k);
8
- if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
9
- desc = { enumerable: true, get: function() { return m[k]; } };
10
- }
11
- Object.defineProperty(o, k2, desc);
12
- }) : (function(o, m, k, k2) {
13
- if (k2 === undefined) k2 = k;
14
- o[k2] = m[k];
15
- }));
16
- var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
17
- Object.defineProperty(o, "default", { enumerable: true, value: v });
18
- }) : function(o, v) {
19
- o["default"] = v;
20
- });
21
- var __importStar = (this && this.__importStar) || (function () {
22
- var ownKeys = function(o) {
23
- ownKeys = Object.getOwnPropertyNames || function (o) {
24
- var ar = [];
25
- for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
26
- return ar;
27
- };
28
- return ownKeys(o);
29
- };
30
- return function (mod) {
31
- if (mod && mod.__esModule) return mod;
32
- var result = {};
33
- if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
34
- __setModuleDefault(result, mod);
35
- return result;
36
- };
37
- })();
38
10
  var __importDefault = (this && this.__importDefault) || function (mod) {
39
11
  return (mod && mod.__esModule) ? mod : { "default": mod };
40
12
  };
41
13
  Object.defineProperty(exports, "__esModule", { value: true });
42
14
  exports.runSession = runSession;
43
15
  const ws_1 = __importDefault(require("ws"));
44
- const readline = __importStar(require("readline"));
45
16
  const config_js_1 = require("./config.js");
46
17
  const auth_js_1 = require("./auth.js");
47
18
  const tools_js_1 = require("./tools.js");
48
19
  const display_js_1 = require("./display.js");
20
+ const ui_state_js_1 = require("./ui_state.js");
49
21
  async function runSession(sessionId) {
50
22
  const wsUrl = `${config_js_1.WS_URL}/terminal/sessions/${sessionId}/stream`;
51
23
  return new Promise((resolve, reject) => {
52
24
  const ws = new ws_1.default(wsUrl);
53
25
  let connected = false;
54
- let waitingForToolResult = false;
55
- let pendingResolve = null;
56
- // ── Readline for user input ───────────────────────────────────
57
- const rl = readline.createInterface({
58
- input: process.stdin,
59
- output: process.stdout,
60
- terminal: true,
61
- });
26
+ const ui = new ui_state_js_1.SessionUI();
27
+ let firstTokenThisTurn = true;
28
+ // #6169 review §1 guard against concurrent tool_call messages.
29
+ // The server-side WS handler dispatches tool calls serially (one
30
+ // tool_call → wait for tool_result → next tool_call), but a buggy
31
+ // server or future protocol change could break that invariant.
32
+ // Overlapping executions would corrupt the SessionUI state
33
+ // machine (running_tool vs awaiting_approval) and possibly skip
34
+ // the approval gate on the second call. Track the in-flight
35
+ // tool_use_id; reject any second tool_call that arrives before
36
+ // the first one's tool_result was sent.
37
+ let inFlightToolUseId = null;
62
38
  ws.on("open", () => {
63
39
  // Auth
64
40
  ws.send(JSON.stringify({ type: "auth", token: (0, auth_js_1.getToken)() }));
@@ -72,51 +48,99 @@ async function runSession(sessionId) {
72
48
  connected = true;
73
49
  (0, tools_js_1.setSessionCwd)(process.cwd());
74
50
  (0, display_js_1.printWelcome)(msg.session_id, msg.session_name, msg.resumed, msg.message_count);
75
- promptUser();
51
+ startUserPromptLoop();
76
52
  break;
77
53
  case "text_delta":
54
+ if (firstTokenThisTurn) {
55
+ ui.onFirstToken();
56
+ firstTokenThisTurn = false;
57
+ }
78
58
  (0, display_js_1.printTextDelta)(msg.content);
79
59
  break;
80
- case "tool_call":
81
- waitingForToolResult = true;
60
+ case "tool_call": {
61
+ // #6169 review §1 — reject overlapping tool calls. The
62
+ // server-side WS handler is supposed to dispatch one
63
+ // tool_call at a time and wait for its tool_result before
64
+ // sending the next; a protocol violation here would
65
+ // corrupt the SessionUI state. Reject the second tool by
66
+ // returning an is_error tool_result and logging — leaves
67
+ // the first execution untouched.
68
+ if (inFlightToolUseId !== null) {
69
+ const errMsg = `Protocol violation: tool_call (id=${msg.tool_use_id}) arrived ` +
70
+ `while another tool (id=${inFlightToolUseId}) is still in flight. ` +
71
+ `CLI rejects overlapping executions; the server WS handler should ` +
72
+ `serialize tool dispatch.`;
73
+ console.error(`\n[cli] ${errMsg}\n`);
74
+ ws.send(JSON.stringify({
75
+ type: "tool_result",
76
+ tool_use_id: msg.tool_use_id,
77
+ content: errMsg,
78
+ is_error: true,
79
+ }));
80
+ break;
81
+ }
82
+ inFlightToolUseId = msg.tool_use_id;
83
+ // executeTool drives its own state transitions when an
84
+ // approval is needed (running_tool ↔ awaiting_approval).
85
+ ui.setState("running_tool");
82
86
  (0, tools_js_1.executeTool)({
83
87
  tool_use_id: msg.tool_use_id,
84
88
  name: msg.name,
85
89
  input: msg.input,
86
- }).then((result) => {
87
- waitingForToolResult = false;
90
+ }, ui).then((result) => {
91
+ inFlightToolUseId = null;
88
92
  ws.send(JSON.stringify({
89
93
  type: "tool_result",
90
94
  tool_use_id: result.tool_use_id,
91
95
  content: result.content,
92
96
  is_error: result.is_error,
93
97
  }));
98
+ // Back to generating; the next text_delta will clear any
99
+ // spinner if onFirstToken hasn't yet been called for this
100
+ // generation segment.
101
+ ui.setState("generating");
102
+ firstTokenThisTurn = true;
94
103
  });
95
104
  break;
105
+ }
96
106
  case "message_stop":
107
+ ui.setState("idle");
97
108
  (0, display_js_1.printTurnEnd)(msg.cost_usd || 0);
98
- promptUser();
109
+ startUserPromptLoop();
99
110
  break;
100
111
  case "error":
112
+ ui.setState("idle");
101
113
  (0, display_js_1.printError)(msg.message);
102
114
  if (!connected) {
103
115
  ws.close();
104
116
  reject(new Error(msg.message));
105
117
  }
106
118
  else {
107
- promptUser();
119
+ startUserPromptLoop();
108
120
  }
109
121
  break;
122
+ case "server_tool_call":
123
+ // #6509 PR3 — visibility line for the 15 server-side tools
124
+ // in terminal_orchestrator/main.py SERVER_TOOLS. Clear the
125
+ // spinner first so the [server:<name>] line doesn't get
126
+ // overwritten by the spinner's next frame, and pin
127
+ // firstTokenThisTurn=false so a subsequent text_delta
128
+ // doesn't double-clear (onFirstToken is idempotent but
129
+ // the bookkeeping flag should reflect reality).
130
+ ui.onFirstToken();
131
+ firstTokenThisTurn = false;
132
+ (0, display_js_1.printServerToolCall)(msg.name, msg.input_summary || "");
133
+ break;
110
134
  case "pong":
111
135
  break;
112
136
  }
113
137
  });
114
138
  ws.on("close", () => {
115
- rl.close();
139
+ ui.getRl().close();
116
140
  resolve();
117
141
  });
118
142
  ws.on("error", (err) => {
119
- rl.close();
143
+ ui.getRl().close();
120
144
  reject(err);
121
145
  });
122
146
  // ── Ping keepalive ────────────────────────────────────────────
@@ -126,24 +150,33 @@ async function runSession(sessionId) {
126
150
  }
127
151
  }, 30000);
128
152
  ws.on("close", () => clearInterval(pingInterval));
129
- // ── User input ────────────────────────────────────────────────
130
- function promptUser() {
131
- if (!connected || waitingForToolResult)
153
+ // ── User input loop ────────────────────────────────────────────
154
+ async function startUserPromptLoop() {
155
+ if (!connected)
132
156
  return;
133
157
  (0, display_js_1.printPrompt)();
134
- rl.once("line", (line) => {
135
- const text = line.trim();
136
- if (!text) {
137
- promptUser();
138
- return;
139
- }
140
- if (ws.readyState === ws_1.default.OPEN) {
141
- ws.send(JSON.stringify({ type: "message", content: text }));
142
- }
143
- });
158
+ const text = await ui.promptLine();
159
+ if (!text) {
160
+ startUserPromptLoop();
161
+ return;
162
+ }
163
+ if (ws.readyState === ws_1.default.OPEN) {
164
+ // Mark generating BEFORE sending the message — gives the user
165
+ // an immediate spinner while we wait for the first token. The
166
+ // server may take 1-3s before the first text_delta lands;
167
+ // pre-#6163 this was a silent wait that looked like a hang.
168
+ ui.setState("generating");
169
+ firstTokenThisTurn = true;
170
+ ws.send(JSON.stringify({ type: "message", content: text }));
171
+ }
144
172
  }
145
- // Ctrl+C
146
- rl.on("close", () => {
173
+ // Ctrl+C — registered via onRlClose (not getRl().on) so the listener
174
+ // survives the rl close-and-recreate cycle in promptApprovalMenu
175
+ // (SPRINT-CLI-APPROVAL-MENU-1 / #6509 PR1). The intra-menu close is
176
+ // suppressed inside promptApprovalMenu via removeAllListeners before
177
+ // calling rl.close(), so this listener only fires for genuine
178
+ // user-initiated Ctrl+C at the main prompt.
179
+ ui.onRlClose(() => {
147
180
  console.log("\nSession paused. Resume with: xiaotime dev --session " + sessionId);
148
181
  ws.close();
149
182
  });
package/dist/ws.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"ws.js","sourceRoot":"","sources":["../src/ws.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"ws.js","sourceRoot":"","sources":["../src/ws.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "xiaotime",
3
- "version": "0.2.1",
3
+ "version": "0.3.0",
4
4
  "description": "Xiaotime Developer — persistent-memory AI coding assistant",
5
5
  "bin": {
6
6
  "xiaotime": "./dist/index.js"
@@ -12,6 +12,8 @@
12
12
  "scripts": {
13
13
  "build": "tsc",
14
14
  "dev": "ts-node src/index.ts",
15
+ "test": "vitest run",
16
+ "test:watch": "vitest",
15
17
  "prepublishOnly": "npm run build"
16
18
  },
17
19
  "dependencies": {
@@ -23,7 +25,8 @@
23
25
  "@types/ws": "^8.5.12",
24
26
  "@types/node": "^22.0.0",
25
27
  "typescript": "^5.7.0",
26
- "ts-node": "^10.9.2"
28
+ "ts-node": "^10.9.2",
29
+ "vitest": "^2.1.0"
27
30
  },
28
31
  "engines": {
29
32
  "node": ">=18.0.0"