@lalalic/neoy-core 0.1.8 → 0.1.10
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/package.json +1 -1
- package/src/core/tools/xchat.mjs +23 -4
package/package.json
CHANGED
package/src/core/tools/xchat.mjs
CHANGED
|
@@ -11,7 +11,7 @@ const THREAD_ID = /^[A-Za-z0-9_-]{8,160}$/;
|
|
|
11
11
|
const XCHAT_COMMAND_TOOLS = [
|
|
12
12
|
{
|
|
13
13
|
name: "xchat.turn.new",
|
|
14
|
-
description: "
|
|
14
|
+
description: "Submit a ChatGPT turn. Default async queues durable FIFO and returns status=submitted; sync submits immediately in a caller-owned WebHelm Session and returns a verified receipt.",
|
|
15
15
|
inputSchema: {
|
|
16
16
|
type: "object",
|
|
17
17
|
additionalProperties: false,
|
|
@@ -19,6 +19,9 @@ const XCHAT_COMMAND_TOOLS = [
|
|
|
19
19
|
project_id: { type: "string", description: "Optional stable ChatGPT Project ID. Omit for a standalone thread." },
|
|
20
20
|
thread_id: { type: "string", description: "Stable current ChatGPT thread ID." },
|
|
21
21
|
message: { type: "string", description: "Continuation/handoff message for the next turn." },
|
|
22
|
+
mode: { type: "string", enum: ["async", "sync"], description: "async is the default durable queue; sync waits for submission and requires caller-owned session_id." },
|
|
23
|
+
mergeable: { type: "boolean", description: "Default false. Append to the same thread's pending mergeable turn." },
|
|
24
|
+
session_id: { type: "string", description: "Required for sync only. Caller creates and closes this WebHelm Session." },
|
|
22
25
|
reason: { type: "string", description: "Optional diagnostic reason for the control transfer." },
|
|
23
26
|
},
|
|
24
27
|
required: ["thread_id", "message"],
|
|
@@ -49,7 +52,7 @@ const XCHAT_COMMAND_MAP = new Map([
|
|
|
49
52
|
|
|
50
53
|
export const XCHAT_LIFECYCLE_TOOLS = [{
|
|
51
54
|
name: "chatgpt",
|
|
52
|
-
description: "Submit
|
|
55
|
+
description: "Submit ChatGPT turns (async FIFO by default, sync opt-in) or create a thread synchronously. Use command='help' for mode and session requirements.",
|
|
53
56
|
inputSchema: {
|
|
54
57
|
type: "object",
|
|
55
58
|
properties: {
|
|
@@ -87,8 +90,20 @@ function validate(args, name) {
|
|
|
87
90
|
threadId = requireText(args, "thread_id");
|
|
88
91
|
if (!THREAD_ID.test(threadId)) throw new Error("thread_id is invalid");
|
|
89
92
|
}
|
|
93
|
+
const mode = name === "xchat.turn.new" ? (args.mode === undefined ? "async" : args.mode) : null;
|
|
94
|
+
if (name === "xchat.turn.new" && !["async", "sync"].includes(mode)) throw new Error("mode must be async or sync");
|
|
95
|
+
const mergeable = name === "xchat.turn.new" ? (args.mergeable ?? false) : false;
|
|
96
|
+
if (typeof mergeable !== "boolean") throw new Error("mergeable must be a boolean");
|
|
97
|
+
if (mergeable && mode !== "async") throw new Error("mergeable requires async mode");
|
|
98
|
+
const sessionId = args.session_id;
|
|
99
|
+
if (name === "xchat.turn.new") {
|
|
100
|
+
if (mode === "sync" && (typeof sessionId !== "string" || !sessionId.trim())) {
|
|
101
|
+
throw new Error("mode sync requires caller-owned session_id");
|
|
102
|
+
}
|
|
103
|
+
if (mode === "async" && sessionId !== undefined) throw new Error("mode async does not accept session_id");
|
|
104
|
+
}
|
|
90
105
|
const reason = typeof args.reason === "string" && args.reason.trim() ? args.reason.trim().slice(0, 2000) : null;
|
|
91
|
-
return { projectId, threadId, sourceThreadId, temporary, message, reason };
|
|
106
|
+
return { projectId, threadId, sourceThreadId, temporary, message, reason, mode, sessionId, mergeable };
|
|
92
107
|
}
|
|
93
108
|
|
|
94
109
|
function resultText(payload) {
|
|
@@ -136,6 +151,8 @@ export function scheduleXChatLifecycle(name, input, options = {}) {
|
|
|
136
151
|
message: parsed.message,
|
|
137
152
|
reason: parsed.reason,
|
|
138
153
|
...(parsed.threadId ? { thread_id: parsed.threadId } : {}),
|
|
154
|
+
...(action === "new-turn" ? { mode: parsed.mode } : {}),
|
|
155
|
+
...(action === "new-turn" ? { mergeable: parsed.mergeable } : {}),
|
|
139
156
|
...(parsed.sourceThreadId ? { source_thread_id: parsed.sourceThreadId } : {}),
|
|
140
157
|
};
|
|
141
158
|
const dir = fs.mkdtempSync(path.join(options.tmpDir || process.env.TMPDIR || "/tmp", "neoy-chatgpt-"));
|
|
@@ -145,7 +162,9 @@ export function scheduleXChatLifecycle(name, input, options = {}) {
|
|
|
145
162
|
fs.writeFileSync(configPath, JSON.stringify(config), { mode: 0o600 });
|
|
146
163
|
const cli = options.cli || process.env.BROWSER_WORKSPACE_CLI || "uvx";
|
|
147
164
|
const prefix = options.cli || process.env.BROWSER_WORKSPACE_CLI ? [] : ["browser-workspace"];
|
|
148
|
-
const
|
|
165
|
+
const sessionArgs = action === "new-thread" ? ["--auto-session"] :
|
|
166
|
+
parsed.mode === "sync" ? ["--mode", "sync", "--session-id", parsed.sessionId.trim()] : ["--mode", "async"];
|
|
167
|
+
const result = (options.spawnSyncImpl || spawnSync)(cli, [...prefix, "platform", "run", "chatgpt", action, ...sessionArgs, "--config", configPath], {
|
|
149
168
|
encoding: "utf8",
|
|
150
169
|
timeout: Number(process.env.XCHAT_LIFECYCLE_TIMEOUT_MS || 600_000),
|
|
151
170
|
maxBuffer: 4 * 1024 * 1024,
|