cursor-api-proxy 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.
- package/README.md +219 -0
- package/dist/cli.d.ts +5 -0
- package/dist/cli.js +53 -0
- package/dist/cli.js.map +1 -0
- package/dist/client.d.ts +95 -0
- package/dist/client.js +316 -0
- package/dist/client.js.map +1 -0
- package/dist/lib/agent-cmd-args.d.ts +5 -0
- package/dist/lib/agent-cmd-args.js +24 -0
- package/dist/lib/agent-cmd-args.js.map +1 -0
- package/dist/lib/agent-runner.d.ts +12 -0
- package/dist/lib/agent-runner.js +38 -0
- package/dist/lib/agent-runner.js.map +1 -0
- package/dist/lib/anthropic.d.ts +26 -0
- package/dist/lib/anthropic.js +59 -0
- package/dist/lib/anthropic.js.map +1 -0
- package/dist/lib/cli-stream-parser.d.ts +8 -0
- package/dist/lib/cli-stream-parser.js +46 -0
- package/dist/lib/cli-stream-parser.js.map +1 -0
- package/dist/lib/config.d.ts +28 -0
- package/dist/lib/config.js +24 -0
- package/dist/lib/config.js.map +1 -0
- package/dist/lib/cursor-cli.d.ts +9 -0
- package/dist/lib/cursor-cli.js +30 -0
- package/dist/lib/cursor-cli.js.map +1 -0
- package/dist/lib/cursorCli.d.ts +9 -0
- package/dist/lib/cursorCli.js +30 -0
- package/dist/lib/cursorCli.js.map +1 -0
- package/dist/lib/env.d.ts +41 -0
- package/dist/lib/env.js +138 -0
- package/dist/lib/env.js.map +1 -0
- package/dist/lib/handlers/anthropic-messages.d.ts +9 -0
- package/dist/lib/handlers/anthropic-messages.js +124 -0
- package/dist/lib/handlers/anthropic-messages.js.map +1 -0
- package/dist/lib/handlers/chat-completions.d.ts +9 -0
- package/dist/lib/handlers/chat-completions.js +98 -0
- package/dist/lib/handlers/chat-completions.js.map +1 -0
- package/dist/lib/handlers/health.d.ts +7 -0
- package/dist/lib/handlers/health.js +15 -0
- package/dist/lib/handlers/health.js.map +1 -0
- package/dist/lib/handlers/models.d.ts +14 -0
- package/dist/lib/handlers/models.js +34 -0
- package/dist/lib/handlers/models.js.map +1 -0
- package/dist/lib/http.d.ts +5 -0
- package/dist/lib/http.js +32 -0
- package/dist/lib/http.js.map +1 -0
- package/dist/lib/max-mode-preflight.d.ts +5 -0
- package/dist/lib/max-mode-preflight.js +56 -0
- package/dist/lib/max-mode-preflight.js.map +1 -0
- package/dist/lib/model-map.d.ts +17 -0
- package/dist/lib/model-map.js +62 -0
- package/dist/lib/model-map.js.map +1 -0
- package/dist/lib/modelMap.d.ts +17 -0
- package/dist/lib/modelMap.js +62 -0
- package/dist/lib/modelMap.js.map +1 -0
- package/dist/lib/openai.d.ts +7 -0
- package/dist/lib/openai.js +59 -0
- package/dist/lib/openai.js.map +1 -0
- package/dist/lib/process.d.ts +19 -0
- package/dist/lib/process.js +92 -0
- package/dist/lib/process.js.map +1 -0
- package/dist/lib/request-listener.d.ts +7 -0
- package/dist/lib/request-listener.js +70 -0
- package/dist/lib/request-listener.js.map +1 -0
- package/dist/lib/request-log.d.ts +13 -0
- package/dist/lib/request-log.js +110 -0
- package/dist/lib/request-log.js.map +1 -0
- package/dist/lib/requestLog.d.ts +2 -0
- package/dist/lib/requestLog.js +19 -0
- package/dist/lib/requestLog.js.map +1 -0
- package/dist/lib/resolve-model.d.ts +8 -0
- package/dist/lib/resolve-model.js +18 -0
- package/dist/lib/resolve-model.js.map +1 -0
- package/dist/lib/server.d.ts +8 -0
- package/dist/lib/server.js +35 -0
- package/dist/lib/server.js.map +1 -0
- package/dist/lib/workspace.d.ts +6 -0
- package/dist/lib/workspace.js +15 -0
- package/dist/lib/workspace.js.map +1 -0
- package/package.json +50 -0
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { tmpdir } from "node:os";
|
|
2
|
+
import { run } from "./process.js";
|
|
3
|
+
export function parseCursorCliModels(output) {
|
|
4
|
+
const lines = output.split(/\r?\n/g).map((l) => l.trim());
|
|
5
|
+
const models = [];
|
|
6
|
+
for (const line of lines) {
|
|
7
|
+
const match = line.match(/^([A-Za-z0-9][A-Za-z0-9._:/-]*)\s+-\s+(.*)$/);
|
|
8
|
+
if (!match)
|
|
9
|
+
continue;
|
|
10
|
+
const id = match[1];
|
|
11
|
+
const rawName = match[2];
|
|
12
|
+
const name = rawName.replace(/\s*\([^)]*\)\s*$/g, "").trim();
|
|
13
|
+
models.push({ id, name: name || id });
|
|
14
|
+
}
|
|
15
|
+
const byId = new Map();
|
|
16
|
+
for (const m of models)
|
|
17
|
+
byId.set(m.id, m);
|
|
18
|
+
return [...byId.values()];
|
|
19
|
+
}
|
|
20
|
+
export async function listCursorCliModels(args) {
|
|
21
|
+
const list = await run(args.agentBin, ["--list-models"], {
|
|
22
|
+
cwd: tmpdir(),
|
|
23
|
+
timeoutMs: args.timeoutMs,
|
|
24
|
+
});
|
|
25
|
+
if (list.code !== 0) {
|
|
26
|
+
throw new Error(`agent --list-models failed: ${list.stderr.trim()}`);
|
|
27
|
+
}
|
|
28
|
+
return parseCursorCliModels(list.stdout);
|
|
29
|
+
}
|
|
30
|
+
//# sourceMappingURL=cursor-cli.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cursor-cli.js","sourceRoot":"","sources":["../../src/lib/cursor-cli.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,SAAS,CAAC;AAEjC,OAAO,EAAE,GAAG,EAAE,MAAM,cAAc,CAAC;AAInC,MAAM,UAAU,oBAAoB,CAAC,MAAc;IACjD,MAAM,KAAK,GAAG,MAAM,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC;IAC1D,MAAM,MAAM,GAAqB,EAAE,CAAC;IAEpC,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,6CAA6C,CAAC,CAAC;QACxE,IAAI,CAAC,KAAK;YAAE,SAAS;QACrB,MAAM,EAAE,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;QACpB,MAAM,OAAO,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;QACzB,MAAM,IAAI,GAAG,OAAO,CAAC,OAAO,CAAC,mBAAmB,EAAE,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;QAC7D,MAAM,CAAC,IAAI,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,IAAI,IAAI,EAAE,EAAE,CAAC,CAAC;IACxC,CAAC;IAED,MAAM,IAAI,GAAG,IAAI,GAAG,EAA0B,CAAC;IAC/C,KAAK,MAAM,CAAC,IAAI,MAAM;QAAE,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;IAC1C,OAAO,CAAC,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC,CAAC;AAC5B,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,mBAAmB,CAAC,IAGzC;IACC,MAAM,IAAI,GAAG,MAAM,GAAG,CAAC,IAAI,CAAC,QAAQ,EAAE,CAAC,eAAe,CAAC,EAAE;QACvD,GAAG,EAAE,MAAM,EAAE;QACb,SAAS,EAAE,IAAI,CAAC,SAAS;KAC1B,CAAC,CAAC;IAEH,IAAI,IAAI,CAAC,IAAI,KAAK,CAAC,EAAE,CAAC;QACpB,MAAM,IAAI,KAAK,CAAC,+BAA+B,IAAI,CAAC,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;IACvE,CAAC;IAED,OAAO,oBAAoB,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;AAC3C,CAAC"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
export type CursorCliModel = {
|
|
2
|
+
id: string;
|
|
3
|
+
name: string;
|
|
4
|
+
};
|
|
5
|
+
export declare function parseCursorCliModels(output: string): CursorCliModel[];
|
|
6
|
+
export declare function listCursorCliModels(args: {
|
|
7
|
+
agentBin: string;
|
|
8
|
+
timeoutMs: number;
|
|
9
|
+
}): Promise<CursorCliModel[]>;
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { tmpdir } from "node:os";
|
|
2
|
+
import { run } from "./process.js";
|
|
3
|
+
export function parseCursorCliModels(output) {
|
|
4
|
+
const lines = output.split(/\r?\n/g).map((l) => l.trim());
|
|
5
|
+
const models = [];
|
|
6
|
+
for (const line of lines) {
|
|
7
|
+
const match = line.match(/^([A-Za-z0-9][A-Za-z0-9._:/-]*)\s+-\s+(.*)$/);
|
|
8
|
+
if (!match)
|
|
9
|
+
continue;
|
|
10
|
+
const id = match[1];
|
|
11
|
+
const rawName = match[2];
|
|
12
|
+
const name = rawName.replace(/\s*\([^)]*\)\s*$/g, "").trim();
|
|
13
|
+
models.push({ id, name: name || id });
|
|
14
|
+
}
|
|
15
|
+
const byId = new Map();
|
|
16
|
+
for (const m of models)
|
|
17
|
+
byId.set(m.id, m);
|
|
18
|
+
return [...byId.values()];
|
|
19
|
+
}
|
|
20
|
+
export async function listCursorCliModels(args) {
|
|
21
|
+
const list = await run(args.agentBin, ["--list-models"], {
|
|
22
|
+
cwd: tmpdir(),
|
|
23
|
+
timeoutMs: args.timeoutMs,
|
|
24
|
+
});
|
|
25
|
+
if (list.code !== 0) {
|
|
26
|
+
throw new Error(`agent --list-models failed: ${list.stderr.trim()}`);
|
|
27
|
+
}
|
|
28
|
+
return parseCursorCliModels(list.stdout);
|
|
29
|
+
}
|
|
30
|
+
//# sourceMappingURL=cursorCli.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cursorCli.js","sourceRoot":"","sources":["../../src/lib/cursorCli.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,SAAS,CAAC;AAEjC,OAAO,EAAE,GAAG,EAAE,MAAM,cAAc,CAAC;AAInC,MAAM,UAAU,oBAAoB,CAAC,MAAc;IACjD,MAAM,KAAK,GAAG,MAAM,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC;IAC1D,MAAM,MAAM,GAAqB,EAAE,CAAC;IAEpC,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,6CAA6C,CAAC,CAAC;QACxE,IAAI,CAAC,KAAK;YAAE,SAAS;QACrB,MAAM,EAAE,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;QACpB,MAAM,OAAO,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;QACzB,MAAM,IAAI,GAAG,OAAO,CAAC,OAAO,CAAC,mBAAmB,EAAE,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;QAC7D,MAAM,CAAC,IAAI,CAAC,EAAE,EAAE,EAAE,IAAI,EAAE,IAAI,IAAI,EAAE,EAAE,CAAC,CAAC;IACxC,CAAC;IAED,MAAM,IAAI,GAAG,IAAI,GAAG,EAA0B,CAAC;IAC/C,KAAK,MAAM,CAAC,IAAI,MAAM;QAAE,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;IAC1C,OAAO,CAAC,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC,CAAC;AAC5B,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,mBAAmB,CAAC,IAGzC;IACC,MAAM,IAAI,GAAG,MAAM,GAAG,CAAC,IAAI,CAAC,QAAQ,EAAE,CAAC,eAAe,CAAC,EAAE;QACvD,GAAG,EAAE,MAAM,EAAE;QACb,SAAS,EAAE,IAAI,CAAC,SAAS;KAC1B,CAAC,CAAC;IAEH,IAAI,IAAI,CAAC,IAAI,KAAK,CAAC,EAAE,CAAC;QACpB,MAAM,IAAI,KAAK,CAAC,+BAA+B,IAAI,CAAC,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;IACvE,CAAC;IAED,OAAO,oBAAoB,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;AAC3C,CAAC"}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
export type EnvSource = Record<string, string | undefined>;
|
|
2
|
+
export type EnvOptions = {
|
|
3
|
+
tailscale?: boolean;
|
|
4
|
+
env?: EnvSource;
|
|
5
|
+
cwd?: string;
|
|
6
|
+
platform?: NodeJS.Platform;
|
|
7
|
+
};
|
|
8
|
+
export type LoadedEnv = {
|
|
9
|
+
agentBin: string;
|
|
10
|
+
agentNode?: string;
|
|
11
|
+
agentScript?: string;
|
|
12
|
+
commandShell: string;
|
|
13
|
+
host: string;
|
|
14
|
+
port: number;
|
|
15
|
+
requiredKey?: string;
|
|
16
|
+
defaultModel: string;
|
|
17
|
+
force: boolean;
|
|
18
|
+
approveMcps: boolean;
|
|
19
|
+
strictModel: boolean;
|
|
20
|
+
workspace: string;
|
|
21
|
+
timeoutMs: number;
|
|
22
|
+
tlsCertPath?: string;
|
|
23
|
+
tlsKeyPath?: string;
|
|
24
|
+
sessionsLogPath: string;
|
|
25
|
+
chatOnlyWorkspace: boolean;
|
|
26
|
+
verbose: boolean;
|
|
27
|
+
/** When true, set maxMode in cli-config.json before each run (larger context, more tools). */
|
|
28
|
+
maxMode: boolean;
|
|
29
|
+
};
|
|
30
|
+
export type AgentCommand = {
|
|
31
|
+
command: string;
|
|
32
|
+
args: string[];
|
|
33
|
+
env: EnvSource;
|
|
34
|
+
windowsVerbatimArguments?: boolean;
|
|
35
|
+
/** Path to agent entry script (e.g. index.js). Set when using node+script so max-mode preflight can find config. */
|
|
36
|
+
agentScriptPath?: string;
|
|
37
|
+
/** Cursor config dir (cli-config.json). Set so CLI reads the same config preflight wrote to. */
|
|
38
|
+
configDir?: string;
|
|
39
|
+
};
|
|
40
|
+
export declare function loadEnvConfig(opts?: EnvOptions): LoadedEnv;
|
|
41
|
+
export declare function resolveAgentCommand(cmd: string, args: string[], opts?: EnvOptions): AgentCommand;
|
package/dist/lib/env.js
ADDED
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
import * as fs from "node:fs";
|
|
2
|
+
import * as path from "node:path";
|
|
3
|
+
function getEnvSource(env) {
|
|
4
|
+
return env ?? process.env;
|
|
5
|
+
}
|
|
6
|
+
function getCwd(cwd) {
|
|
7
|
+
return cwd ?? process.cwd();
|
|
8
|
+
}
|
|
9
|
+
function firstDefined(env, names) {
|
|
10
|
+
for (const name of names) {
|
|
11
|
+
const value = env[name];
|
|
12
|
+
if (value != null)
|
|
13
|
+
return value;
|
|
14
|
+
}
|
|
15
|
+
return undefined;
|
|
16
|
+
}
|
|
17
|
+
function envString(env, names) {
|
|
18
|
+
const value = firstDefined(env, names);
|
|
19
|
+
if (value == null)
|
|
20
|
+
return undefined;
|
|
21
|
+
const trimmed = value.trim();
|
|
22
|
+
return trimmed ? trimmed : undefined;
|
|
23
|
+
}
|
|
24
|
+
function envBool(env, names, defaultValue) {
|
|
25
|
+
const raw = envString(env, names);
|
|
26
|
+
if (raw == null)
|
|
27
|
+
return defaultValue;
|
|
28
|
+
const value = raw.toLowerCase();
|
|
29
|
+
if (value === "1" || value === "true" || value === "yes" || value === "on")
|
|
30
|
+
return true;
|
|
31
|
+
if (value === "0" || value === "false" || value === "no" || value === "off")
|
|
32
|
+
return false;
|
|
33
|
+
return defaultValue;
|
|
34
|
+
}
|
|
35
|
+
function envNumber(env, names, defaultValue) {
|
|
36
|
+
const raw = envString(env, names);
|
|
37
|
+
if (raw == null)
|
|
38
|
+
return defaultValue;
|
|
39
|
+
const value = Number(raw);
|
|
40
|
+
return Number.isFinite(value) ? value : defaultValue;
|
|
41
|
+
}
|
|
42
|
+
function normalizeModelId(raw) {
|
|
43
|
+
if (!raw)
|
|
44
|
+
return "auto";
|
|
45
|
+
const parts = raw.split("/");
|
|
46
|
+
return parts[parts.length - 1] || "auto";
|
|
47
|
+
}
|
|
48
|
+
function resolveAbsolutePath(raw, cwd) {
|
|
49
|
+
if (!raw)
|
|
50
|
+
return undefined;
|
|
51
|
+
return path.resolve(cwd, raw);
|
|
52
|
+
}
|
|
53
|
+
export function loadEnvConfig(opts = {}) {
|
|
54
|
+
const env = getEnvSource(opts.env);
|
|
55
|
+
const cwd = getCwd(opts.cwd);
|
|
56
|
+
const host = envString(env, ["CURSOR_BRIDGE_HOST"]) ?? (opts.tailscale ? "0.0.0.0" : "127.0.0.1");
|
|
57
|
+
const portValue = envNumber(env, ["CURSOR_BRIDGE_PORT"], 8765);
|
|
58
|
+
const port = Number.isFinite(portValue) && portValue > 0 ? portValue : 8765;
|
|
59
|
+
const sessionsLogPath = (() => {
|
|
60
|
+
const explicit = resolveAbsolutePath(envString(env, ["CURSOR_BRIDGE_SESSIONS_LOG"]), cwd);
|
|
61
|
+
if (explicit)
|
|
62
|
+
return explicit;
|
|
63
|
+
const home = envString(env, ["HOME", "USERPROFILE"]);
|
|
64
|
+
if (home)
|
|
65
|
+
return path.join(home, ".cursor-api-proxy", "sessions.log");
|
|
66
|
+
return path.join(cwd, "sessions.log");
|
|
67
|
+
})();
|
|
68
|
+
return {
|
|
69
|
+
agentBin: envString(env, ["CURSOR_AGENT_BIN", "CURSOR_CLI_BIN", "CURSOR_CLI_PATH"]) ?? "agent",
|
|
70
|
+
agentNode: envString(env, ["CURSOR_AGENT_NODE"]),
|
|
71
|
+
agentScript: envString(env, ["CURSOR_AGENT_SCRIPT"]),
|
|
72
|
+
commandShell: envString(env, ["COMSPEC"]) ?? "cmd.exe",
|
|
73
|
+
host,
|
|
74
|
+
port,
|
|
75
|
+
requiredKey: envString(env, ["CURSOR_BRIDGE_API_KEY"]),
|
|
76
|
+
defaultModel: normalizeModelId(envString(env, ["CURSOR_BRIDGE_DEFAULT_MODEL"])),
|
|
77
|
+
force: envBool(env, ["CURSOR_BRIDGE_FORCE"], false),
|
|
78
|
+
approveMcps: envBool(env, ["CURSOR_BRIDGE_APPROVE_MCPS"], false),
|
|
79
|
+
strictModel: envBool(env, ["CURSOR_BRIDGE_STRICT_MODEL"], true),
|
|
80
|
+
workspace: resolveAbsolutePath(envString(env, ["CURSOR_BRIDGE_WORKSPACE"]), cwd) ?? cwd,
|
|
81
|
+
timeoutMs: envNumber(env, ["CURSOR_BRIDGE_TIMEOUT_MS"], 300_000),
|
|
82
|
+
tlsCertPath: resolveAbsolutePath(envString(env, ["CURSOR_BRIDGE_TLS_CERT"]), cwd),
|
|
83
|
+
tlsKeyPath: resolveAbsolutePath(envString(env, ["CURSOR_BRIDGE_TLS_KEY"]), cwd),
|
|
84
|
+
sessionsLogPath,
|
|
85
|
+
chatOnlyWorkspace: envBool(env, ["CURSOR_BRIDGE_CHAT_ONLY_WORKSPACE"], true),
|
|
86
|
+
verbose: envBool(env, ["CURSOR_BRIDGE_VERBOSE"], false),
|
|
87
|
+
maxMode: envBool(env, ["CURSOR_BRIDGE_MAX_MODE"], false),
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
export function resolveAgentCommand(cmd, args, opts = {}) {
|
|
91
|
+
const env = getEnvSource(opts.env);
|
|
92
|
+
const loaded = loadEnvConfig(opts);
|
|
93
|
+
const platform = opts.platform ?? process.platform;
|
|
94
|
+
const cwd = getCwd(opts.cwd);
|
|
95
|
+
if (platform === "win32") {
|
|
96
|
+
if (loaded.agentNode && loaded.agentScript) {
|
|
97
|
+
const agentScriptPath = path.isAbsolute(loaded.agentScript)
|
|
98
|
+
? loaded.agentScript
|
|
99
|
+
: path.resolve(cwd, loaded.agentScript);
|
|
100
|
+
const agentDir = path.dirname(agentScriptPath);
|
|
101
|
+
const configDir = path.join(agentDir, "..", "data", "config");
|
|
102
|
+
const out = {
|
|
103
|
+
command: loaded.agentNode,
|
|
104
|
+
args: [loaded.agentScript, ...args],
|
|
105
|
+
env: { ...env, CURSOR_INVOKED_AS: "agent.cmd" },
|
|
106
|
+
agentScriptPath,
|
|
107
|
+
configDir: fs.existsSync(path.join(configDir, "cli-config.json")) ? configDir : undefined,
|
|
108
|
+
};
|
|
109
|
+
return out;
|
|
110
|
+
}
|
|
111
|
+
if (/\.cmd$/i.test(cmd)) {
|
|
112
|
+
const cmdResolved = path.resolve(cwd, cmd);
|
|
113
|
+
const dir = path.dirname(cmdResolved);
|
|
114
|
+
const nodeBin = path.join(dir, "node.exe");
|
|
115
|
+
const script = path.join(dir, "index.js");
|
|
116
|
+
if (fs.existsSync(nodeBin) && fs.existsSync(script)) {
|
|
117
|
+
const configDir = path.join(dir, "..", "data", "config");
|
|
118
|
+
return {
|
|
119
|
+
command: nodeBin,
|
|
120
|
+
args: [script, ...args],
|
|
121
|
+
env: { ...env, CURSOR_INVOKED_AS: "agent.cmd" },
|
|
122
|
+
agentScriptPath: script,
|
|
123
|
+
configDir: fs.existsSync(path.join(configDir, "cli-config.json")) ? configDir : undefined,
|
|
124
|
+
};
|
|
125
|
+
}
|
|
126
|
+
const quotedArgs = args.map((arg) => (arg.includes(" ") ? `"${arg}"` : arg)).join(" ");
|
|
127
|
+
const cmdLine = `""${cmd}" ${quotedArgs}"`;
|
|
128
|
+
return {
|
|
129
|
+
command: loaded.commandShell,
|
|
130
|
+
args: ["/d", "/s", "/c", cmdLine],
|
|
131
|
+
env,
|
|
132
|
+
windowsVerbatimArguments: true,
|
|
133
|
+
};
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
return { command: cmd, args, env };
|
|
137
|
+
}
|
|
138
|
+
//# sourceMappingURL=env.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"env.js","sourceRoot":"","sources":["../../src/lib/env.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import * as http from "node:http";
|
|
2
|
+
import type { BridgeConfig } from "../config.js";
|
|
3
|
+
export type AnthropicMessagesCtx = {
|
|
4
|
+
config: BridgeConfig;
|
|
5
|
+
lastRequestedModelRef: {
|
|
6
|
+
current?: string;
|
|
7
|
+
};
|
|
8
|
+
};
|
|
9
|
+
export declare function handleAnthropicMessages(req: http.IncomingMessage, res: http.ServerResponse, ctx: AnthropicMessagesCtx, rawBody: string, method: string, pathname: string, remoteAddress: string): Promise<void>;
|
|
@@ -0,0 +1,124 @@
|
|
|
1
|
+
import { randomUUID } from "node:crypto";
|
|
2
|
+
import { buildPromptFromAnthropicMessages } from "../anthropic.js";
|
|
3
|
+
import { buildAgentCmdArgs } from "../agent-cmd-args.js";
|
|
4
|
+
import { runAgentStream, runAgentSync } from "../agent-runner.js";
|
|
5
|
+
import { createStreamParser } from "../cli-stream-parser.js";
|
|
6
|
+
import { json, writeSseHeaders } from "../http.js";
|
|
7
|
+
import { resolveToCursorModel } from "../model-map.js";
|
|
8
|
+
import { normalizeModelId } from "../openai.js";
|
|
9
|
+
import { logAgentError, logTrafficRequest, logTrafficResponse, } from "../request-log.js";
|
|
10
|
+
import { resolveModel } from "../resolve-model.js";
|
|
11
|
+
import { resolveWorkspace } from "../workspace.js";
|
|
12
|
+
export async function handleAnthropicMessages(req, res, ctx, rawBody, method, pathname, remoteAddress) {
|
|
13
|
+
const { config, lastRequestedModelRef } = ctx;
|
|
14
|
+
const body = JSON.parse(rawBody || "{}");
|
|
15
|
+
const requested = normalizeModelId(body.model);
|
|
16
|
+
const model = resolveModel(requested, lastRequestedModelRef, config);
|
|
17
|
+
if (body.max_tokens == null || typeof body.max_tokens !== "number") {
|
|
18
|
+
json(res, 400, {
|
|
19
|
+
error: {
|
|
20
|
+
type: "invalid_request_error",
|
|
21
|
+
message: "max_tokens is required",
|
|
22
|
+
},
|
|
23
|
+
});
|
|
24
|
+
return;
|
|
25
|
+
}
|
|
26
|
+
const cursorModel = resolveToCursorModel(model) ?? model;
|
|
27
|
+
const prompt = buildPromptFromAnthropicMessages(body.messages, body.system);
|
|
28
|
+
const trafficMessages = [];
|
|
29
|
+
if (body.system) {
|
|
30
|
+
const sys = typeof body.system === "string"
|
|
31
|
+
? body.system
|
|
32
|
+
: body.system
|
|
33
|
+
.filter((p) => p.type === "text")
|
|
34
|
+
.map((p) => p.text ?? "")
|
|
35
|
+
.join("\n");
|
|
36
|
+
if (sys.trim())
|
|
37
|
+
trafficMessages.push({ role: "system", content: sys.trim() });
|
|
38
|
+
}
|
|
39
|
+
for (const m of body.messages ?? []) {
|
|
40
|
+
const text = typeof m.content === "string"
|
|
41
|
+
? m.content
|
|
42
|
+
: m.content
|
|
43
|
+
.filter((p) => p.type === "text")
|
|
44
|
+
.map((p) => p.text ?? "")
|
|
45
|
+
.join("");
|
|
46
|
+
if (text)
|
|
47
|
+
trafficMessages.push({ role: m.role, content: text });
|
|
48
|
+
}
|
|
49
|
+
logTrafficRequest(config.verbose, model ?? cursorModel, trafficMessages, !!body.stream);
|
|
50
|
+
const headerWs = req.headers["x-cursor-workspace"];
|
|
51
|
+
const { workspaceDir, tempDir } = resolveWorkspace(config, headerWs);
|
|
52
|
+
const cmdArgs = buildAgentCmdArgs(config, workspaceDir, cursorModel, prompt, !!body.stream);
|
|
53
|
+
const msgId = `msg_${randomUUID().replace(/-/g, "")}`;
|
|
54
|
+
if (body.stream) {
|
|
55
|
+
writeSseHeaders(res);
|
|
56
|
+
const writeEvent = (evt) => {
|
|
57
|
+
res.write(`data: ${JSON.stringify(evt)}\n\n`);
|
|
58
|
+
};
|
|
59
|
+
writeEvent({
|
|
60
|
+
type: "message_start",
|
|
61
|
+
message: {
|
|
62
|
+
id: msgId,
|
|
63
|
+
type: "message",
|
|
64
|
+
role: "assistant",
|
|
65
|
+
model: model ?? cursorModel,
|
|
66
|
+
content: [],
|
|
67
|
+
},
|
|
68
|
+
});
|
|
69
|
+
writeEvent({
|
|
70
|
+
type: "content_block_start",
|
|
71
|
+
index: 0,
|
|
72
|
+
content_block: { type: "text", text: "" },
|
|
73
|
+
});
|
|
74
|
+
let accumulated = "";
|
|
75
|
+
const parseLine = createStreamParser((text) => {
|
|
76
|
+
accumulated += text;
|
|
77
|
+
writeEvent({
|
|
78
|
+
type: "content_block_delta",
|
|
79
|
+
index: 0,
|
|
80
|
+
delta: { type: "text_delta", text },
|
|
81
|
+
});
|
|
82
|
+
}, () => {
|
|
83
|
+
logTrafficResponse(config.verbose, model ?? cursorModel, accumulated, true);
|
|
84
|
+
writeEvent({ type: "content_block_stop", index: 0 });
|
|
85
|
+
writeEvent({
|
|
86
|
+
type: "message_delta",
|
|
87
|
+
delta: { stop_reason: "end_turn" },
|
|
88
|
+
});
|
|
89
|
+
writeEvent({ type: "message_stop" });
|
|
90
|
+
});
|
|
91
|
+
runAgentStream(config, workspaceDir, cmdArgs, parseLine, tempDir)
|
|
92
|
+
.then(({ code, stderr: stderrOut }) => {
|
|
93
|
+
if (code !== 0) {
|
|
94
|
+
logAgentError(config.sessionsLogPath, method, pathname, remoteAddress, code, stderrOut);
|
|
95
|
+
}
|
|
96
|
+
res.end();
|
|
97
|
+
})
|
|
98
|
+
.catch((err) => {
|
|
99
|
+
console.error(`[${new Date().toISOString()}] Agent stream error:`, err);
|
|
100
|
+
res.end();
|
|
101
|
+
});
|
|
102
|
+
return;
|
|
103
|
+
}
|
|
104
|
+
const out = await runAgentSync(config, workspaceDir, cmdArgs, tempDir);
|
|
105
|
+
if (out.code !== 0) {
|
|
106
|
+
const errMsg = logAgentError(config.sessionsLogPath, method, pathname, remoteAddress, out.code, out.stderr);
|
|
107
|
+
json(res, 500, {
|
|
108
|
+
error: { type: "api_error", message: errMsg },
|
|
109
|
+
});
|
|
110
|
+
return;
|
|
111
|
+
}
|
|
112
|
+
const content = out.stdout.trim();
|
|
113
|
+
logTrafficResponse(config.verbose, model ?? cursorModel, content, false);
|
|
114
|
+
json(res, 200, {
|
|
115
|
+
id: msgId,
|
|
116
|
+
type: "message",
|
|
117
|
+
role: "assistant",
|
|
118
|
+
content: [{ type: "text", text: content }],
|
|
119
|
+
model: model ?? cursorModel,
|
|
120
|
+
stop_reason: "end_turn",
|
|
121
|
+
usage: { input_tokens: 0, output_tokens: 0 },
|
|
122
|
+
});
|
|
123
|
+
}
|
|
124
|
+
//# sourceMappingURL=anthropic-messages.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"anthropic-messages.js","sourceRoot":"","sources":["../../../src/lib/handlers/anthropic-messages.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import * as http from "node:http";
|
|
2
|
+
import type { BridgeConfig } from "../config.js";
|
|
3
|
+
export type ChatCompletionsCtx = {
|
|
4
|
+
config: BridgeConfig;
|
|
5
|
+
lastRequestedModelRef: {
|
|
6
|
+
current?: string;
|
|
7
|
+
};
|
|
8
|
+
};
|
|
9
|
+
export declare function handleChatCompletions(req: http.IncomingMessage, res: http.ServerResponse, ctx: ChatCompletionsCtx, rawBody: string, method: string, pathname: string, remoteAddress: string): Promise<void>;
|
|
@@ -0,0 +1,98 @@
|
|
|
1
|
+
import { randomUUID } from "node:crypto";
|
|
2
|
+
import { buildAgentCmdArgs } from "../agent-cmd-args.js";
|
|
3
|
+
import { runAgentStream, runAgentSync } from "../agent-runner.js";
|
|
4
|
+
import { createStreamParser } from "../cli-stream-parser.js";
|
|
5
|
+
import { json, writeSseHeaders } from "../http.js";
|
|
6
|
+
import { resolveToCursorModel } from "../model-map.js";
|
|
7
|
+
import { buildPromptFromMessages, normalizeModelId, } from "../openai.js";
|
|
8
|
+
import { logAgentError, logTrafficRequest, logTrafficResponse, } from "../request-log.js";
|
|
9
|
+
import { resolveModel } from "../resolve-model.js";
|
|
10
|
+
import { resolveWorkspace } from "../workspace.js";
|
|
11
|
+
export async function handleChatCompletions(req, res, ctx, rawBody, method, pathname, remoteAddress) {
|
|
12
|
+
const { config, lastRequestedModelRef } = ctx;
|
|
13
|
+
const body = JSON.parse(rawBody || "{}");
|
|
14
|
+
const requested = normalizeModelId(body.model);
|
|
15
|
+
const model = resolveModel(requested, lastRequestedModelRef, config);
|
|
16
|
+
const cursorModel = resolveToCursorModel(model) ?? model;
|
|
17
|
+
const prompt = buildPromptFromMessages(body.messages ?? []);
|
|
18
|
+
const trafficMessages = (body.messages ?? []).map((m) => {
|
|
19
|
+
const content = typeof m?.content === "string"
|
|
20
|
+
? m.content
|
|
21
|
+
: Array.isArray(m?.content)
|
|
22
|
+
? m.content
|
|
23
|
+
.filter((p) => p.type === "text")
|
|
24
|
+
.map((p) => p.text ?? "")
|
|
25
|
+
.join("")
|
|
26
|
+
: "";
|
|
27
|
+
return { role: String(m?.role ?? "user"), content };
|
|
28
|
+
});
|
|
29
|
+
logTrafficRequest(config.verbose, model ?? cursorModel, trafficMessages, !!body.stream);
|
|
30
|
+
const headerWs = req.headers["x-cursor-workspace"];
|
|
31
|
+
const { workspaceDir, tempDir } = resolveWorkspace(config, headerWs);
|
|
32
|
+
const cmdArgs = buildAgentCmdArgs(config, workspaceDir, cursorModel, prompt, !!body.stream);
|
|
33
|
+
const id = `chatcmpl_${randomUUID().replace(/-/g, "")}`;
|
|
34
|
+
const created = Math.floor(Date.now() / 1000);
|
|
35
|
+
if (body.stream) {
|
|
36
|
+
writeSseHeaders(res);
|
|
37
|
+
let accumulated = "";
|
|
38
|
+
const parseLine = createStreamParser((text) => {
|
|
39
|
+
accumulated += text;
|
|
40
|
+
res.write(`data: ${JSON.stringify({
|
|
41
|
+
id,
|
|
42
|
+
object: "chat.completion.chunk",
|
|
43
|
+
created,
|
|
44
|
+
model,
|
|
45
|
+
choices: [
|
|
46
|
+
{ index: 0, delta: { content: text }, finish_reason: null },
|
|
47
|
+
],
|
|
48
|
+
})}\n\n`);
|
|
49
|
+
}, () => {
|
|
50
|
+
logTrafficResponse(config.verbose, model ?? cursorModel, accumulated, true);
|
|
51
|
+
res.write(`data: ${JSON.stringify({
|
|
52
|
+
id,
|
|
53
|
+
object: "chat.completion.chunk",
|
|
54
|
+
created,
|
|
55
|
+
model,
|
|
56
|
+
choices: [{ index: 0, delta: {}, finish_reason: "stop" }],
|
|
57
|
+
})}\n\n`);
|
|
58
|
+
res.write("data: [DONE]\n\n");
|
|
59
|
+
});
|
|
60
|
+
runAgentStream(config, workspaceDir, cmdArgs, parseLine, tempDir)
|
|
61
|
+
.then(({ code, stderr: stderrOut }) => {
|
|
62
|
+
if (code !== 0) {
|
|
63
|
+
logAgentError(config.sessionsLogPath, method, pathname, remoteAddress, code, stderrOut);
|
|
64
|
+
}
|
|
65
|
+
res.end();
|
|
66
|
+
})
|
|
67
|
+
.catch((err) => {
|
|
68
|
+
console.error(`[${new Date().toISOString()}] Agent stream error:`, err);
|
|
69
|
+
res.end();
|
|
70
|
+
});
|
|
71
|
+
return;
|
|
72
|
+
}
|
|
73
|
+
const out = await runAgentSync(config, workspaceDir, cmdArgs, tempDir);
|
|
74
|
+
if (out.code !== 0) {
|
|
75
|
+
const errMsg = logAgentError(config.sessionsLogPath, method, pathname, remoteAddress, out.code, out.stderr);
|
|
76
|
+
json(res, 500, {
|
|
77
|
+
error: { message: errMsg, code: "cursor_cli_error" },
|
|
78
|
+
});
|
|
79
|
+
return;
|
|
80
|
+
}
|
|
81
|
+
const content = out.stdout.trim();
|
|
82
|
+
logTrafficResponse(config.verbose, model ?? cursorModel, content, false);
|
|
83
|
+
json(res, 200, {
|
|
84
|
+
id,
|
|
85
|
+
object: "chat.completion",
|
|
86
|
+
created,
|
|
87
|
+
model,
|
|
88
|
+
choices: [
|
|
89
|
+
{
|
|
90
|
+
index: 0,
|
|
91
|
+
message: { role: "assistant", content },
|
|
92
|
+
finish_reason: "stop",
|
|
93
|
+
},
|
|
94
|
+
],
|
|
95
|
+
usage: { prompt_tokens: 0, completion_tokens: 0, total_tokens: 0 },
|
|
96
|
+
});
|
|
97
|
+
}
|
|
98
|
+
//# sourceMappingURL=chat-completions.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chat-completions.js","sourceRoot":"","sources":["../../../src/lib/handlers/chat-completions.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { json } from "../http.js";
|
|
2
|
+
export function handleHealth(res, opts) {
|
|
3
|
+
const { version, config } = opts;
|
|
4
|
+
json(res, 200, {
|
|
5
|
+
ok: true,
|
|
6
|
+
version,
|
|
7
|
+
workspace: config.workspace,
|
|
8
|
+
mode: config.mode,
|
|
9
|
+
defaultModel: config.defaultModel,
|
|
10
|
+
force: config.force,
|
|
11
|
+
approveMcps: config.approveMcps,
|
|
12
|
+
strictModel: config.strictModel,
|
|
13
|
+
});
|
|
14
|
+
}
|
|
15
|
+
//# sourceMappingURL=health.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"health.js","sourceRoot":"","sources":["../../../src/lib/handlers/health.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;AAOlC,MAAM,UAAU,YAAY,CAC1B,GAAwB,EACxB,IAAuB;IAEvB,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;IACjC,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE;QACb,EAAE,EAAE,IAAI;QACR,OAAO;QACP,SAAS,EAAE,MAAM,CAAC,SAAS;QAC3B,IAAI,EAAE,MAAM,CAAC,IAAI;QACjB,YAAY,EAAE,MAAM,CAAC,YAAY;QACjC,KAAK,EAAE,MAAM,CAAC,KAAK;QACnB,WAAW,EAAE,MAAM,CAAC,WAAW;QAC/B,WAAW,EAAE,MAAM,CAAC,WAAW;KAChC,CAAC,CAAC;AACL,CAAC"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import * as http from "node:http";
|
|
2
|
+
import type { BridgeConfig } from "../config.js";
|
|
3
|
+
import type { CursorCliModel } from "../cursor-cli.js";
|
|
4
|
+
export type ModelCache = {
|
|
5
|
+
at: number;
|
|
6
|
+
models: CursorCliModel[];
|
|
7
|
+
};
|
|
8
|
+
export type HandleModelsOpts = {
|
|
9
|
+
config: BridgeConfig;
|
|
10
|
+
modelCacheRef: {
|
|
11
|
+
current?: ModelCache;
|
|
12
|
+
};
|
|
13
|
+
};
|
|
14
|
+
export declare function handleModels(res: http.ServerResponse, opts: HandleModelsOpts): Promise<void>;
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { listCursorCliModels } from "../cursor-cli.js";
|
|
2
|
+
import { json } from "../http.js";
|
|
3
|
+
import { getAnthropicModelAliases } from "../model-map.js";
|
|
4
|
+
const MODEL_CACHE_TTL_MS = 5 * 60_000;
|
|
5
|
+
export async function handleModels(res, opts) {
|
|
6
|
+
const { config, modelCacheRef } = opts;
|
|
7
|
+
const now = Date.now();
|
|
8
|
+
if (!modelCacheRef.current ||
|
|
9
|
+
now - modelCacheRef.current.at > MODEL_CACHE_TTL_MS) {
|
|
10
|
+
const models = await listCursorCliModels({
|
|
11
|
+
agentBin: config.agentBin,
|
|
12
|
+
timeoutMs: 60_000,
|
|
13
|
+
});
|
|
14
|
+
modelCacheRef.current = { at: now, models };
|
|
15
|
+
}
|
|
16
|
+
const models = modelCacheRef.current.models;
|
|
17
|
+
const cursorModels = models.map((m) => ({
|
|
18
|
+
id: m.id,
|
|
19
|
+
object: "model",
|
|
20
|
+
owned_by: "cursor",
|
|
21
|
+
name: m.name,
|
|
22
|
+
}));
|
|
23
|
+
const anthropicAliases = getAnthropicModelAliases(models.map((m) => m.id)).map((a) => ({
|
|
24
|
+
id: a.id,
|
|
25
|
+
object: "model",
|
|
26
|
+
owned_by: "cursor",
|
|
27
|
+
name: a.name,
|
|
28
|
+
}));
|
|
29
|
+
json(res, 200, {
|
|
30
|
+
object: "list",
|
|
31
|
+
data: [...cursorModels, ...anthropicAliases],
|
|
32
|
+
});
|
|
33
|
+
}
|
|
34
|
+
//# sourceMappingURL=models.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"models.js","sourceRoot":"","sources":["../../../src/lib/handlers/models.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AACvD,OAAO,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;AAClC,OAAO,EAAE,wBAAwB,EAAE,MAAM,iBAAiB,CAAC;AAE3D,MAAM,kBAAkB,GAAG,CAAC,GAAG,MAAM,CAAC;AAStC,MAAM,CAAC,KAAK,UAAU,YAAY,CAChC,GAAwB,EACxB,IAAsB;IAEtB,MAAM,EAAE,MAAM,EAAE,aAAa,EAAE,GAAG,IAAI,CAAC;IACvC,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;IACvB,IACE,CAAC,aAAa,CAAC,OAAO;QACtB,GAAG,GAAG,aAAa,CAAC,OAAO,CAAC,EAAE,GAAG,kBAAkB,EACnD,CAAC;QACD,MAAM,MAAM,GAAG,MAAM,mBAAmB,CAAC;YACvC,QAAQ,EAAE,MAAM,CAAC,QAAQ;YACzB,SAAS,EAAE,MAAM;SAClB,CAAC,CAAC;QACH,aAAa,CAAC,OAAO,GAAG,EAAE,EAAE,EAAE,GAAG,EAAE,MAAM,EAAE,CAAC;IAC9C,CAAC;IAED,MAAM,MAAM,GAAG,aAAa,CAAC,OAAO,CAAC,MAAM,CAAC;IAC5C,MAAM,YAAY,GAAG,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;QACtC,EAAE,EAAE,CAAC,CAAC,EAAE;QACR,MAAM,EAAE,OAAgB;QACxB,QAAQ,EAAE,QAAiB;QAC3B,IAAI,EAAE,CAAC,CAAC,IAAI;KACb,CAAC,CAAC,CAAC;IACJ,MAAM,gBAAgB,GAAG,wBAAwB,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,GAAG,CAC5E,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;QACN,EAAE,EAAE,CAAC,CAAC,EAAE;QACR,MAAM,EAAE,OAAgB;QACxB,QAAQ,EAAE,QAAiB;QAC3B,IAAI,EAAE,CAAC,CAAC,IAAI;KACb,CAAC,CACH,CAAC;IAEF,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE;QACb,MAAM,EAAE,MAAM;QACd,IAAI,EAAE,CAAC,GAAG,YAAY,EAAE,GAAG,gBAAgB,CAAC;KAC7C,CAAC,CAAC;AACL,CAAC"}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import * as http from "node:http";
|
|
2
|
+
export declare function extractBearerToken(req: http.IncomingMessage): string | undefined;
|
|
3
|
+
export declare function json(res: http.ServerResponse, status: number, body: unknown): void;
|
|
4
|
+
export declare function writeSseHeaders(res: http.ServerResponse): void;
|
|
5
|
+
export declare function readBody(req: http.IncomingMessage): Promise<string>;
|