fix: switch from SDK to CLI wrapper (npx claude-code) for auth compatibility
This commit is contained in:
+53
-36
@@ -1,52 +1,69 @@
|
|||||||
import { query } from "@anthropic-ai/claude-agent-sdk";
|
import { spawn } from "child_process";
|
||||||
|
|
||||||
export interface ClaudeResult {
|
export interface ClaudeResult {
|
||||||
sessionId: string;
|
sessionId: string;
|
||||||
result: string;
|
result: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
interface CliJsonResult {
|
||||||
|
result?: string;
|
||||||
|
session_id?: string;
|
||||||
|
is_error?: boolean;
|
||||||
|
}
|
||||||
|
|
||||||
|
function runClaude(args: string[], cwd: string): Promise<string> {
|
||||||
|
return new Promise((resolve, reject) => {
|
||||||
|
const proc = spawn("npx", ["--yes", "@anthropic-ai/claude-code", ...args], {
|
||||||
|
cwd,
|
||||||
|
shell: true,
|
||||||
|
env: { ...process.env },
|
||||||
|
});
|
||||||
|
|
||||||
|
let stdout = "";
|
||||||
|
let stderr = "";
|
||||||
|
|
||||||
|
proc.stdout.on("data", (data: Buffer) => {
|
||||||
|
stdout += data.toString();
|
||||||
|
});
|
||||||
|
|
||||||
|
proc.stderr.on("data", (data: Buffer) => {
|
||||||
|
stderr += data.toString();
|
||||||
|
});
|
||||||
|
|
||||||
|
proc.on("close", (code: number | null) => {
|
||||||
|
if (code !== 0 && !stdout) {
|
||||||
|
reject(new Error(stderr || `claude exited with code ${code}`));
|
||||||
|
} else {
|
||||||
|
resolve(stdout);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
proc.on("error", reject);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
export class ClaudeService {
|
export class ClaudeService {
|
||||||
async createSession(prompt: string, cwd: string): Promise<ClaudeResult> {
|
async createSession(prompt: string, cwd: string): Promise<ClaudeResult> {
|
||||||
let sessionId = "";
|
const raw = await runClaude(
|
||||||
let result = "";
|
["-p", prompt, "--output-format", "json", "--dangerously-skip-permissions"],
|
||||||
|
cwd,
|
||||||
|
);
|
||||||
|
|
||||||
for await (const message of query({
|
const parsed = JSON.parse(raw.trim().split("\n").pop()!) as CliJsonResult;
|
||||||
prompt,
|
|
||||||
options: {
|
|
||||||
cwd,
|
|
||||||
permissionMode: "bypassPermissions",
|
|
||||||
allowedTools: [
|
|
||||||
"Read", "Write", "Edit", "Bash", "Glob", "Grep",
|
|
||||||
"WebSearch", "WebFetch", "Agent",
|
|
||||||
],
|
|
||||||
},
|
|
||||||
})) {
|
|
||||||
if (message.type === "system" && message.subtype === "init") {
|
|
||||||
sessionId = message.session_id;
|
|
||||||
}
|
|
||||||
if ("result" in message && typeof message.result === "string") {
|
|
||||||
result = message.result;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return { sessionId, result };
|
return {
|
||||||
|
sessionId: parsed.session_id ?? "",
|
||||||
|
result: parsed.result ?? "",
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
async sendMessage(prompt: string, sessionId: string): Promise<string> {
|
async sendMessage(prompt: string, sessionId: string): Promise<string> {
|
||||||
let result = "";
|
const raw = await runClaude(
|
||||||
|
["-p", prompt, "--output-format", "json", "--resume", sessionId, "--dangerously-skip-permissions"],
|
||||||
|
process.cwd(),
|
||||||
|
);
|
||||||
|
|
||||||
for await (const message of query({
|
const parsed = JSON.parse(raw.trim().split("\n").pop()!) as CliJsonResult;
|
||||||
prompt,
|
return parsed.result ?? "";
|
||||||
options: {
|
|
||||||
resume: sessionId,
|
|
||||||
permissionMode: "bypassPermissions",
|
|
||||||
},
|
|
||||||
})) {
|
|
||||||
if ("result" in message && typeof message.result === "string") {
|
|
||||||
result = message.result;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user