lazycodex-ai 5.1.41 → 5.1.43
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.de.md +118 -0
- package/README.es.md +118 -0
- package/README.fr.md +118 -0
- package/README.it.md +118 -0
- package/README.ja.md +2 -1
- package/README.ko.md +2 -1
- package/README.md +3 -2
- package/README.pt-br.md +118 -0
- package/README.ru.md +2 -1
- package/README.zh-cn.md +2 -1
- package/dist/cli/index.js +187 -39
- package/dist/cli/service-auth/cli-keystore.fixture.d.ts +1 -7
- package/dist/cli/service-auth/index.d.ts +3 -0
- package/dist/cli/service-auth/keystore.d.ts +8 -2
- package/dist/cli/service-auth/secret-service-lock.d.ts +4 -0
- package/dist/cli/service-auth/session.d.ts +7 -1
- package/dist/cli-node/index.js +187 -39
- package/package.json +1 -1
- package/packages/lsp-daemon/dist/cli.js +363 -35
- package/packages/lsp-daemon/dist/client.js +341 -13
- package/packages/lsp-daemon/dist/index.js +344 -16
- package/packages/lsp-tools-mcp/dist/cli.js +333 -5
- package/packages/lsp-tools-mcp/dist/mcp.js +333 -5
- package/packages/lsp-tools-mcp/dist/tools.js +333 -5
- package/packages/omo-codex/plugin/.codex-plugin/plugin.json +1 -1
- package/packages/omo-codex/plugin/components/bootstrap/dist/cli.js +68 -9
- package/packages/omo-codex/plugin/components/bootstrap/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/bootstrap/package.json +1 -1
- package/packages/omo-codex/plugin/components/comment-checker/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/comment-checker/package.json +1 -1
- package/packages/omo-codex/plugin/components/git-bash/hooks/hooks.json +2 -2
- package/packages/omo-codex/plugin/components/git-bash/package.json +1 -1
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/lazycodex-executor-verify/package.json +1 -1
- package/packages/omo-codex/plugin/components/lsp/dist/.omo-runtime-manifest.json +3 -3
- package/packages/omo-codex/plugin/components/lsp/dist/cli.js +358 -36
- package/packages/omo-codex/plugin/components/lsp/hooks/hooks.json +2 -2
- package/packages/omo-codex/plugin/components/lsp/package.json +1 -1
- package/packages/omo-codex/plugin/components/rules/hooks/hooks.json +4 -4
- package/packages/omo-codex/plugin/components/rules/package.json +1 -1
- package/packages/omo-codex/plugin/components/teammode/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/teammode/package.json +1 -1
- package/packages/omo-codex/plugin/components/telemetry/dist/cli.js +2 -0
- package/packages/omo-codex/plugin/components/telemetry/dist/posthog.js +2 -0
- package/packages/omo-codex/plugin/components/telemetry/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/telemetry/package.json +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/ultrawork/package.json +1 -1
- package/packages/omo-codex/plugin/components/ulw-execute-continuation/hooks/hooks.json +1 -1
- package/packages/omo-codex/plugin/components/ulw-execute-continuation/package.json +1 -1
- package/packages/omo-codex/plugin/components/ulw-loop/hooks/hooks.json +5 -5
- package/packages/omo-codex/plugin/components/ulw-loop/package.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-git-bash-mcp-reminder.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-lsp-diagnostics-cache.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-compact-resetting-project-rule-cache.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-comments.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-lsp-diagnostics.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-checking-thread-title-hygiene.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-matching-project-rules.json +1 -1
- package/packages/omo-codex/plugin/hooks/post-tool-use-recording-spawn-admission.json +1 -1
- package/packages/omo-codex/plugin/hooks/pre-tool-use-enforcing-unlimited-goal-budget.json +1 -1
- package/packages/omo-codex/plugin/hooks/pre-tool-use-guarding-ulw-loop-spawns.json +1 -1
- package/packages/omo-codex/plugin/hooks/pre-tool-use-recommending-git-bash-mcp.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-checking-auto-update.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-checking-bootstrap-provisioning.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-loading-project-rules.json +1 -1
- package/packages/omo-codex/plugin/hooks/session-start-recording-session-telemetry.json +1 -1
- package/packages/omo-codex/plugin/hooks/stop-checking-ulw-execute-continuation.json +1 -1
- package/packages/omo-codex/plugin/hooks/stop-checking-ulw-loop-resume.json +1 -1
- package/packages/omo-codex/plugin/hooks/subagent-stop-verifying-lazycodex-executor-evidence.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-checking-ultrawork-trigger.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-checking-ulw-loop-steering.json +1 -1
- package/packages/omo-codex/plugin/hooks/user-prompt-submit-loading-project-rules.json +1 -1
- package/packages/omo-codex/plugin/package-lock.json +17 -12
- package/packages/omo-codex/plugin/package.json +1 -1
- package/packages/omo-codex/plugin/skills/browser/runtime/omowright/manifest.json +1 -1
- package/packages/omo-codex/scripts/install-dist/install-local.mjs +72 -11
- package/packages/shared-skills/skills/browser/runtime/omowright/manifest.json +1 -1
|
@@ -445,8 +445,8 @@ function parseEndpoint(value) {
|
|
|
445
445
|
}
|
|
446
446
|
|
|
447
447
|
// src/proxy.ts
|
|
448
|
-
import { existsSync as
|
|
449
|
-
import { basename as basename4, delimiter as delimiter4, dirname as
|
|
448
|
+
import { existsSync as existsSync15, realpathSync as realpathSync6 } from "node:fs";
|
|
449
|
+
import { basename as basename4, delimiter as delimiter4, dirname as dirname14, isAbsolute as isAbsolute6 } from "node:path";
|
|
450
450
|
// ../mcp-stdio-core/src/responses.ts
|
|
451
451
|
function successResponse(id, result) {
|
|
452
452
|
return { jsonrpc: "2.0", id, result };
|
|
@@ -5370,6 +5370,321 @@ function missingDependencyAvailability(error) {
|
|
|
5370
5370
|
}
|
|
5371
5371
|
}
|
|
5372
5372
|
|
|
5373
|
+
// ../lsp-core/src/lsp/bun-command-output.ts
|
|
5374
|
+
import { resolve as resolve10 } from "node:path";
|
|
5375
|
+
var TSC_LINE = /^(.+?)\((\d+),(\d+)\): (error|warning|message) (TS\d+): (.*)$/;
|
|
5376
|
+
var TSC_SEVERITY = { error: 1, warning: 2, message: 3 };
|
|
5377
|
+
function parseBunCheckOutput(stdout, cwd) {
|
|
5378
|
+
const results = [];
|
|
5379
|
+
for (const line of stdout.split(/\r?\n/)) {
|
|
5380
|
+
const match = TSC_LINE.exec(line);
|
|
5381
|
+
if (match) {
|
|
5382
|
+
const [, path, lineNumber, column, severity, code, message] = match;
|
|
5383
|
+
const start = { line: Number(lineNumber) - 1, character: Number(column) - 1 };
|
|
5384
|
+
results.push({
|
|
5385
|
+
file: resolve10(cwd, path ?? ""),
|
|
5386
|
+
diagnostic: {
|
|
5387
|
+
range: { start, end: start },
|
|
5388
|
+
severity: TSC_SEVERITY[severity ?? "error"] ?? 1,
|
|
5389
|
+
code: code ?? "",
|
|
5390
|
+
source: "bun check",
|
|
5391
|
+
message: message ?? ""
|
|
5392
|
+
}
|
|
5393
|
+
});
|
|
5394
|
+
continue;
|
|
5395
|
+
}
|
|
5396
|
+
const previous = results[results.length - 1];
|
|
5397
|
+
if (previous !== undefined && /^\s+\S/.test(line)) {
|
|
5398
|
+
previous.diagnostic.message = `${previous.diagnostic.message}
|
|
5399
|
+
${line.trim()}`;
|
|
5400
|
+
}
|
|
5401
|
+
}
|
|
5402
|
+
return results;
|
|
5403
|
+
}
|
|
5404
|
+
function parseBunLintJson(stdout) {
|
|
5405
|
+
let parsed;
|
|
5406
|
+
try {
|
|
5407
|
+
parsed = JSON.parse(stdout);
|
|
5408
|
+
} catch {
|
|
5409
|
+
return;
|
|
5410
|
+
}
|
|
5411
|
+
if (!Array.isArray(parsed))
|
|
5412
|
+
return;
|
|
5413
|
+
const results = [];
|
|
5414
|
+
for (const entry of parsed) {
|
|
5415
|
+
if (entry === null || typeof entry !== "object")
|
|
5416
|
+
continue;
|
|
5417
|
+
const filePath = entry.filePath;
|
|
5418
|
+
const messages = entry.messages;
|
|
5419
|
+
if (typeof filePath !== "string" || !Array.isArray(messages))
|
|
5420
|
+
continue;
|
|
5421
|
+
for (const raw of messages) {
|
|
5422
|
+
const start = { line: Math.max(0, (raw.line ?? 1) - 1), character: Math.max(0, (raw.column ?? 1) - 1) };
|
|
5423
|
+
const end = {
|
|
5424
|
+
line: raw.endLine === undefined ? start.line : Math.max(0, raw.endLine - 1),
|
|
5425
|
+
character: raw.endColumn === undefined ? start.character : Math.max(0, raw.endColumn - 1)
|
|
5426
|
+
};
|
|
5427
|
+
results.push({
|
|
5428
|
+
file: filePath,
|
|
5429
|
+
diagnostic: {
|
|
5430
|
+
range: { start, end },
|
|
5431
|
+
severity: raw.severity === 2 ? 1 : 2,
|
|
5432
|
+
...raw.ruleId ? { code: raw.ruleId } : {},
|
|
5433
|
+
source: "bun lint",
|
|
5434
|
+
message: raw.message ?? ""
|
|
5435
|
+
}
|
|
5436
|
+
});
|
|
5437
|
+
}
|
|
5438
|
+
}
|
|
5439
|
+
return results;
|
|
5440
|
+
}
|
|
5441
|
+
|
|
5442
|
+
// ../lsp-core/src/lsp/bun-project-checks.ts
|
|
5443
|
+
import { spawn as spawn2 } from "node:child_process";
|
|
5444
|
+
import { existsSync as existsSync13, mkdtempSync, readFileSync as readFileSync8, rmSync as rmSync2, statSync as statSync5, writeFileSync as writeFileSync3 } from "node:fs";
|
|
5445
|
+
import { homedir as homedir2, tmpdir } from "node:os";
|
|
5446
|
+
import { dirname as dirname12, join as join8, resolve as resolve11 } from "node:path";
|
|
5447
|
+
var BUN_LOCKFILES = ["bun.lock", "bun.lockb", "bunfig.toml"];
|
|
5448
|
+
var RUNNABLE_EXTENSIONS = [".tsx", ".ts", ".jsx", ".cts", ".cjs", ".js", ".mjs", ".mts"];
|
|
5449
|
+
var BIN_SUFFIXES = process.platform === "win32" ? [".exe", ".bunx", ".cmd", ""] : [""];
|
|
5450
|
+
var PROBE_TIMEOUT_MS = 1e4;
|
|
5451
|
+
var UNFORMATTED_PROBE = `const a=1
|
|
5452
|
+
`;
|
|
5453
|
+
var probeCache = new Map;
|
|
5454
|
+
function findBunProjectRoot(start, home = homedir2()) {
|
|
5455
|
+
const stopAt = resolve11(home);
|
|
5456
|
+
let dir = resolve11(start);
|
|
5457
|
+
for (;; ) {
|
|
5458
|
+
if (dir === stopAt)
|
|
5459
|
+
return;
|
|
5460
|
+
if (BUN_LOCKFILES.some((name) => existsSync13(join8(dir, name))))
|
|
5461
|
+
return dir;
|
|
5462
|
+
if (packageManagerIsBun(join8(dir, "package.json")))
|
|
5463
|
+
return dir;
|
|
5464
|
+
if (existsSync13(join8(dir, ".git")))
|
|
5465
|
+
return;
|
|
5466
|
+
const parent = dirname12(dir);
|
|
5467
|
+
if (parent === dir)
|
|
5468
|
+
return;
|
|
5469
|
+
dir = parent;
|
|
5470
|
+
}
|
|
5471
|
+
}
|
|
5472
|
+
function packageManagerIsBun(packageJsonPath) {
|
|
5473
|
+
const manifest = readJsonObject(packageJsonPath);
|
|
5474
|
+
const packageManager = manifest?.["packageManager"];
|
|
5475
|
+
return typeof packageManager === "string" && packageManager.startsWith("bun@");
|
|
5476
|
+
}
|
|
5477
|
+
function readJsonObject(path) {
|
|
5478
|
+
if (!existsSync13(path))
|
|
5479
|
+
return;
|
|
5480
|
+
try {
|
|
5481
|
+
const parsed = JSON.parse(readFileSync8(path, "utf8"));
|
|
5482
|
+
return parsed !== null && typeof parsed === "object" && !Array.isArray(parsed) ? parsed : undefined;
|
|
5483
|
+
} catch {
|
|
5484
|
+
return;
|
|
5485
|
+
}
|
|
5486
|
+
}
|
|
5487
|
+
function isFile(path) {
|
|
5488
|
+
try {
|
|
5489
|
+
return statSync5(path).isFile();
|
|
5490
|
+
} catch {
|
|
5491
|
+
return false;
|
|
5492
|
+
}
|
|
5493
|
+
}
|
|
5494
|
+
function isDirectory(path) {
|
|
5495
|
+
try {
|
|
5496
|
+
return statSync5(path).isDirectory();
|
|
5497
|
+
} catch {
|
|
5498
|
+
return false;
|
|
5499
|
+
}
|
|
5500
|
+
}
|
|
5501
|
+
function projectShadowsBunCommand(command, cwd) {
|
|
5502
|
+
const packageJsonDir = nearestPackageJsonDir(cwd);
|
|
5503
|
+
if (packageJsonDir !== undefined) {
|
|
5504
|
+
const scripts = readJsonObject(join8(packageJsonDir, "package.json"))?.["scripts"];
|
|
5505
|
+
if (scripts !== null && typeof scripts === "object" && typeof scripts[command] === "string") {
|
|
5506
|
+
return true;
|
|
5507
|
+
}
|
|
5508
|
+
}
|
|
5509
|
+
if (command === "check")
|
|
5510
|
+
return false;
|
|
5511
|
+
const base = join8(cwd, command);
|
|
5512
|
+
if (isFile(base) || RUNNABLE_EXTENSIONS.some((extension) => isFile(`${base}${extension}`)))
|
|
5513
|
+
return true;
|
|
5514
|
+
if (isDirectory(base) && (isFile(join8(base, "package.json")) || RUNNABLE_EXTENSIONS.some((extension) => isFile(join8(base, `index${extension}`))))) {
|
|
5515
|
+
return true;
|
|
5516
|
+
}
|
|
5517
|
+
let dir = resolve11(cwd);
|
|
5518
|
+
for (;; ) {
|
|
5519
|
+
if (BIN_SUFFIXES.some((suffix) => existsSync13(join8(dir, "node_modules", ".bin", `${command}${suffix}`))))
|
|
5520
|
+
return true;
|
|
5521
|
+
const parent = dirname12(dir);
|
|
5522
|
+
if (parent === dir)
|
|
5523
|
+
return false;
|
|
5524
|
+
dir = parent;
|
|
5525
|
+
}
|
|
5526
|
+
}
|
|
5527
|
+
function nearestPackageJsonDir(start) {
|
|
5528
|
+
let dir = resolve11(start);
|
|
5529
|
+
for (;; ) {
|
|
5530
|
+
if (existsSync13(join8(dir, "package.json")))
|
|
5531
|
+
return dir;
|
|
5532
|
+
const parent = dirname12(dir);
|
|
5533
|
+
if (parent === dir)
|
|
5534
|
+
return;
|
|
5535
|
+
dir = parent;
|
|
5536
|
+
}
|
|
5537
|
+
}
|
|
5538
|
+
function binaryIdentity(bunPath) {
|
|
5539
|
+
try {
|
|
5540
|
+
const stats = statSync5(bunPath);
|
|
5541
|
+
return `${stats.mtimeMs}:${stats.size}`;
|
|
5542
|
+
} catch {
|
|
5543
|
+
return "missing";
|
|
5544
|
+
}
|
|
5545
|
+
}
|
|
5546
|
+
function bunHasCommand(bunPath, command, timeoutMs = PROBE_TIMEOUT_MS) {
|
|
5547
|
+
const key = `${bunPath}\x00${binaryIdentity(bunPath)}\x00${command}`;
|
|
5548
|
+
const cached = probeCache.get(key);
|
|
5549
|
+
if (cached !== undefined)
|
|
5550
|
+
return cached;
|
|
5551
|
+
const probe = probeOnce(bunPath, command, timeoutMs).then((answer) => {
|
|
5552
|
+
if (answer === undefined)
|
|
5553
|
+
probeCache.delete(key);
|
|
5554
|
+
return answer === true;
|
|
5555
|
+
});
|
|
5556
|
+
probeCache.set(key, probe);
|
|
5557
|
+
return probe;
|
|
5558
|
+
}
|
|
5559
|
+
async function probeOnce(bunPath, command, timeoutMs) {
|
|
5560
|
+
const emptyDir = mkdtempSync(join8(tmpdir(), "omo-bun-probe-"));
|
|
5561
|
+
const timeout = AbortSignal.timeout(timeoutMs);
|
|
5562
|
+
try {
|
|
5563
|
+
const help = await runBunCommand(bunPath, [command, "--help"], emptyDir, timeout);
|
|
5564
|
+
if (help.exitCode === null)
|
|
5565
|
+
return;
|
|
5566
|
+
if (help.exitCode !== 0)
|
|
5567
|
+
return false;
|
|
5568
|
+
if (command !== "format")
|
|
5569
|
+
return true;
|
|
5570
|
+
const probeFile = join8(emptyDir, "probe.ts");
|
|
5571
|
+
writeFileSync3(probeFile, UNFORMATTED_PROBE);
|
|
5572
|
+
const write = await runBunCommand(bunPath, ["format", "--write", "probe.ts"], emptyDir, timeout);
|
|
5573
|
+
if (write.exitCode === null)
|
|
5574
|
+
return;
|
|
5575
|
+
return write.exitCode === 0 && readFileSync8(probeFile, "utf8") !== UNFORMATTED_PROBE;
|
|
5576
|
+
} catch {
|
|
5577
|
+
return;
|
|
5578
|
+
} finally {
|
|
5579
|
+
rmSync2(emptyDir, { recursive: true, force: true });
|
|
5580
|
+
}
|
|
5581
|
+
}
|
|
5582
|
+
async function resolveBunProjectCommand(command, cwd, options = {}) {
|
|
5583
|
+
if (findBunProjectRoot(cwd, options.homeDir) === undefined)
|
|
5584
|
+
return;
|
|
5585
|
+
if (projectShadowsBunCommand(command, cwd))
|
|
5586
|
+
return;
|
|
5587
|
+
const bunPath = (options.resolveBun ?? defaultResolveBun)(cwd);
|
|
5588
|
+
if (!bunPath)
|
|
5589
|
+
return;
|
|
5590
|
+
return await bunHasCommand(bunPath, command) ? bunPath : undefined;
|
|
5591
|
+
}
|
|
5592
|
+
function defaultResolveBun(cwd) {
|
|
5593
|
+
return resolveServerBinary(["bun"], cwd);
|
|
5594
|
+
}
|
|
5595
|
+
function runBunCommand(bunPath, args, cwd, signal) {
|
|
5596
|
+
signal?.throwIfAborted();
|
|
5597
|
+
const prepared = createSpawnCommand([bunPath, ...args]);
|
|
5598
|
+
return new Promise((resolvePromise, reject) => {
|
|
5599
|
+
const child = spawn2(prepared.command, prepared.args, {
|
|
5600
|
+
cwd,
|
|
5601
|
+
stdio: ["ignore", "pipe", "pipe"],
|
|
5602
|
+
shell: prepared.shell,
|
|
5603
|
+
windowsHide: true,
|
|
5604
|
+
detached: process.platform !== "win32"
|
|
5605
|
+
});
|
|
5606
|
+
const stdout = [];
|
|
5607
|
+
const stderr = [];
|
|
5608
|
+
const onAbort = () => killProcessTree(child, "SIGKILL");
|
|
5609
|
+
signal?.addEventListener("abort", onAbort, { once: true });
|
|
5610
|
+
child.stdout?.on("data", (chunk) => stdout.push(chunk));
|
|
5611
|
+
child.stderr?.on("data", (chunk) => stderr.push(chunk));
|
|
5612
|
+
child.once("error", (error) => {
|
|
5613
|
+
signal?.removeEventListener("abort", onAbort);
|
|
5614
|
+
reject(error);
|
|
5615
|
+
});
|
|
5616
|
+
child.once("close", (exitCode) => {
|
|
5617
|
+
signal?.removeEventListener("abort", onAbort);
|
|
5618
|
+
if (signal?.aborted) {
|
|
5619
|
+
reject(signal.reason);
|
|
5620
|
+
return;
|
|
5621
|
+
}
|
|
5622
|
+
resolvePromise({
|
|
5623
|
+
exitCode,
|
|
5624
|
+
stdout: Buffer.concat(stdout).toString("utf8"),
|
|
5625
|
+
stderr: Buffer.concat(stderr).toString("utf8")
|
|
5626
|
+
});
|
|
5627
|
+
});
|
|
5628
|
+
});
|
|
5629
|
+
}
|
|
5630
|
+
|
|
5631
|
+
// ../lsp-core/src/tools/bun-directory-diagnostics.ts
|
|
5632
|
+
var TYPESCRIPT_EXTENSIONS = new Set([".ts", ".tsx", ".mts", ".cts"]);
|
|
5633
|
+
async function runBunDirectoryDiagnostics(absDir, extension, severity, signal, options = {}) {
|
|
5634
|
+
if (!TYPESCRIPT_EXTENSIONS.has(extension))
|
|
5635
|
+
return;
|
|
5636
|
+
const checkBun = await resolveBunProjectCommand("check", absDir, options);
|
|
5637
|
+
if (checkBun === undefined)
|
|
5638
|
+
return;
|
|
5639
|
+
let typecheck;
|
|
5640
|
+
try {
|
|
5641
|
+
const run = await runBunCommand(checkBun, ["check", "--no-pretty", "."], absDir, signal);
|
|
5642
|
+
typecheck = parseBunCheckOutput(run.stdout, absDir);
|
|
5643
|
+
const failedWithoutDiagnostics = run.exitCode === 1 && typecheck.length === 0;
|
|
5644
|
+
if (run.exitCode !== 0 && run.exitCode !== 1 || failedWithoutDiagnostics)
|
|
5645
|
+
return;
|
|
5646
|
+
} catch (error) {
|
|
5647
|
+
if (signal?.aborted)
|
|
5648
|
+
throw error;
|
|
5649
|
+
return;
|
|
5650
|
+
}
|
|
5651
|
+
const header = [`Directory: ${absDir}`, "Typecheck: bun check (files in this directory and everything they import)"];
|
|
5652
|
+
const projectCommands = ["bun check"];
|
|
5653
|
+
const collected = [...typecheck];
|
|
5654
|
+
const lintBun = await resolveBunProjectCommand("lint", absDir, options);
|
|
5655
|
+
if (lintBun !== undefined) {
|
|
5656
|
+
const lint = await runBunLint(lintBun, absDir, signal);
|
|
5657
|
+
header.push(lint.status);
|
|
5658
|
+
projectCommands.push("bun lint");
|
|
5659
|
+
collected.push(...lint.diagnostics);
|
|
5660
|
+
}
|
|
5661
|
+
const diagnostics = collected.filter(({ diagnostic }) => filterDiagnosticsBySeverity([diagnostic], severity).length > 0);
|
|
5662
|
+
const lines = [...header, `Total diagnostics: ${diagnostics.length}`];
|
|
5663
|
+
const shown = diagnostics.slice(0, DEFAULT_MAX_DIAGNOSTICS);
|
|
5664
|
+
if (shown.length > 0) {
|
|
5665
|
+
lines.push("", ...shown.map(({ file, diagnostic }) => `${file}: ${formatDiagnostic(diagnostic)}`));
|
|
5666
|
+
if (diagnostics.length > shown.length) {
|
|
5667
|
+
lines.push("", `... (${diagnostics.length - shown.length} more diagnostics not shown)`);
|
|
5668
|
+
}
|
|
5669
|
+
}
|
|
5670
|
+
return { output: lines.join(`
|
|
5671
|
+
`), diagnostics, projectCommands };
|
|
5672
|
+
}
|
|
5673
|
+
async function runBunLint(bunPath, absDir, signal) {
|
|
5674
|
+
try {
|
|
5675
|
+
const run = await runBunCommand(bunPath, ["lint", "-f", "json", "."], absDir, signal);
|
|
5676
|
+
const diagnostics = run.exitCode === 0 || run.exitCode === 1 ? parseBunLintJson(run.stdout) : undefined;
|
|
5677
|
+
if (diagnostics !== undefined)
|
|
5678
|
+
return { status: "Lint: bun lint", diagnostics };
|
|
5679
|
+
const reason = run.stderr.trim().split(/\r?\n/)[0] ?? "";
|
|
5680
|
+
return { status: `Lint: bun lint could not lint (exit ${run.exitCode ?? "signal"})${reason ? `: ${reason}` : ""}`, diagnostics: [] };
|
|
5681
|
+
} catch (error) {
|
|
5682
|
+
if (signal?.aborted)
|
|
5683
|
+
throw error;
|
|
5684
|
+
return { status: `Lint: bun lint could not run: ${error instanceof Error ? error.message : String(error)}`, diagnostics: [] };
|
|
5685
|
+
}
|
|
5686
|
+
}
|
|
5687
|
+
|
|
5373
5688
|
// ../lsp-core/src/tools/parameters.ts
|
|
5374
5689
|
function isRecord7(value) {
|
|
5375
5690
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
@@ -5424,7 +5739,7 @@ function asDiagnosticArray(result) {
|
|
|
5424
5739
|
return result;
|
|
5425
5740
|
return result.items ?? [];
|
|
5426
5741
|
}
|
|
5427
|
-
async function executeLspDiagnostics(params, signal) {
|
|
5742
|
+
async function executeLspDiagnostics(params, signal, bunOptions = {}) {
|
|
5428
5743
|
const filePath = requireString(params, "filePath");
|
|
5429
5744
|
const severity = severityFilter(params);
|
|
5430
5745
|
try {
|
|
@@ -5445,6 +5760,19 @@ async function executeLspDiagnostics(params, signal) {
|
|
|
5445
5760
|
};
|
|
5446
5761
|
return text(message, details);
|
|
5447
5762
|
}
|
|
5763
|
+
const bun = await runBunDirectoryDiagnostics(absPath, extension, severity, signal, bunOptions);
|
|
5764
|
+
if (bun !== undefined) {
|
|
5765
|
+
const details = {
|
|
5766
|
+
filePath,
|
|
5767
|
+
severity,
|
|
5768
|
+
mode: "directory",
|
|
5769
|
+
diagnostics: [...bun.diagnostics],
|
|
5770
|
+
totalDiagnostics: bun.diagnostics.length,
|
|
5771
|
+
truncated: bun.diagnostics.length > DEFAULT_MAX_DIAGNOSTICS,
|
|
5772
|
+
projectCommands: [...bun.projectCommands]
|
|
5773
|
+
};
|
|
5774
|
+
return text(bun.output, details);
|
|
5775
|
+
}
|
|
5448
5776
|
const output = await aggregateDiagnosticsForDirectory(absPath, extension, severity, undefined, signal === undefined ? {} : { signal });
|
|
5449
5777
|
const details = {
|
|
5450
5778
|
filePath,
|
|
@@ -5505,7 +5833,7 @@ async function executeLspDiagnostics(params, signal) {
|
|
|
5505
5833
|
}
|
|
5506
5834
|
}
|
|
5507
5835
|
// ../lsp-core/src/lsp/format-document.ts
|
|
5508
|
-
import { readFileSync as
|
|
5836
|
+
import { readFileSync as readFileSync9, renameSync as renameSync3, unlinkSync as unlinkSync4, writeFileSync as writeFileSync4 } from "node:fs";
|
|
5509
5837
|
var DEFAULT_FORMATTING_OPTIONS = {
|
|
5510
5838
|
tabSize: 4,
|
|
5511
5839
|
insertSpaces: false,
|
|
@@ -5520,7 +5848,7 @@ async function formatDocumentWithClient(client, filePath, options = {}) {
|
|
|
5520
5848
|
return { status: "unavailable", reason: "capability_not_advertised" };
|
|
5521
5849
|
if (edits.length === 0)
|
|
5522
5850
|
return UNCHANGED;
|
|
5523
|
-
const before =
|
|
5851
|
+
const before = readFileSync9(filePath, "utf-8");
|
|
5524
5852
|
const normalized = normalizeTextEdits(before, edits, 0);
|
|
5525
5853
|
if (normalized.text === before)
|
|
5526
5854
|
return UNCHANGED;
|
|
@@ -5543,7 +5871,7 @@ function lineDelta(edits) {
|
|
|
5543
5871
|
}
|
|
5544
5872
|
function writeAtomically(filePath, content) {
|
|
5545
5873
|
const tempPath = `${filePath}.omo-format.tmp`;
|
|
5546
|
-
|
|
5874
|
+
writeFileSync4(tempPath, content, "utf-8");
|
|
5547
5875
|
try {
|
|
5548
5876
|
renameSync3(tempPath, filePath);
|
|
5549
5877
|
} catch (error) {
|
|
@@ -5848,7 +6176,7 @@ var LSP_MCP_TOOLS = [
|
|
|
5848
6176
|
name: "diagnostics",
|
|
5849
6177
|
aliases: ["lsp_diagnostics"],
|
|
5850
6178
|
title: "LSP Diagnostics",
|
|
5851
|
-
description: "Get errors, warnings, and hints for a source file or directory.",
|
|
6179
|
+
description: "Get errors, warnings, and hints for a source file or directory. In a Bun project, a TypeScript directory is typechecked with `bun check`, plus `bun lint` when the installed Bun has it.",
|
|
5852
6180
|
inputSchema: objectSchema({
|
|
5853
6181
|
filePath: { type: "string", description: "File or directory path to check." },
|
|
5854
6182
|
severity: {
|
|
@@ -6034,8 +6362,8 @@ function requestedProtocolVersion(params) {
|
|
|
6034
6362
|
|
|
6035
6363
|
// src/daemon-client.ts
|
|
6036
6364
|
import { connect } from "node:net";
|
|
6037
|
-
import { homedir as
|
|
6038
|
-
import { join as
|
|
6365
|
+
import { homedir as homedir4 } from "node:os";
|
|
6366
|
+
import { join as join9 } from "node:path";
|
|
6039
6367
|
import { setTimeout as delay } from "node:timers/promises";
|
|
6040
6368
|
|
|
6041
6369
|
// src/daemon-request-error.ts
|
|
@@ -6112,21 +6440,21 @@ function errorText(error) {
|
|
|
6112
6440
|
}
|
|
6113
6441
|
|
|
6114
6442
|
// src/ensure-daemon.ts
|
|
6115
|
-
import { spawn as
|
|
6116
|
-
import { closeSync as closeSync3, existsSync as
|
|
6443
|
+
import { spawn as spawn3 } from "node:child_process";
|
|
6444
|
+
import { closeSync as closeSync3, existsSync as existsSync14, mkdirSync as mkdirSync4, openSync as openSync3, writeSync as writeSync3 } from "node:fs";
|
|
6117
6445
|
import { Socket } from "node:net";
|
|
6118
|
-
import { dirname as
|
|
6446
|
+
import { dirname as dirname13, isAbsolute as isAbsolute5 } from "node:path";
|
|
6119
6447
|
import { argv0, execPath } from "node:process";
|
|
6120
6448
|
|
|
6121
6449
|
// src/paths.ts
|
|
6122
6450
|
import { createHash as createHash2 } from "node:crypto";
|
|
6123
6451
|
import { createRequire } from "node:module";
|
|
6124
|
-
import { homedir as
|
|
6452
|
+
import { homedir as homedir3, tmpdir as tmpdir2, userInfo } from "node:os";
|
|
6125
6453
|
import * as path from "node:path";
|
|
6126
6454
|
import { fileURLToPath as fileURLToPath3 } from "node:url";
|
|
6127
6455
|
|
|
6128
6456
|
// src/runtime-contract.ts
|
|
6129
|
-
import { statSync as
|
|
6457
|
+
import { statSync as statSync6 } from "node:fs";
|
|
6130
6458
|
import { isAbsolute as isAbsolute4 } from "node:path";
|
|
6131
6459
|
var OMO_LSP_DAEMON_DIR = "OMO_LSP_DAEMON_DIR";
|
|
6132
6460
|
var OMO_LSP_DAEMON_CLI = "OMO_LSP_DAEMON_CLI";
|
|
@@ -6174,7 +6502,7 @@ function resolveDaemonRuntime(env, defaults) {
|
|
|
6174
6502
|
}
|
|
6175
6503
|
let cliStats;
|
|
6176
6504
|
try {
|
|
6177
|
-
cliStats =
|
|
6505
|
+
cliStats = statSync6(cliOverride);
|
|
6178
6506
|
} catch (error) {
|
|
6179
6507
|
if (!(error instanceof Error))
|
|
6180
6508
|
throw error;
|
|
@@ -6251,8 +6579,8 @@ function daemonPaths(env = process.env, runtimeDefaults = packagedRuntimeDefault
|
|
|
6251
6579
|
function defaultDaemonPlatform() {
|
|
6252
6580
|
return {
|
|
6253
6581
|
platform: process.platform,
|
|
6254
|
-
homedir:
|
|
6255
|
-
tmpdir,
|
|
6582
|
+
homedir: homedir3,
|
|
6583
|
+
tmpdir: tmpdir2,
|
|
6256
6584
|
getuid: () => typeof process.getuid === "function" ? process.getuid() : undefined,
|
|
6257
6585
|
username: () => userInfo().username,
|
|
6258
6586
|
path
|
|
@@ -6308,7 +6636,7 @@ function createLineDecoder(onMessage, onParseError) {
|
|
|
6308
6636
|
}
|
|
6309
6637
|
|
|
6310
6638
|
// src/ensure-daemon.ts
|
|
6311
|
-
var
|
|
6639
|
+
var PROBE_TIMEOUT_MS2 = 2000;
|
|
6312
6640
|
var DEFAULT_READY_TIMEOUT_MS = 5000;
|
|
6313
6641
|
var DEFAULT_POLL_INTERVAL_MS = 100;
|
|
6314
6642
|
var FAILED_SPAWN_COOLDOWN_MS = 5000;
|
|
@@ -6353,13 +6681,13 @@ async function waitUntilReachable(paths, deps, readyTimeoutMs, pollIntervalMs, s
|
|
|
6353
6681
|
await awaitWithSignal2(deps.sleep(pollIntervalMs, signal), signal);
|
|
6354
6682
|
}
|
|
6355
6683
|
}
|
|
6356
|
-
async function probeDaemon(paths, timeoutMs =
|
|
6684
|
+
async function probeDaemon(paths, timeoutMs = PROBE_TIMEOUT_MS2, signal) {
|
|
6357
6685
|
const token = readAuthToken(paths);
|
|
6358
6686
|
if (!token)
|
|
6359
6687
|
return false;
|
|
6360
6688
|
return await pingDaemon(paths, token, timeoutMs, signal) !== null;
|
|
6361
6689
|
}
|
|
6362
|
-
function pingDaemon(paths, token, timeoutMs =
|
|
6690
|
+
function pingDaemon(paths, token, timeoutMs = PROBE_TIMEOUT_MS2, signal) {
|
|
6363
6691
|
return new Promise((resolve) => {
|
|
6364
6692
|
const socket = new Socket;
|
|
6365
6693
|
let settled = false;
|
|
@@ -6396,10 +6724,10 @@ function pingDaemon(paths, token, timeoutMs = PROBE_TIMEOUT_MS, signal) {
|
|
|
6396
6724
|
});
|
|
6397
6725
|
}
|
|
6398
6726
|
function spawnDaemonProcess(paths, deps = {}) {
|
|
6399
|
-
mkdirSync4(
|
|
6727
|
+
mkdirSync4(dirname13(paths.log), { recursive: true });
|
|
6400
6728
|
const logFd = openSync3(paths.log, "a");
|
|
6401
6729
|
try {
|
|
6402
|
-
const spawnDaemonChild = deps.spawn ??
|
|
6730
|
+
const spawnDaemonChild = deps.spawn ?? spawn3;
|
|
6403
6731
|
const executable = deps.resolveExecutable?.() ?? resolveDaemonNodeExecutable();
|
|
6404
6732
|
const child = spawnDaemonChild(executable, [paths.cliPath, "daemon"], {
|
|
6405
6733
|
detached: true,
|
|
@@ -6419,7 +6747,7 @@ function spawnDaemonProcess(paths, deps = {}) {
|
|
|
6419
6747
|
throw error;
|
|
6420
6748
|
}
|
|
6421
6749
|
}
|
|
6422
|
-
function resolveDaemonNodeExecutable(cachedExecPath = execPath, originalArgv0 = argv0, pathExists =
|
|
6750
|
+
function resolveDaemonNodeExecutable(cachedExecPath = execPath, originalArgv0 = argv0, pathExists = existsSync14) {
|
|
6423
6751
|
if (pathExists(cachedExecPath))
|
|
6424
6752
|
return cachedExecPath;
|
|
6425
6753
|
if (isAbsolute5(originalArgv0) && pathExists(originalArgv0))
|
|
@@ -6428,7 +6756,7 @@ function resolveDaemonNodeExecutable(cachedExecPath = execPath, originalArgv0 =
|
|
|
6428
6756
|
}
|
|
6429
6757
|
function defaultEnsureDaemonDeps() {
|
|
6430
6758
|
return {
|
|
6431
|
-
probe: (paths, signal) => probeDaemon(paths,
|
|
6759
|
+
probe: (paths, signal) => probeDaemon(paths, PROBE_TIMEOUT_MS2, signal),
|
|
6432
6760
|
spawnDaemon: (paths) => spawnDaemonProcess(paths),
|
|
6433
6761
|
sleep: (ms, signal) => sleepWithSignal(ms, signal),
|
|
6434
6762
|
now: () => Date.now()
|
|
@@ -6657,12 +6985,12 @@ function callFormatViaDaemon(filePath, options) {
|
|
|
6657
6985
|
}
|
|
6658
6986
|
function currentRequestContext(env = process.env) {
|
|
6659
6987
|
const cwd = process.cwd();
|
|
6660
|
-
const home = env["HOME"] ??
|
|
6988
|
+
const home = env["HOME"] ?? homedir4();
|
|
6661
6989
|
return parseLspRequestContext({
|
|
6662
6990
|
cwd,
|
|
6663
|
-
projectConfigPaths: [
|
|
6664
|
-
userConfigPath:
|
|
6665
|
-
installDecisionsPath:
|
|
6991
|
+
projectConfigPaths: [join9(cwd, ".codex", "lsp-client.json")],
|
|
6992
|
+
userConfigPath: join9(home, ".codex", "lsp-client.json"),
|
|
6993
|
+
installDecisionsPath: join9(home, ".codex", "lsp-install-decisions.json"),
|
|
6666
6994
|
capabilities: { installDecisionTool: true }
|
|
6667
6995
|
});
|
|
6668
6996
|
}
|
|
@@ -6917,18 +7245,18 @@ function canonicalizePathList(value) {
|
|
|
6917
7245
|
return value.split(delimiter4).map((entry) => canonicalizePath(entry) ?? entry).join(delimiter4);
|
|
6918
7246
|
}
|
|
6919
7247
|
function canonicalizePath(value) {
|
|
6920
|
-
if (value === undefined || !isAbsolute6(value) || !
|
|
7248
|
+
if (value === undefined || !isAbsolute6(value) || !existsSync15(value))
|
|
6921
7249
|
return value;
|
|
6922
7250
|
return realpathSync6(value);
|
|
6923
7251
|
}
|
|
6924
7252
|
function projectRootFromOpenCodeConfigPath(path) {
|
|
6925
7253
|
if (basename4(path) !== "lsp.json" && basename4(path) !== "lsp-client.json")
|
|
6926
7254
|
return;
|
|
6927
|
-
const configDir =
|
|
7255
|
+
const configDir = dirname14(path);
|
|
6928
7256
|
const configDirName = basename4(configDir);
|
|
6929
7257
|
if (configDirName !== ".opencode" && configDirName !== ".omo")
|
|
6930
7258
|
return;
|
|
6931
|
-
return
|
|
7259
|
+
return dirname14(configDir);
|
|
6932
7260
|
}
|
|
6933
7261
|
|
|
6934
7262
|
// src/daemon-server.ts
|
|
@@ -6938,7 +7266,7 @@ import { createServer as createServer2 } from "node:net";
|
|
|
6938
7266
|
// src/version-reap.ts
|
|
6939
7267
|
import { execFile } from "node:child_process";
|
|
6940
7268
|
import { readdir, readFile, rm } from "node:fs/promises";
|
|
6941
|
-
import { basename as basename5, dirname as
|
|
7269
|
+
import { basename as basename5, dirname as dirname15, join as join10 } from "node:path";
|
|
6942
7270
|
var TERM_GRACE_MS = 5000;
|
|
6943
7271
|
var KILL_GRACE_MS = 1000;
|
|
6944
7272
|
var VERSION_ENTRY_PATTERN = /^v([A-Za-z0-9][A-Za-z0-9._+-]{0,127})$/;
|
|
@@ -6959,7 +7287,7 @@ async function attestDaemonCliProcess(pid, platform, deps = {}) {
|
|
|
6959
7287
|
return isNodeCliDaemonCommand(command.trim());
|
|
6960
7288
|
}
|
|
6961
7289
|
async function reapStaleDaemonVersions(ownPaths, deps = {}) {
|
|
6962
|
-
const baseDir =
|
|
7290
|
+
const baseDir = dirname15(ownPaths.dir);
|
|
6963
7291
|
const platform = deps.platform ?? process.platform;
|
|
6964
7292
|
const isAlive = deps.isAlive ?? isProcessAlive;
|
|
6965
7293
|
const attest = deps.attest ?? ((pid) => attestDaemonCliProcess(pid, platform));
|
|
@@ -6978,7 +7306,7 @@ async function reapStaleDaemonVersions(ownPaths, deps = {}) {
|
|
|
6978
7306
|
const version = parseVersionEntry(entry.name);
|
|
6979
7307
|
if (version === null || !entry.isDirectory())
|
|
6980
7308
|
continue;
|
|
6981
|
-
const versionDir =
|
|
7309
|
+
const versionDir = join10(baseDir, entry.name);
|
|
6982
7310
|
const siblingPaths = daemonPaths({ [OMO_LSP_DAEMON_DIR]: baseDir }, { cliPath: ownPaths.cliPath, version });
|
|
6983
7311
|
results.push(await reapOneVersion({
|
|
6984
7312
|
version,
|
|
@@ -7002,7 +7330,7 @@ async function reapOneVersion(context) {
|
|
|
7002
7330
|
const { version, versionDir } = context;
|
|
7003
7331
|
const owner = context.readOwner(context.siblingPaths);
|
|
7004
7332
|
if (!owner) {
|
|
7005
|
-
const lockPid = readLockPid(
|
|
7333
|
+
const lockPid = readLockPid(join10(versionDir, "daemon.lock"));
|
|
7006
7334
|
if (lockPid !== null && context.isAlive(lockPid)) {
|
|
7007
7335
|
context.log(`reap: sparing v${version}: owner metadata missing but daemon.lock is held by live pid ${lockPid}`);
|
|
7008
7336
|
return { version, status: "spared", reason: `owner metadata missing but lock held by live pid ${lockPid}` };
|