lody 0.49.0 → 0.49.1

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 (2) hide show
  1. package/dist/index.js +14 -178
  2. package/package.json +2 -2
package/dist/index.js CHANGED
@@ -1,6 +1,6 @@
1
1
  #!/usr/bin/env node
2
2
  import require$$3$5, { randomUUID, randomBytes, createHash } from "crypto";
3
- import require$$0$5, { inspect as inspect$1, types as types$6, promisify as promisify$1 } from "util";
3
+ import require$$0$5, { inspect as inspect$1, types as types$6 } from "util";
4
4
  import require$$2$6 from "url";
5
5
  import * as path$2 from "path";
6
6
  import path__default, { normalize as normalize$1, resolve as resolve$1 } from "path";
@@ -20,7 +20,7 @@ import * as diagch from "diagnostics_channel";
20
20
  import diagch__default from "diagnostics_channel";
21
21
  import * as net from "node:net";
22
22
  import require$$1$4 from "async_hooks";
23
- import require$$1$5, { execFile as execFile$1, spawn as spawn$1 } from "node:child_process";
23
+ import require$$1$5, { execFile, spawn as spawn$1 } from "node:child_process";
24
24
  import fs$6, { readdir, readFile, createReadStream, existsSync, readFileSync as readFileSync$1, promises } from "node:fs";
25
25
  import * as os from "node:os";
26
26
  import os__default$1 from "node:os";
@@ -45,7 +45,7 @@ import require$$1$6 from "string_decoder";
45
45
  import * as http$2 from "http";
46
46
  import http__default from "http";
47
47
  import require$$1$7 from "https";
48
- import require$$0$a, { execSync, exec, execFileSync, execFile as execFile$2 } from "child_process";
48
+ import require$$0$a, { execSync, exec, execFileSync, execFile as execFile$1 } from "child_process";
49
49
  import { randomFillSync, randomUUID as randomUUID$1, createHash as createHash$1 } from "node:crypto";
50
50
  import require$$0$b from "net";
51
51
  import require$$4$3 from "tls";
@@ -20576,7 +20576,7 @@ Event: ${getEventDescription(event)}`);
20576
20576
  };
20577
20577
  try {
20578
20578
  const output = await new Promise((resolve2, reject) => {
20579
- execFile$1("/usr/bin/sw_vers", (error2, stdout) => {
20579
+ execFile("/usr/bin/sw_vers", (error2, stdout) => {
20580
20580
  if (error2) {
20581
20581
  reject(error2);
20582
20582
  return;
@@ -36821,7 +36821,7 @@ Mongoose Error Code: ${error2.code}` : ""}`
36821
36821
  return client;
36822
36822
  }
36823
36823
  const name = "lody";
36824
- const version$4 = "0.49.0";
36824
+ const version$4 = "0.49.1";
36825
36825
  const description$1 = "Lody Agent CLI tool for managing remote command execution";
36826
36826
  const type$2 = "module";
36827
36827
  const main$3 = "dist/index.js";
@@ -104343,7 +104343,7 @@ stream:${scope2.streamId}`;
104343
104343
  }
104344
104344
  var outExports = requireOut();
104345
104345
  const fastGlob = getDefaultExportFromCjs(outExports);
104346
- promisify(execFile$1);
104346
+ promisify(execFile);
104347
104347
  function toPath(urlOrPath) {
104348
104348
  return urlOrPath instanceof URL ? fileURLToPath(urlOrPath) : urlOrPath;
104349
104349
  }
@@ -104677,7 +104677,7 @@ stream:${scope2.streamId}`;
104677
104677
  }
104678
104678
  var ignoreExports = requireIgnore();
104679
104679
  const gitIgnore = getDefaultExportFromCjs(ignoreExports);
104680
- function isPathInside$1(childPath, parentPath) {
104680
+ function isPathInside(childPath, parentPath) {
104681
104681
  const relation = path__default$1.relative(parentPath, childPath);
104682
104682
  return Boolean(relation && relation !== ".." && !relation.startsWith(`..${path__default$1.sep}`) && relation !== path__default$1.resolve(childPath));
104683
104683
  }
@@ -104824,7 +104824,7 @@ stream:${scope2.streamId}`;
104824
104824
  const isWithinGitRoot = (gitRoot, cwd) => {
104825
104825
  const resolvedGitRoot = path__default$1.resolve(gitRoot);
104826
104826
  const resolvedCwd = path__default$1.resolve(cwd);
104827
- return resolvedCwd === resolvedGitRoot || isPathInside$1(resolvedCwd, resolvedGitRoot);
104827
+ return resolvedCwd === resolvedGitRoot || isPathInside(resolvedCwd, resolvedGitRoot);
104828
104828
  };
104829
104829
  const getParentGitignorePaths = (gitRoot, cwd) => {
104830
104830
  if (gitRoot && typeof gitRoot !== "string") {
@@ -104957,7 +104957,7 @@ stream:${scope2.streamId}`;
104957
104957
  const toRelativePath = (fileOrDirectory, cwd) => {
104958
104958
  if (path__default$1.isAbsolute(fileOrDirectory)) {
104959
104959
  const relativePath = path__default$1.relative(cwd, fileOrDirectory);
104960
- if (relativePath && !isPathInside$1(fileOrDirectory, cwd)) {
104960
+ if (relativePath && !isPathInside(fileOrDirectory, cwd)) {
104961
104961
  return void 0;
104962
104962
  }
104963
104963
  return relativePath;
@@ -129454,7 +129454,6 @@ ${escapeHtmlScriptContent(VISUAL_ANNOTATION_INSPECTOR_BROWSER_SCRIPT)}
129454
129454
  const PREVIEW_REGISTRY_LOCK_NAME = "preview-tunnels";
129455
129455
  const PREVIEW_REGISTRY_FILE = path__default.join(os__default.homedir(), ".lody", "preview-tunnels.json");
129456
129456
  const PREVIEW_REGISTRY_FUTURE_SKEW_MS = 6e4;
129457
- const execFile = promisify$1(execFile$2);
129458
129457
  const normalizeHost = (host) => {
129459
129458
  const trimmed = host.trim().toLowerCase();
129460
129459
  return trimmed.startsWith("[") && trimmed.endsWith("]") ? trimmed.slice(1, -1) : trimmed;
@@ -129565,96 +129564,6 @@ ${escapeHtmlScriptContent(VISUAL_ANNOTATION_INSPECTOR_BROWSER_SCRIPT)}
129565
129564
  clearTimeout(timeout2);
129566
129565
  }
129567
129566
  };
129568
- const parseLsofOwners = (stdout) => {
129569
- const owners = [];
129570
- let current2 = null;
129571
- for (const rawLine of stdout.split(/\r?\n/)) {
129572
- const line3 = rawLine.trim();
129573
- if (!line3) {
129574
- continue;
129575
- }
129576
- const kind = line3[0];
129577
- const value = line3.slice(1);
129578
- if (kind === "p") {
129579
- const pid = Number.parseInt(value, 10);
129580
- if (Number.isInteger(pid) && pid > 0) {
129581
- current2 = {
129582
- pid,
129583
- listenNames: []
129584
- };
129585
- owners.push(current2);
129586
- } else {
129587
- current2 = null;
129588
- }
129589
- continue;
129590
- }
129591
- if (!current2) {
129592
- continue;
129593
- }
129594
- if (kind === "c") {
129595
- current2.name = value;
129596
- } else if (kind === "n") {
129597
- current2.listenNames.push(value);
129598
- }
129599
- }
129600
- return owners;
129601
- };
129602
- const getPortOwners = async (port) => {
129603
- try {
129604
- const { stdout } = await execFile("lsof", [
129605
- "-nP",
129606
- `-iTCP:${port}`,
129607
- "-sTCP:LISTEN",
129608
- "-Fpcn"
129609
- ], {
129610
- timeout: 2e3,
129611
- maxBuffer: 128 * 1024
129612
- });
129613
- return parseLsofOwners(stdout);
129614
- } catch {
129615
- return [];
129616
- }
129617
- };
129618
- const isLoopbackListenName = (name2, port) => {
129619
- const lower = name2.toLowerCase();
129620
- if (lower.includes(`*:${port}`) || lower.includes(`0.0.0.0:${port}`)) {
129621
- return false;
129622
- }
129623
- return lower.includes(`127.0.0.1:${port}`) || lower.includes(`localhost:${port}`) || lower.includes(`[::1]:${port}`) || lower.includes(`::1:${port}`);
129624
- };
129625
- const getProcessCwd = async (pid) => {
129626
- if (process.platform === "linux") {
129627
- try {
129628
- return await fs__default$1.realpath(`/proc/${pid}/cwd`);
129629
- } catch {
129630
- return null;
129631
- }
129632
- }
129633
- try {
129634
- const { stdout } = await execFile("lsof", [
129635
- "-a",
129636
- "-p",
129637
- String(pid),
129638
- "-d",
129639
- "cwd",
129640
- "-Fn"
129641
- ], {
129642
- timeout: 2e3,
129643
- maxBuffer: 64 * 1024
129644
- });
129645
- const cwdLine = stdout.split(/\r?\n/).map((line3) => line3.trim()).find((line3) => line3.startsWith("n"));
129646
- if (!cwdLine) {
129647
- return null;
129648
- }
129649
- return await fs__default$1.realpath(cwdLine.slice(1));
129650
- } catch {
129651
- return null;
129652
- }
129653
- };
129654
- const isPathInside = (child, parent) => {
129655
- const relative2 = path__default.relative(parent, child);
129656
- return relative2 === "" || !!relative2 && !relative2.startsWith("..") && !path__default.isAbsolute(relative2);
129657
- };
129658
129567
  const isProcessAlive$1 = (pid) => {
129659
129568
  if (!Number.isInteger(pid) || pid <= 0) {
129660
129569
  return false;
@@ -129840,7 +129749,7 @@ ${escapeHtmlScriptContent(VISUAL_ANNOTATION_INSPECTOR_BROWSER_SCRIPT)}
129840
129749
  });
129841
129750
  return this.connectionResponse(request.sessionId, false, connection, failure);
129842
129751
  }
129843
- const validation2 = await this.validateTargetForCreate(request.sessionId, candidate.target);
129752
+ const validation2 = await this.validateTargetForCreate(candidate.target);
129844
129753
  if ("failure" in validation2) {
129845
129754
  const connection = this.failedConnection("create", validation2.failure, now2, candidate.target);
129846
129755
  await this.patchSessionPreview(request.sessionId, {
@@ -130066,7 +129975,7 @@ ${escapeHtmlScriptContent(VISUAL_ANNOTATION_INSPECTOR_BROWSER_SCRIPT)}
130066
129975
  connection: revoked
130067
129976
  };
130068
129977
  }
130069
- async validateTargetForCreate(sessionId, target) {
129978
+ async validateTargetForCreate(target) {
130070
129979
  const normalized = normalizeTarget(target);
130071
129980
  if (isValidationFailure(normalized)) {
130072
129981
  return {
@@ -130079,12 +129988,6 @@ ${escapeHtmlScriptContent(VISUAL_ANNOTATION_INSPECTOR_BROWSER_SCRIPT)}
130079
129988
  failure: tcpFailure
130080
129989
  };
130081
129990
  }
130082
- const owner = await this.resolveOwnedPort(sessionId, normalized.port);
130083
- if ("failure" in owner) {
130084
- return {
130085
- failure: owner.failure
130086
- };
130087
- }
130088
129991
  const httpFailure = await probeHttp(normalized);
130089
129992
  if (httpFailure) {
130090
129993
  return {
@@ -130092,9 +129995,7 @@ ${escapeHtmlScriptContent(VISUAL_ANNOTATION_INSPECTOR_BROWSER_SCRIPT)}
130092
129995
  };
130093
129996
  }
130094
129997
  return {
130095
- normalizedTarget: normalized,
130096
- ownerPid: owner.pid,
130097
- ownerCwd: owner.cwd
129998
+ normalizedTarget: normalized
130098
129999
  };
130099
130000
  }
130100
130001
  resolveGatewayUrl() {
@@ -130230,70 +130131,6 @@ ${escapeHtmlScriptContent(VISUAL_ANNOTATION_INSPECTOR_BROWSER_SCRIPT)}
130230
130131
  this.deps.logger.debug(`[${sessionId}] Failed to release preview machine slot: ${formatErrorMessage(error2)}`);
130231
130132
  });
130232
130133
  }
130233
- async resolveOwnedPort(sessionId, port) {
130234
- const session = this.deps.sessionManager.getSession(sessionId);
130235
- const hostWorkdir = session?.getHostWorkdir();
130236
- if (!hostWorkdir) {
130237
- return {
130238
- failure: {
130239
- code: "process_not_owned_by_session",
130240
- message: "Preview requires an active local session with a host working directory.",
130241
- retryable: true
130242
- }
130243
- };
130244
- }
130245
- const owners = await getPortOwners(port);
130246
- if (owners.length === 0) {
130247
- return {
130248
- failure: {
130249
- code: "process_not_owned_by_session",
130250
- message: `Unable to determine which process owns local port ${port}.`,
130251
- retryable: true
130252
- }
130253
- };
130254
- }
130255
- const loopbackOwners = owners.filter((owner) => owner.listenNames.length > 0 && owner.listenNames.every((name2) => isLoopbackListenName(name2, port)));
130256
- if (loopbackOwners.length === 0) {
130257
- return {
130258
- failure: {
130259
- code: "host_not_loopback",
130260
- message: `Port ${port} is not exclusively bound to a loopback interface.`,
130261
- retryable: false
130262
- }
130263
- };
130264
- }
130265
- let realHostWorkdir;
130266
- try {
130267
- realHostWorkdir = await fs__default$1.realpath(hostWorkdir);
130268
- } catch (error2) {
130269
- return {
130270
- failure: {
130271
- code: "process_not_owned_by_session",
130272
- message: `Unable to resolve session workdir: ${formatErrorMessage(error2)}`,
130273
- retryable: true
130274
- }
130275
- };
130276
- }
130277
- for (const owner of loopbackOwners) {
130278
- const ownerCwd = await getProcessCwd(owner.pid);
130279
- if (!ownerCwd) {
130280
- continue;
130281
- }
130282
- if (isPathInside(ownerCwd, realHostWorkdir)) {
130283
- return {
130284
- pid: owner.pid,
130285
- cwd: ownerCwd
130286
- };
130287
- }
130288
- }
130289
- return {
130290
- failure: {
130291
- code: "process_not_owned_by_session",
130292
- message: `Port ${port} is not owned by a process running inside this session workdir.`,
130293
- retryable: true
130294
- }
130295
- };
130296
- }
130297
130134
  async getSessionMeta(sessionId) {
130298
130135
  const record2 = await this.deps.workspaceDocument.repo.getDocMeta(getSessionRoomId(sessionId));
130299
130136
  if (!record2?.meta || isLoroRepoDocDeleted(record2)) {
@@ -130528,7 +130365,6 @@ ${escapeHtmlScriptContent(VISUAL_ANNOTATION_INSPECTOR_BROWSER_SCRIPT)}
130528
130365
  this.previewService = new PreviewService({
130529
130366
  logger: this.logger,
130530
130367
  workspaceDocument: this.workspaceDocument,
130531
- sessionManager: this.sessionManager,
130532
130368
  machineId: this.machineId,
130533
130369
  workspaceId: this.workspaceId,
130534
130370
  userId: this.userId,
@@ -134296,7 +134132,7 @@ ${escapeHtmlScriptContent(VISUAL_ANNOTATION_INSPECTOR_BROWSER_SCRIPT)}
134296
134132
  }
134297
134133
  async function isGhCliAuthed(logger2) {
134298
134134
  return new Promise((resolve2) => {
134299
- const child = execFile$2("gh", [
134135
+ const child = execFile$1("gh", [
134300
134136
  "auth",
134301
134137
  "status"
134302
134138
  ], {
@@ -142041,7 +141877,7 @@ export PATH=${toSingleQuotedShellString(ghShimBinDir)}:"$PATH"
142041
141877
  const DEFAULT_LOCAL_PROJECT_READ_MAX_BYTES = 64 * 1024;
142042
141878
  const HARD_LOCAL_PROJECT_READ_MAX_BYTES = 1024 * 1024;
142043
141879
  const GIT_COMMAND_MAX_BUFFER_BYTES = 64 * 1024 * 1024;
142044
- const execFileAsync = promisify(execFile$1);
141880
+ const execFileAsync = promisify(execFile);
142045
141881
  function clampInteger(value, min2, max2, fallback2) {
142046
141882
  if (typeof value !== "number" || Number.isNaN(value) || !Number.isFinite(value)) {
142047
141883
  return fallback2;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "lody",
3
- "version": "0.49.0",
3
+ "version": "0.49.1",
4
4
  "description": "Lody Agent CLI tool for managing remote command execution",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",
@@ -74,8 +74,8 @@
74
74
  "ws": "^8.18.3",
75
75
  "zod": "^4.1.5",
76
76
  "@lody/cli-supervisor": "0.0.1",
77
- "@lody/loro-streams-rpc": "0.0.1",
78
77
  "@lody/convex": "0.0.1",
78
+ "@lody/loro-streams-rpc": "0.0.1",
79
79
  "@lody/shared": "0.0.1",
80
80
  "loro-code": "0.0.1"
81
81
  },