@parall/daemon 1.32.0 → 1.32.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.
@@ -17718,9 +17718,9 @@ var require_getMachineId_linux = __commonJS({
17718
17718
  var api_1 = (init_esm(), __toCommonJS(esm_exports));
17719
17719
  async function getMachineId() {
17720
17720
  const paths = ["/etc/machine-id", "/var/lib/dbus/machine-id"];
17721
- for (const path11 of paths) {
17721
+ for (const path12 of paths) {
17722
17722
  try {
17723
- const result = await fs_1.promises.readFile(path11, { encoding: "utf8" });
17723
+ const result = await fs_1.promises.readFile(path12, { encoding: "utf8" });
17724
17724
  return result.trim();
17725
17725
  } catch (e) {
17726
17726
  api_1.diag.debug(`error reading machine id: ${e}`);
@@ -21123,7 +21123,7 @@ function appendRootPathToUrlIfNeeded(url) {
21123
21123
  return void 0;
21124
21124
  }
21125
21125
  }
21126
- function appendResourcePathToUrl(url, path11) {
21126
+ function appendResourcePathToUrl(url, path12) {
21127
21127
  try {
21128
21128
  new URL(url);
21129
21129
  } catch (_a) {
@@ -21133,11 +21133,11 @@ function appendResourcePathToUrl(url, path11) {
21133
21133
  if (!url.endsWith("/")) {
21134
21134
  url = url + "/";
21135
21135
  }
21136
- url += path11;
21136
+ url += path12;
21137
21137
  try {
21138
21138
  new URL(url);
21139
21139
  } catch (_b) {
21140
- diag2.warn("Configuration: Provided URL appended with '" + path11 + "' is not a valid URL, using 'undefined' instead of '" + url + "'");
21140
+ diag2.warn("Configuration: Provided URL appended with '" + path12 + "' is not a valid URL, using 'undefined' instead of '" + url + "'");
21141
21141
  return void 0;
21142
21142
  }
21143
21143
  return url;
@@ -26656,8 +26656,8 @@ var updater_exports = {};
26656
26656
  __export(updater_exports, {
26657
26657
  DaemonUpdater: () => DaemonUpdater
26658
26658
  });
26659
- import * as fs9 from "node:fs";
26660
- import * as path9 from "node:path";
26659
+ import * as fs10 from "node:fs";
26660
+ import * as path10 from "node:path";
26661
26661
  import * as https2 from "node:https";
26662
26662
  import * as http3 from "node:http";
26663
26663
  import { createHash as createHash3 } from "node:crypto";
@@ -26748,20 +26748,20 @@ MCowBQYDK2VwAyEAQHQAZThNX7+deJNyHl/5DgiAa1OHx7UQoJotam0JhUk=
26748
26748
  return false;
26749
26749
  if (!state.previous_version)
26750
26750
  return false;
26751
- const previousDir = path9.join(this.bundleDir, "versions", state.previous_version);
26752
- if (!fs9.existsSync(previousDir))
26751
+ const previousDir = path10.join(this.bundleDir, "versions", state.previous_version);
26752
+ if (!fs10.existsSync(previousDir))
26753
26753
  return false;
26754
26754
  this.log.warn(`rollback: ${current.version} failed ${state.boot_count} boots, reverting to ${state.previous_version}`);
26755
26755
  if (process.platform === "win32") {
26756
- const currentDir = path9.join(this.bundleDir, "current");
26757
- if (fs9.existsSync(currentDir)) {
26758
- for (const file of fs9.readdirSync(currentDir)) {
26759
- fs9.unlinkSync(path9.join(currentDir, file));
26756
+ const currentDir = path10.join(this.bundleDir, "current");
26757
+ if (fs10.existsSync(currentDir)) {
26758
+ for (const file of fs10.readdirSync(currentDir)) {
26759
+ fs10.unlinkSync(path10.join(currentDir, file));
26760
26760
  }
26761
26761
  }
26762
- fs9.mkdirSync(currentDir, { recursive: true });
26763
- for (const file of fs9.readdirSync(previousDir)) {
26764
- fs9.copyFileSync(path9.join(previousDir, file), path9.join(currentDir, file));
26762
+ fs10.mkdirSync(currentDir, { recursive: true });
26763
+ for (const file of fs10.readdirSync(previousDir)) {
26764
+ fs10.copyFileSync(path10.join(previousDir, file), path10.join(currentDir, file));
26765
26765
  }
26766
26766
  } else {
26767
26767
  this.swapSymlink(state.previous_version);
@@ -26869,11 +26869,11 @@ MCowBQYDK2VwAyEAQHQAZThNX7+deJNyHl/5DgiAa1OHx7UQoJotam0JhUk=
26869
26869
  return false;
26870
26870
  }
26871
26871
  }
26872
- const stagingDir = path9.join(this.bundleDir, "staging");
26872
+ const stagingDir = path10.join(this.bundleDir, "staging");
26873
26873
  this.cleanDir(stagingDir);
26874
- fs9.mkdirSync(stagingDir, { recursive: true });
26874
+ fs10.mkdirSync(stagingDir, { recursive: true });
26875
26875
  for (const [filename, meta] of Object.entries(remote.files)) {
26876
- const filePath = path9.join(stagingDir, filename);
26876
+ const filePath = path10.join(stagingDir, filename);
26877
26877
  const fileUrl = `${this.cdnBaseUrl}/${remote.version}/${filename}`;
26878
26878
  try {
26879
26879
  await this.downloadFile(fileUrl, filePath);
@@ -26882,7 +26882,7 @@ MCowBQYDK2VwAyEAQHQAZThNX7+deJNyHl/5DgiAa1OHx7UQoJotam0JhUk=
26882
26882
  this.cleanDir(stagingDir);
26883
26883
  return false;
26884
26884
  }
26885
- const content = fs9.readFileSync(filePath);
26885
+ const content = fs10.readFileSync(filePath);
26886
26886
  const hash = createHash3("sha256").update(content).digest("hex");
26887
26887
  if (hash !== meta.sha256) {
26888
26888
  this.log.error(`update: sha256 mismatch for ${filename} (expected ${meta.sha256}, got ${hash})`);
@@ -26895,7 +26895,7 @@ MCowBQYDK2VwAyEAQHQAZThNX7+deJNyHl/5DgiAa1OHx7UQoJotam0JhUk=
26895
26895
  return false;
26896
26896
  }
26897
26897
  }
26898
- fs9.writeFileSync(path9.join(stagingDir, "manifest.json"), JSON.stringify(remote, null, 2));
26898
+ fs10.writeFileSync(path10.join(stagingDir, "manifest.json"), JSON.stringify(remote, null, 2));
26899
26899
  this.atomicSwap(stagingDir, remote.version);
26900
26900
  const newState = {
26901
26901
  confirmed_version: local?.version ?? state?.confirmed_version,
@@ -26909,24 +26909,24 @@ MCowBQYDK2VwAyEAQHQAZThNX7+deJNyHl/5DgiAa1OHx7UQoJotam0JhUk=
26909
26909
  return true;
26910
26910
  }
26911
26911
  atomicSwap(stagingDir, newVersion) {
26912
- const versionsDir = path9.join(this.bundleDir, "versions");
26913
- const targetDir = path9.join(versionsDir, newVersion);
26914
- const currentLink = path9.join(this.bundleDir, "current");
26915
- fs9.mkdirSync(versionsDir, { recursive: true });
26916
- if (fs9.existsSync(targetDir)) {
26917
- fs9.rmSync(targetDir, { recursive: true });
26918
- }
26919
- fs9.renameSync(stagingDir, targetDir);
26912
+ const versionsDir = path10.join(this.bundleDir, "versions");
26913
+ const targetDir = path10.join(versionsDir, newVersion);
26914
+ const currentLink = path10.join(this.bundleDir, "current");
26915
+ fs10.mkdirSync(versionsDir, { recursive: true });
26916
+ if (fs10.existsSync(targetDir)) {
26917
+ fs10.rmSync(targetDir, { recursive: true });
26918
+ }
26919
+ fs10.renameSync(stagingDir, targetDir);
26920
26920
  if (process.platform === "win32") {
26921
26921
  const currentDir = currentLink;
26922
- if (fs9.existsSync(currentDir)) {
26923
- for (const file of fs9.readdirSync(currentDir)) {
26924
- fs9.unlinkSync(path9.join(currentDir, file));
26922
+ if (fs10.existsSync(currentDir)) {
26923
+ for (const file of fs10.readdirSync(currentDir)) {
26924
+ fs10.unlinkSync(path10.join(currentDir, file));
26925
26925
  }
26926
26926
  }
26927
- fs9.mkdirSync(currentDir, { recursive: true });
26928
- for (const file of fs9.readdirSync(targetDir)) {
26929
- fs9.copyFileSync(path9.join(targetDir, file), path9.join(currentDir, file));
26927
+ fs10.mkdirSync(currentDir, { recursive: true });
26928
+ for (const file of fs10.readdirSync(targetDir)) {
26929
+ fs10.copyFileSync(path10.join(targetDir, file), path10.join(currentDir, file));
26930
26930
  }
26931
26931
  } else {
26932
26932
  this.swapSymlink(newVersion);
@@ -26934,14 +26934,14 @@ MCowBQYDK2VwAyEAQHQAZThNX7+deJNyHl/5DgiAa1OHx7UQoJotam0JhUk=
26934
26934
  this.pruneOldVersions(versionsDir, newVersion);
26935
26935
  }
26936
26936
  swapSymlink(version) {
26937
- const currentLink = path9.join(this.bundleDir, "current");
26937
+ const currentLink = path10.join(this.bundleDir, "current");
26938
26938
  const tmpLink = `${currentLink}.new`;
26939
26939
  try {
26940
- fs9.unlinkSync(tmpLink);
26940
+ fs10.unlinkSync(tmpLink);
26941
26941
  } catch {
26942
26942
  }
26943
- fs9.symlinkSync(`versions/${version}`, tmpLink);
26944
- fs9.renameSync(tmpLink, currentLink);
26943
+ fs10.symlinkSync(`versions/${version}`, tmpLink);
26944
+ fs10.renameSync(tmpLink, currentLink);
26945
26945
  }
26946
26946
  pruneOldVersions(versionsDir, currentVersion) {
26947
26947
  const state = this.loadUpdateState();
@@ -26951,9 +26951,9 @@ MCowBQYDK2VwAyEAQHQAZThNX7+deJNyHl/5DgiAa1OHx7UQoJotam0JhUk=
26951
26951
  if (state?.confirmed_version)
26952
26952
  keep.add(state.confirmed_version);
26953
26953
  try {
26954
- for (const entry of fs9.readdirSync(versionsDir)) {
26954
+ for (const entry of fs10.readdirSync(versionsDir)) {
26955
26955
  if (!keep.has(entry)) {
26956
- fs9.rmSync(path9.join(versionsDir, entry), { recursive: true });
26956
+ fs10.rmSync(path10.join(versionsDir, entry), { recursive: true });
26957
26957
  }
26958
26958
  }
26959
26959
  } catch {
@@ -26961,26 +26961,26 @@ MCowBQYDK2VwAyEAQHQAZThNX7+deJNyHl/5DgiAa1OHx7UQoJotam0JhUk=
26961
26961
  }
26962
26962
  // --- Manifest & State I/O ---
26963
26963
  loadLocalManifest() {
26964
- const currentDir = path9.join(this.bundleDir, "current");
26965
- const manifestPath = path9.join(currentDir, "manifest.json");
26964
+ const currentDir = path10.join(this.bundleDir, "current");
26965
+ const manifestPath = path10.join(currentDir, "manifest.json");
26966
26966
  try {
26967
- return JSON.parse(fs9.readFileSync(manifestPath, "utf-8"));
26967
+ return JSON.parse(fs10.readFileSync(manifestPath, "utf-8"));
26968
26968
  } catch {
26969
26969
  return null;
26970
26970
  }
26971
26971
  }
26972
26972
  loadUpdateState() {
26973
- const statePath = path9.join(this.bundleDir, "update-state.json");
26973
+ const statePath = path10.join(this.bundleDir, "update-state.json");
26974
26974
  try {
26975
- return JSON.parse(fs9.readFileSync(statePath, "utf-8"));
26975
+ return JSON.parse(fs10.readFileSync(statePath, "utf-8"));
26976
26976
  } catch {
26977
26977
  return null;
26978
26978
  }
26979
26979
  }
26980
26980
  saveUpdateState(state) {
26981
- const statePath = path9.join(this.bundleDir, "update-state.json");
26982
- fs9.mkdirSync(path9.dirname(statePath), { recursive: true });
26983
- fs9.writeFileSync(statePath, JSON.stringify(state, null, 2));
26981
+ const statePath = path10.join(this.bundleDir, "update-state.json");
26982
+ fs10.mkdirSync(path10.dirname(statePath), { recursive: true });
26983
+ fs10.writeFileSync(statePath, JSON.stringify(state, null, 2));
26984
26984
  }
26985
26985
  // --- HTTP helpers ---
26986
26986
  httpGet(url, maxRedirects = 5) {
@@ -27030,14 +27030,14 @@ MCowBQYDK2VwAyEAQHQAZThNX7+deJNyHl/5DgiAa1OHx7UQoJotam0JhUk=
27030
27030
  reject(new Error(`HTTP ${res.statusCode} for ${url}`));
27031
27031
  return;
27032
27032
  }
27033
- const file = fs9.createWriteStream(dest);
27033
+ const file = fs10.createWriteStream(dest);
27034
27034
  res.pipe(file);
27035
27035
  file.on("finish", () => {
27036
27036
  file.close();
27037
27037
  resolve5();
27038
27038
  });
27039
27039
  file.on("error", (err) => {
27040
- fs9.unlinkSync(dest);
27040
+ fs10.unlinkSync(dest);
27041
27041
  reject(err);
27042
27042
  });
27043
27043
  });
@@ -27049,7 +27049,7 @@ MCowBQYDK2VwAyEAQHQAZThNX7+deJNyHl/5DgiAa1OHx7UQoJotam0JhUk=
27049
27049
  }
27050
27050
  cleanDir(dir) {
27051
27051
  try {
27052
- fs9.rmSync(dir, { recursive: true });
27052
+ fs10.rmSync(dir, { recursive: true });
27053
27053
  } catch {
27054
27054
  }
27055
27055
  }
@@ -27506,10 +27506,10 @@ var ParallClient = class _ParallClient {
27506
27506
  * REFRESH_THRESHOLD_S, refresh it **before** sending the request.
27507
27507
  * No-op when the token is still fresh, missing, or un-parseable.
27508
27508
  */
27509
- async ensureFreshToken(path11) {
27509
+ async ensureFreshToken(path12) {
27510
27510
  if (!this.token || !this.getRefreshToken)
27511
27511
  return;
27512
- const pathSuffix = path11.replace(/^\/api\/v1/, "");
27512
+ const pathSuffix = path12.replace(/^\/api\/v1/, "");
27513
27513
  if (_ParallClient.AUTH_PATHS.has(pathSuffix))
27514
27514
  return;
27515
27515
  const exp = _ParallClient.decodeJwtExp(this.token);
@@ -27541,11 +27541,11 @@ var ParallClient = class _ParallClient {
27541
27541
  this.refreshPromise = null;
27542
27542
  }
27543
27543
  }
27544
- async request(method, path11, body, query, retried = false, opts) {
27544
+ async request(method, path12, body, query, retried = false, opts) {
27545
27545
  if (!retried) {
27546
- await this.ensureFreshToken(path11);
27546
+ await this.ensureFreshToken(path12);
27547
27547
  }
27548
- let url = `${this.baseUrl}${path11}`;
27548
+ let url = `${this.baseUrl}${path12}`;
27549
27549
  if (query) {
27550
27550
  const params = new URLSearchParams();
27551
27551
  for (const [key, value] of Object.entries(query)) {
@@ -27570,12 +27570,12 @@ var ParallClient = class _ParallClient {
27570
27570
  throw _ParallClient.normalizeFetchError(err);
27571
27571
  }
27572
27572
  if (res.status === 401) {
27573
- const pathSuffix = path11.replace(/^\/api\/v1/, "");
27573
+ const pathSuffix = path12.replace(/^\/api\/v1/, "");
27574
27574
  const isAuthPath = _ParallClient.AUTH_PATHS.has(pathSuffix);
27575
27575
  if (!retried && !isAuthPath && this.getRefreshToken) {
27576
27576
  const refreshed = await this.tryRefresh();
27577
27577
  if (refreshed) {
27578
- return this.request(method, path11, body, query, true, opts);
27578
+ return this.request(method, path12, body, query, true, opts);
27579
27579
  }
27580
27580
  }
27581
27581
  if (this.onTokenExpired && !isAuthPath) {
@@ -27584,15 +27584,7 @@ var ParallClient = class _ParallClient {
27584
27584
  }
27585
27585
  if (!res.ok) {
27586
27586
  const rawErrorBody = await res.json().catch(() => ({}));
27587
- const errorBody = rawErrorBody !== null && typeof rawErrorBody === "object" ? rawErrorBody : {};
27588
- const errorObj = errorBody?.error && typeof errorBody.error === "object" ? errorBody.error : void 0;
27589
- const errMsg = errorObj?.message ?? (typeof errorBody?.error === "string" ? errorBody.error : void 0);
27590
- const errCode = errorObj?.code ?? (typeof errorBody?.code === "string" ? errorBody.code : void 0);
27591
- const apiError = new ApiError(res.status, errMsg ?? res.statusText, errCode);
27592
- const { error: _e, code: _c, message: _m, ...extras } = errorBody;
27593
- if (Object.keys(extras).length > 0)
27594
- apiError.extras = extras;
27595
- throw apiError;
27587
+ throw buildApiError(res, rawErrorBody);
27596
27588
  }
27597
27589
  if (res.status === 204)
27598
27590
  return void 0;
@@ -27612,15 +27604,15 @@ var ParallClient = class _ParallClient {
27612
27604
  * hit the 100 MiB cap, so a longer 5-minute timeout is used so a
27613
27605
  * 50 MiB blob on a slow connection doesn't get chopped at 15 s.
27614
27606
  */
27615
- async multipartRequest(method, path11, body, retried = false) {
27607
+ async multipartRequest(method, path12, body, retried = false) {
27616
27608
  if (!retried) {
27617
- await this.ensureFreshToken(path11);
27609
+ await this.ensureFreshToken(path12);
27618
27610
  }
27619
27611
  const { "Content-Type": _drop, ...headers } = this.buildHeaders();
27620
27612
  void _drop;
27621
27613
  let res;
27622
27614
  try {
27623
- res = await fetch(`${this.baseUrl}${path11}`, {
27615
+ res = await fetch(`${this.baseUrl}${path12}`, {
27624
27616
  method,
27625
27617
  headers,
27626
27618
  body,
@@ -27630,12 +27622,12 @@ var ParallClient = class _ParallClient {
27630
27622
  throw _ParallClient.normalizeFetchError(err);
27631
27623
  }
27632
27624
  if (res.status === 401) {
27633
- const pathSuffix = path11.replace(/^\/api\/v1/, "");
27625
+ const pathSuffix = path12.replace(/^\/api\/v1/, "");
27634
27626
  const isAuthPath = _ParallClient.AUTH_PATHS.has(pathSuffix);
27635
27627
  if (!retried && !isAuthPath && this.getRefreshToken) {
27636
27628
  const refreshed = await this.tryRefresh();
27637
27629
  if (refreshed) {
27638
- return this.multipartRequest(method, path11, body, true);
27630
+ return this.multipartRequest(method, path12, body, true);
27639
27631
  }
27640
27632
  }
27641
27633
  if (this.onTokenExpired && !isAuthPath) {
@@ -27644,15 +27636,7 @@ var ParallClient = class _ParallClient {
27644
27636
  }
27645
27637
  if (!res.ok) {
27646
27638
  const rawErrorBody = await res.json().catch(() => ({}));
27647
- const errorBody = rawErrorBody !== null && typeof rawErrorBody === "object" ? rawErrorBody : {};
27648
- const errorObj = errorBody?.error && typeof errorBody.error === "object" ? errorBody.error : void 0;
27649
- const errMsg = errorObj?.message ?? (typeof errorBody?.error === "string" ? errorBody.error : void 0);
27650
- const errCode = errorObj?.code ?? (typeof errorBody?.code === "string" ? errorBody.code : void 0);
27651
- const apiError = new ApiError(res.status, errMsg ?? res.statusText, errCode);
27652
- const { error: _e, code: _c, message: _m, ...extras } = errorBody;
27653
- if (Object.keys(extras).length > 0)
27654
- apiError.extras = extras;
27655
- throw apiError;
27639
+ throw buildApiError(res, rawErrorBody);
27656
27640
  }
27657
27641
  if (res.status === 204)
27658
27642
  return void 0;
@@ -28233,8 +28217,8 @@ var ParallClient = class _ParallClient {
28233
28217
  async requestMachineUpdate(orgId, machineId, mandatory = false) {
28234
28218
  await this.request("POST", ENDPOINTS.MACHINE_REQUEST_UPDATE(orgId, machineId), { mandatory });
28235
28219
  }
28236
- async browseMachineFilesystem(orgId, machineId, path11) {
28237
- return this.request("POST", ENDPOINTS.MACHINE_BROWSE(orgId, machineId), { path: path11 }, void 0, false, { timeoutMs: 15e3 });
28220
+ async browseMachineFilesystem(orgId, machineId, path12) {
28221
+ return this.request("POST", ENDPOINTS.MACHINE_BROWSE(orgId, machineId), { path: path12 }, void 0, false, { timeoutMs: 15e3 });
28238
28222
  }
28239
28223
  /** Create a new machine key. Returns the raw key string (shown once) + metadata. */
28240
28224
  async createMachineKey(orgId, machineId, name) {
@@ -28334,15 +28318,7 @@ var ParallClient = class _ParallClient {
28334
28318
  return null;
28335
28319
  if (!res.ok) {
28336
28320
  const rawErrorBody = await res.json().catch(() => ({}));
28337
- const errorBody = rawErrorBody !== null && typeof rawErrorBody === "object" ? rawErrorBody : {};
28338
- const errorObj = errorBody?.error && typeof errorBody.error === "object" ? errorBody.error : void 0;
28339
- const errMsg = errorObj?.message ?? (typeof errorBody?.error === "string" ? errorBody.error : void 0);
28340
- const errCode = errorObj?.code ?? (typeof errorBody?.code === "string" ? errorBody.code : void 0);
28341
- const apiError = new ApiError(res.status, errMsg ?? res.statusText, errCode);
28342
- const { error: _e, code: _c, message: _m, ...extras } = errorBody;
28343
- if (Object.keys(extras).length > 0)
28344
- apiError.extras = extras;
28345
- throw apiError;
28321
+ throw buildApiError(res, rawErrorBody);
28346
28322
  }
28347
28323
  return res.json();
28348
28324
  }
@@ -28603,8 +28579,8 @@ var ParallClient = class _ParallClient {
28603
28579
  async deleteWikiPathScope(orgId, wikiId, scopeId) {
28604
28580
  await this.request("DELETE", ENDPOINTS.WIKI_PATH_SCOPE(orgId, wikiId, scopeId));
28605
28581
  }
28606
- async getWikiAccessStatus(orgId, wikiId, path11) {
28607
- return this.request("GET", ENDPOINTS.WIKI_ACCESS_STATUS(orgId, wikiId), void 0, path11 ? { path: path11 } : void 0);
28582
+ async getWikiAccessStatus(orgId, wikiId, path12) {
28583
+ return this.request("GET", ENDPOINTS.WIKI_ACCESS_STATUS(orgId, wikiId), void 0, path12 ? { path: path12 } : void 0);
28608
28584
  }
28609
28585
  async createWikiAccessRequest(orgId, wikiId, data) {
28610
28586
  await this.request("POST", ENDPOINTS.WIKI_ACCESS_REQUESTS(orgId, wikiId), data);
@@ -28613,14 +28589,14 @@ var ParallClient = class _ParallClient {
28613
28589
  async getWikiCommits(orgId, wikiId, params) {
28614
28590
  return this.request("GET", ENDPOINTS.WIKI_COMMITS(orgId, wikiId), void 0, params);
28615
28591
  }
28616
- async getWikiFileCommits(orgId, wikiId, path11, params) {
28592
+ async getWikiFileCommits(orgId, wikiId, path12, params) {
28617
28593
  return this.request("GET", ENDPOINTS.WIKI_FILE_COMMITS(orgId, wikiId), void 0, {
28618
- path: path11,
28594
+ path: path12,
28619
28595
  ...params
28620
28596
  });
28621
28597
  }
28622
- async getWikiBlame(orgId, wikiId, path11, ref) {
28623
- return this.request("GET", ENDPOINTS.WIKI_BLAME(orgId, wikiId), void 0, { path: path11, ref });
28598
+ async getWikiBlame(orgId, wikiId, path12, ref) {
28599
+ return this.request("GET", ENDPOINTS.WIKI_BLAME(orgId, wikiId), void 0, { path: path12, ref });
28624
28600
  }
28625
28601
  // ---- Wiki Operations (audit log) ----
28626
28602
  async getWikiOperations(orgId, wikiId, params) {
@@ -28808,6 +28784,12 @@ var ApiError = class extends Error {
28808
28784
  status;
28809
28785
  code;
28810
28786
  extras;
28787
+ /** Attempted action (authorization denials) — e.g. "chat.add_member". */
28788
+ action;
28789
+ /** Target resource URI that was evaluated — e.g. "prll://cht_…". */
28790
+ resourceUri;
28791
+ /** Whether the action is approval-executable (PERMISSION_DENIED only). */
28792
+ approvable;
28811
28793
  constructor(status, message, code) {
28812
28794
  super(message);
28813
28795
  this.status = status;
@@ -28815,6 +28797,33 @@ var ApiError = class extends Error {
28815
28797
  this.name = "ApiError";
28816
28798
  }
28817
28799
  };
28800
+ function buildApiError(res, rawErrorBody) {
28801
+ const errorBody = rawErrorBody !== null && typeof rawErrorBody === "object" ? rawErrorBody : {};
28802
+ const errorObj = errorBody.error && typeof errorBody.error === "object" ? errorBody.error : void 0;
28803
+ const errMsg = (typeof errorObj?.message === "string" ? errorObj.message : void 0) ?? (typeof errorBody.message === "string" ? errorBody.message : void 0) ?? (typeof errorBody.error === "string" ? errorBody.error : void 0);
28804
+ const errCode = (typeof errorObj?.code === "string" ? errorObj.code : void 0) ?? (typeof errorBody.code === "string" ? errorBody.code : void 0);
28805
+ const apiError = new ApiError(res.status, errMsg ?? res.statusText, errCode);
28806
+ const anchors = errorObj ?? errorBody;
28807
+ if (typeof anchors.action === "string")
28808
+ apiError.action = anchors.action;
28809
+ if (typeof anchors.resource_uri === "string")
28810
+ apiError.resourceUri = anchors.resource_uri;
28811
+ if (typeof anchors.approvable === "boolean")
28812
+ apiError.approvable = anchors.approvable;
28813
+ const structural = /* @__PURE__ */ new Set(["error", "code", "message", "status"]);
28814
+ const extras = {};
28815
+ for (const [k, v] of Object.entries(errorBody))
28816
+ if (!structural.has(k))
28817
+ extras[k] = v;
28818
+ if (errorObj) {
28819
+ for (const [k, v] of Object.entries(errorObj))
28820
+ if (!structural.has(k))
28821
+ extras[k] = v;
28822
+ }
28823
+ if (Object.keys(extras).length > 0)
28824
+ apiError.extras = extras;
28825
+ return apiError;
28826
+ }
28818
28827
 
28819
28828
  // ts/sdk/dist/ws.js
28820
28829
  function isRetryableNetworkError(err) {
@@ -29283,8 +29292,8 @@ init_config();
29283
29292
 
29284
29293
  // ts/daemon/dist/supervisor.js
29285
29294
  import { spawn as spawn3 } from "node:child_process";
29286
- import * as fs8 from "node:fs";
29287
- import * as path8 from "node:path";
29295
+ import * as fs9 from "node:fs";
29296
+ import * as path9 from "node:path";
29288
29297
 
29289
29298
  // ts/daemon/dist/filesystem.js
29290
29299
  import * as fs2 from "fs";
@@ -29913,9 +29922,8 @@ function isNodeError(err) {
29913
29922
  }
29914
29923
 
29915
29924
  // ts/daemon/dist/clip-runtime/process-manager.js
29916
- import * as fs6 from "node:fs";
29917
- import * as path6 from "node:path";
29918
- import { execFileSync } from "node:child_process";
29925
+ import * as fs7 from "node:fs";
29926
+ import * as path7 from "node:path";
29919
29927
 
29920
29928
  // ts/daemon/dist/clip-runtime/process.js
29921
29929
  import { spawn as spawn2 } from "node:child_process";
@@ -30487,6 +30495,39 @@ var ClipProcess = class {
30487
30495
  }
30488
30496
  };
30489
30497
 
30498
+ // ts/daemon/dist/clip-runtime/bun-resolver.js
30499
+ import * as fs6 from "node:fs";
30500
+ import * as path6 from "node:path";
30501
+ import { execFileSync } from "node:child_process";
30502
+ function findBunBinary() {
30503
+ const isWindows = process.platform === "win32";
30504
+ const binName = isWindows ? "bun.exe" : "bun";
30505
+ const embedded = path6.join(path6.dirname(process.execPath), binName);
30506
+ if (fs6.existsSync(embedded))
30507
+ return embedded;
30508
+ if (!isWindows) {
30509
+ const candidates = [
30510
+ path6.join(process.env.HOME || "", ".bun", "bin", "bun"),
30511
+ "/usr/local/bin/bun",
30512
+ "/opt/homebrew/bin/bun"
30513
+ ];
30514
+ for (const candidate of candidates) {
30515
+ if (fs6.existsSync(candidate))
30516
+ return candidate;
30517
+ }
30518
+ }
30519
+ const lookupCmd = isWindows ? "where.exe" : "which";
30520
+ const lookupArg = isWindows ? "bun.exe" : "bun";
30521
+ try {
30522
+ const result = execFileSync(lookupCmd, [lookupArg], { encoding: "utf-8" }).trim();
30523
+ const firstLine = result.split("\n")[0]?.trim();
30524
+ if (firstLine)
30525
+ return firstLine;
30526
+ } catch {
30527
+ }
30528
+ throw new Error("bun binary not found \u2014 install Bun (https://bun.sh) or set bunPath option");
30529
+ }
30530
+
30490
30531
  // ts/daemon/dist/clip-runtime/process-manager.js
30491
30532
  var ClipProcessManager = class {
30492
30533
  bunPath;
@@ -30664,10 +30705,10 @@ var ClipProcessManager = class {
30664
30705
  * Reads clip-config.json if present, or scans subdirectories for clip.json files.
30665
30706
  */
30666
30707
  async loadInstalledClips() {
30667
- const configFile = path6.join(path6.dirname(this.clipsDir), "clip-config.json");
30668
- if (fs6.existsSync(configFile)) {
30708
+ const configFile = path7.join(path7.dirname(this.clipsDir), "clip-config.json");
30709
+ if (fs7.existsSync(configFile)) {
30669
30710
  try {
30670
- const content = fs6.readFileSync(configFile, "utf-8");
30711
+ const content = fs7.readFileSync(configFile, "utf-8");
30671
30712
  const configs = JSON.parse(content);
30672
30713
  for (const config of configs) {
30673
30714
  this.registerClip(config);
@@ -30677,18 +30718,18 @@ var ClipProcessManager = class {
30677
30718
  console.warn("[clip-manager] failed to parse clip-config.json, scanning directory");
30678
30719
  }
30679
30720
  }
30680
- if (!fs6.existsSync(this.clipsDir))
30721
+ if (!fs7.existsSync(this.clipsDir))
30681
30722
  return;
30682
- const entries = fs6.readdirSync(this.clipsDir, { withFileTypes: true });
30723
+ const entries = fs7.readdirSync(this.clipsDir, { withFileTypes: true });
30683
30724
  for (const entry of entries) {
30684
30725
  if (!entry.isDirectory())
30685
30726
  continue;
30686
- const clipDir = path6.join(this.clipsDir, entry.name);
30687
- const clipJsonPath = path6.join(clipDir, "clip.json");
30688
- const pkgJsonPath = path6.join(clipDir, "package.json");
30689
- if (fs6.existsSync(clipJsonPath)) {
30727
+ const clipDir = path7.join(this.clipsDir, entry.name);
30728
+ const clipJsonPath = path7.join(clipDir, "clip.json");
30729
+ const pkgJsonPath = path7.join(clipDir, "package.json");
30730
+ if (fs7.existsSync(clipJsonPath)) {
30690
30731
  try {
30691
- const clipJson = JSON.parse(fs6.readFileSync(clipJsonPath, "utf-8"));
30732
+ const clipJson = JSON.parse(fs7.readFileSync(clipJsonPath, "utf-8"));
30692
30733
  this.registerClip({
30693
30734
  name: clipJson.name || entry.name,
30694
30735
  package: clipJson.name,
@@ -30699,9 +30740,9 @@ var ClipProcessManager = class {
30699
30740
  } catch {
30700
30741
  console.warn(`[clip-manager] failed to parse clip.json in ${clipDir}`);
30701
30742
  }
30702
- } else if (fs6.existsSync(pkgJsonPath)) {
30743
+ } else if (fs7.existsSync(pkgJsonPath)) {
30703
30744
  try {
30704
- const pkgJson = JSON.parse(fs6.readFileSync(pkgJsonPath, "utf-8"));
30745
+ const pkgJson = JSON.parse(fs7.readFileSync(pkgJsonPath, "utf-8"));
30705
30746
  this.registerClip({
30706
30747
  name: pkgJson.name || entry.name,
30707
30748
  package: pkgJson.name,
@@ -30740,8 +30781,14 @@ var ClipProcessManager = class {
30740
30781
  async spawnProcess(config) {
30741
30782
  const proc = new ClipProcess(config);
30742
30783
  const clipDataDir = this.ensureClipDataDir(config);
30743
- proc.spawn(this.resolveBun(), {
30744
- PINIX_DATA_DIR: clipDataDir
30784
+ const bunPath = this.resolveBun();
30785
+ proc.spawn(bunPath, {
30786
+ PINIX_DATA_DIR: clipDataDir,
30787
+ // Expose the embedded bun's directory on the clip's PATH so a clip that
30788
+ // shells out to `bun` by name resolves it — the daemon's launchd PATH
30789
+ // does not include Frameworks/. Symmetric with installDeps(); relies on
30790
+ // the embedded binary being named `bun` (Frameworks/bun).
30791
+ PATH: `${path7.dirname(bunPath)}${path7.delimiter}${process.env.PATH ?? ""}`
30745
30792
  });
30746
30793
  this.setStatus(config.name, "running", "starting");
30747
30794
  try {
@@ -30770,8 +30817,8 @@ var ClipProcessManager = class {
30770
30817
  return proc;
30771
30818
  }
30772
30819
  ensureClipDataDir(config) {
30773
- const dir = path6.join(this.dataDir, config.name);
30774
- fs6.mkdirSync(dir, { recursive: true });
30820
+ const dir = path7.join(this.dataDir, config.name);
30821
+ fs7.mkdirSync(dir, { recursive: true });
30775
30822
  return dir;
30776
30823
  }
30777
30824
  removeIfSame(name, proc) {
@@ -30789,30 +30836,6 @@ var ClipProcessManager = class {
30789
30836
  }
30790
30837
  }
30791
30838
  };
30792
- function findBunBinary() {
30793
- const isWindows = process.platform === "win32";
30794
- if (!isWindows) {
30795
- const candidates = [
30796
- path6.join(process.env.HOME || "", ".bun", "bin", "bun"),
30797
- "/usr/local/bin/bun",
30798
- "/opt/homebrew/bin/bun"
30799
- ];
30800
- for (const candidate of candidates) {
30801
- if (fs6.existsSync(candidate))
30802
- return candidate;
30803
- }
30804
- }
30805
- const lookupCmd = isWindows ? "where.exe" : "which";
30806
- const lookupArg = isWindows ? "bun.exe" : "bun";
30807
- try {
30808
- const result = execFileSync(lookupCmd, [lookupArg], { encoding: "utf-8" }).trim();
30809
- const firstLine = result.split("\n")[0]?.trim();
30810
- if (firstLine)
30811
- return firstLine;
30812
- } catch {
30813
- }
30814
- throw new Error("bun binary not found \u2014 install Bun (https://bun.sh) or set bunPath option");
30815
- }
30816
30839
 
30817
30840
  // ts/daemon/dist/clip-runtime/clip-provider.js
30818
30841
  import * as http2 from "node:http2";
@@ -30995,7 +31018,7 @@ var ClipProvider = class _ClipProvider {
30995
31018
  void this.openStream();
30996
31019
  return;
30997
31020
  }
30998
- this.sendProviderMessage({ heartbeat: {} }).catch((err) => {
31021
+ this.sendProviderMessage({ ping: { sentAtUnixMs: Date.now() } }).catch((err) => {
30999
31022
  this.opts.log.warn(`[clip-provider] heartbeat send failed: ${String(err)}`);
31000
31023
  });
31001
31024
  }, _ClipProvider.HEARTBEAT_INTERVAL_MS);
@@ -31024,12 +31047,12 @@ var ClipProvider = class _ClipProvider {
31024
31047
  // ---------------------------------------------------------------------------
31025
31048
  subscribeStatusChanges() {
31026
31049
  const mgr = this.opts.clipManager;
31027
- this.statusUnsubscribe = mgr.addStatusListener((name, status, _message) => {
31050
+ this.statusUnsubscribe = mgr.addStatusListener((name, status, message) => {
31028
31051
  if (!this.connected)
31029
31052
  return;
31030
- const protoStatus = status === "running" ? "CLIP_ONLINE_STATUS_ONLINE" : status === "error" ? "CLIP_ONLINE_STATUS_ERROR" : "CLIP_ONLINE_STATUS_OFFLINE";
31053
+ const protoStatus = status === "running" ? "CLIP_STATUS_RUNNING" : status === "error" ? "CLIP_STATUS_ERROR" : "CLIP_STATUS_SLEEPING";
31031
31054
  this.sendProviderMessage({
31032
- clipStatusChanged: { alias: name, status: protoStatus }
31055
+ clipStatusChanged: { name, status: protoStatus, message }
31033
31056
  }).catch((err) => {
31034
31057
  this.opts.log.warn(`[clip-provider] status change send failed: ${String(err)}`);
31035
31058
  });
@@ -31048,18 +31071,16 @@ var ClipProvider = class _ClipProvider {
31048
31071
  // Message handling
31049
31072
  // ---------------------------------------------------------------------------
31050
31073
  handleHubMessage(msg) {
31051
- if (msg.registered) {
31052
- this.handleRegistered(msg.registered);
31074
+ if (msg.registerResponse) {
31075
+ this.handleRegistered(msg.registerResponse);
31053
31076
  } else if (msg.invokeCommand) {
31054
31077
  void this.handleInvokeCommand(msg.invokeCommand);
31055
- } else if (msg.heartbeat !== void 0) {
31056
- this.sendProviderMessage({ heartbeat: {} }).catch(() => {
31057
- });
31078
+ } else if (msg.pong !== void 0) {
31058
31079
  }
31059
31080
  }
31060
31081
  handleRegistered(reg) {
31061
31082
  if (reg.accepted) {
31062
- this.opts.log.info(`[clip-provider] registered with hub (org=${reg.orgId})`);
31083
+ this.opts.log.info(`[clip-provider] registered with hub (org=${this.opts.orgId})`);
31063
31084
  this.connected = true;
31064
31085
  this.reconnectAttempt = 0;
31065
31086
  this.startHeartbeat();
@@ -31071,7 +31092,7 @@ var ClipProvider = class _ClipProvider {
31071
31092
  }
31072
31093
  }
31073
31094
  async handleInvokeCommand(cmd) {
31074
- const { requestId, clipAlias, commandName } = cmd;
31095
+ const { requestId, clipName, command } = cmd;
31075
31096
  const timeoutMs = cmd.timeoutMs ?? 3e4;
31076
31097
  try {
31077
31098
  let input;
@@ -31085,7 +31106,7 @@ var ClipProvider = class _ClipProvider {
31085
31106
  }
31086
31107
  let timer;
31087
31108
  const output = await Promise.race([
31088
- this.opts.clipManager.invoke(clipAlias, commandName, input),
31109
+ this.opts.clipManager.invoke(clipName, command, input),
31089
31110
  new Promise((_, reject) => {
31090
31111
  timer = setTimeout(() => reject(new Error("invoke timeout")), timeoutMs);
31091
31112
  })
@@ -31102,7 +31123,10 @@ var ClipProvider = class _ClipProvider {
31102
31123
  await this.sendProviderMessage({
31103
31124
  invokeResult: {
31104
31125
  requestId,
31105
- error: isCommandError ? err.message : String(err),
31126
+ error: {
31127
+ code: isCommandError ? "CLIP_COMMAND_ERROR" : "INVOKE_FAILED",
31128
+ message: isCommandError ? err.message : String(err)
31129
+ },
31106
31130
  errorIsCommand: isCommandError,
31107
31131
  done: true
31108
31132
  }
@@ -31118,8 +31142,7 @@ var ClipProvider = class _ClipProvider {
31118
31142
  await this.sendProviderMessage({
31119
31143
  register: {
31120
31144
  providerName: this.opts.providerName,
31121
- clips,
31122
- orgId: this.opts.orgId
31145
+ clips
31123
31146
  }
31124
31147
  });
31125
31148
  }
@@ -31147,26 +31170,50 @@ var ClipProvider = class _ClipProvider {
31147
31170
  clipConfigToRegistration(clip) {
31148
31171
  const manifest = clip.manifest;
31149
31172
  const commands = manifest ? manifest.commandDetails.map((cmd) => this.commandDetailToInfo(cmd)) : [];
31173
+ const pkg = manifest?.package ?? clip.package ?? clip.name;
31150
31174
  return {
31151
31175
  alias: clip.name,
31152
- name: manifest?.package ?? clip.package ?? clip.name,
31176
+ package: pkg,
31153
31177
  version: manifest?.version ?? clip.version ?? "",
31154
- commands
31178
+ domain: manifest?.domain,
31179
+ commands,
31180
+ hasWeb: manifest?.hasWeb ?? false,
31181
+ dependencies: this.dependencyNames(manifest?.dependencies),
31182
+ tokenProtected: Boolean(clip.token),
31183
+ name: pkg,
31184
+ patterns: manifest?.patterns,
31185
+ entities: this.stringEntities(manifest?.entities),
31186
+ description: manifest?.description
31155
31187
  };
31156
31188
  }
31157
31189
  commandDetailToInfo(detail) {
31158
31190
  return {
31159
31191
  name: detail.name,
31160
31192
  description: detail.description ?? "",
31161
- inputSchema: detail.input ? Buffer.from(detail.input, "utf-8").toString("base64") : void 0,
31162
- outputSchema: detail.output ? Buffer.from(detail.output, "utf-8").toString("base64") : void 0
31193
+ input: detail.input,
31194
+ output: detail.output
31163
31195
  };
31164
31196
  }
31197
+ dependencyNames(deps) {
31198
+ if (!deps)
31199
+ return void 0;
31200
+ const names = Object.entries(deps).map(([slot, dep]) => dep.package ?? slot).filter((name) => name.length > 0);
31201
+ return names.length > 0 ? names : void 0;
31202
+ }
31203
+ stringEntities(entities) {
31204
+ if (!entities)
31205
+ return void 0;
31206
+ const out = {};
31207
+ for (const [key, value] of Object.entries(entities)) {
31208
+ out[key] = typeof value === "string" ? value : JSON.stringify(value);
31209
+ }
31210
+ return out;
31211
+ }
31165
31212
  };
31166
31213
 
31167
31214
  // ts/daemon/dist/clip-runtime/clip-installer.js
31168
- import * as fs7 from "node:fs";
31169
- import * as path7 from "node:path";
31215
+ import * as fs8 from "node:fs";
31216
+ import * as path8 from "node:path";
31170
31217
  import * as crypto from "node:crypto";
31171
31218
  import { execFileSync as execFileSync2 } from "node:child_process";
31172
31219
  import { pipeline } from "node:stream/promises";
@@ -31245,7 +31292,7 @@ async function httpDownload(url, destPath, maxRedirects = 10) {
31245
31292
  reject(new Error(`download failed: HTTP ${res.statusCode} for ${url}`));
31246
31293
  return;
31247
31294
  }
31248
- const ws = fs7.createWriteStream(destPath);
31295
+ const ws = fs8.createWriteStream(destPath);
31249
31296
  pipeline(res, ws).then(resolve5, reject);
31250
31297
  });
31251
31298
  req.on("error", reject);
@@ -31377,11 +31424,11 @@ function verifyChecksum(filePath, algo, expectedHex) {
31377
31424
  return;
31378
31425
  }
31379
31426
  const hash = crypto.createHash(algo);
31380
- const content = fs7.readFileSync(filePath);
31427
+ const content = fs8.readFileSync(filePath);
31381
31428
  hash.update(content);
31382
31429
  const actual = hash.digest("hex");
31383
31430
  if (actual !== expectedHex) {
31384
- throw new Error(`checksum mismatch for ${path7.basename(filePath)}: expected ${algo}:${expectedHex}, got ${algo}:${actual}`);
31431
+ throw new Error(`checksum mismatch for ${path8.basename(filePath)}: expected ${algo}:${expectedHex}, got ${algo}:${actual}`);
31385
31432
  }
31386
31433
  }
31387
31434
  function validateTarEntries(tarballPath) {
@@ -31398,18 +31445,18 @@ function validateTarEntries(tarballPath) {
31398
31445
  const trimmed = entry.trim();
31399
31446
  if (!trimmed)
31400
31447
  continue;
31401
- if (path7.isAbsolute(trimmed)) {
31448
+ if (path8.isAbsolute(trimmed)) {
31402
31449
  throw new Error(`tarball contains absolute path: "${trimmed}"`);
31403
31450
  }
31404
- const normalized = path7.normalize(trimmed);
31405
- if (normalized.startsWith("..") || normalized.includes(`${path7.sep}..${path7.sep}`)) {
31451
+ const normalized = path8.normalize(trimmed);
31452
+ if (normalized.startsWith("..") || normalized.includes(`${path8.sep}..${path8.sep}`)) {
31406
31453
  throw new Error(`tarball contains path traversal: "${trimmed}"`);
31407
31454
  }
31408
31455
  }
31409
31456
  }
31410
31457
  function extractTarball(tarballPath, destDir) {
31411
31458
  const stripComponents = detectStripComponents(tarballPath);
31412
- fs7.mkdirSync(destDir, { recursive: true });
31459
+ fs8.mkdirSync(destDir, { recursive: true });
31413
31460
  try {
31414
31461
  execFileSync2("tar", [
31415
31462
  "xzf",
@@ -31450,74 +31497,95 @@ function detectStripComponents(tarballPath) {
31450
31497
  return commonPrefix ? 1 : 0;
31451
31498
  }
31452
31499
  function installDeps(clipDir) {
31453
- const pkgJsonPath = path7.join(clipDir, "package.json");
31454
- if (!fs7.existsSync(pkgJsonPath))
31500
+ const pkgJsonPath = path8.join(clipDir, "package.json");
31501
+ if (!fs8.existsSync(pkgJsonPath))
31455
31502
  return;
31456
31503
  let hasDeps = false;
31457
31504
  try {
31458
- const pkg = JSON.parse(fs7.readFileSync(pkgJsonPath, "utf-8"));
31505
+ const pkg = JSON.parse(fs8.readFileSync(pkgJsonPath, "utf-8"));
31459
31506
  hasDeps = !!(pkg.dependencies && Object.keys(pkg.dependencies).length > 0);
31460
31507
  } catch {
31461
31508
  }
31462
- const runners = [
31463
- { cmd: "bun", args: ["install", "--frozen-lockfile"] },
31464
- { cmd: "bun", args: ["install"] },
31465
- { cmd: "npm", args: ["install", "--production"] }
31466
- ];
31467
- for (const runner of runners) {
31468
- try {
31469
- execFileSync2(runner.cmd, runner.args, {
31470
- cwd: clipDir,
31471
- stdio: "pipe",
31472
- timeout: 12e4
31473
- });
31474
- return;
31475
- } catch {
31509
+ const failures = [];
31510
+ let bunPath = null;
31511
+ try {
31512
+ bunPath = findBunBinary();
31513
+ } catch (err) {
31514
+ failures.push(`resolve bun: ${err instanceof Error ? err.message : String(err)}`);
31515
+ }
31516
+ if (bunPath) {
31517
+ const bunEnv = {
31518
+ ...process.env,
31519
+ PATH: `${path8.dirname(bunPath)}${path8.delimiter}${process.env.PATH ?? ""}`
31520
+ };
31521
+ for (const args of [["install", "--frozen-lockfile"], ["install"]]) {
31522
+ try {
31523
+ execFileSync2(bunPath, args, {
31524
+ cwd: clipDir,
31525
+ stdio: "pipe",
31526
+ timeout: 12e4,
31527
+ env: bunEnv
31528
+ });
31529
+ return;
31530
+ } catch (err) {
31531
+ failures.push(`bun ${args.join(" ")}: ${err instanceof Error ? err.message : String(err)}`);
31532
+ }
31476
31533
  }
31477
31534
  }
31535
+ try {
31536
+ execFileSync2("npm", ["install", "--production"], {
31537
+ cwd: clipDir,
31538
+ stdio: "pipe",
31539
+ timeout: 12e4
31540
+ });
31541
+ return;
31542
+ } catch (err) {
31543
+ failures.push(`npm install: ${err instanceof Error ? err.message : String(err)}`);
31544
+ }
31478
31545
  if (hasDeps) {
31479
- throw new Error(`failed to install dependencies in ${clipDir} \u2014 clip declares dependencies but no package manager succeeded`);
31546
+ throw new Error(`failed to install dependencies in ${clipDir} \u2014 clip declares dependencies but no package manager succeeded:
31547
+ ${failures.join("\n ")}`);
31480
31548
  }
31481
- console.warn(`[clip-installer] could not run package manager in ${clipDir} (no dependencies declared, continuing)`);
31549
+ console.warn(`[clip-installer] could not run a package manager in ${clipDir} (no dependencies declared, continuing): ${failures.join("; ")}`);
31482
31550
  }
31483
31551
  async function installClip(opts) {
31484
31552
  const registryUrl = (opts.registryUrl ?? DEFAULT_REGISTRY_URL).replace(/\/+$/, "");
31485
31553
  const parsed = parseSource(opts.source);
31486
31554
  const alias = opts.alias ?? deriveAlias(parsed);
31487
- const destDir = path7.join(opts.clipsDir, alias);
31555
+ const destDir = path8.join(opts.clipsDir, alias);
31488
31556
  const versionMeta = await resolveVersionMeta(registryUrl, parsed);
31489
- const tmpDir = path7.join(opts.clipsDir, `.tmp-${alias}-${Date.now()}`);
31490
- fs7.mkdirSync(tmpDir, { recursive: true });
31491
- const tarballPath = path7.join(tmpDir, `${alias}-${versionMeta.version}.tgz`);
31492
- const stageDir = path7.join(tmpDir, "stage");
31557
+ const tmpDir = path8.join(opts.clipsDir, `.tmp-${alias}-${Date.now()}`);
31558
+ fs8.mkdirSync(tmpDir, { recursive: true });
31559
+ const tarballPath = path8.join(tmpDir, `${alias}-${versionMeta.version}.tgz`);
31560
+ const stageDir = path8.join(tmpDir, "stage");
31493
31561
  try {
31494
31562
  await httpDownload(versionMeta.tarball, tarballPath);
31495
31563
  verifyChecksum(tarballPath, versionMeta.checksumAlgo, versionMeta.checksumHex);
31496
31564
  validateTarEntries(tarballPath);
31497
31565
  extractTarball(tarballPath, stageDir);
31498
31566
  installDeps(stageDir);
31499
- const backupDir = path7.join(opts.clipsDir, `.backup-${alias}-${Date.now()}`);
31567
+ const backupDir = path8.join(opts.clipsDir, `.backup-${alias}-${Date.now()}`);
31500
31568
  let backedUp = false;
31501
31569
  try {
31502
- if (fs7.existsSync(destDir)) {
31503
- fs7.renameSync(destDir, backupDir);
31570
+ if (fs8.existsSync(destDir)) {
31571
+ fs8.renameSync(destDir, backupDir);
31504
31572
  backedUp = true;
31505
31573
  }
31506
- fs7.renameSync(stageDir, destDir);
31574
+ fs8.renameSync(stageDir, destDir);
31507
31575
  if (backedUp) {
31508
- fs7.rmSync(backupDir, { recursive: true, force: true });
31576
+ fs8.rmSync(backupDir, { recursive: true, force: true });
31509
31577
  }
31510
31578
  } catch (swapErr) {
31511
- if (backedUp && !fs7.existsSync(destDir)) {
31579
+ if (backedUp && !fs8.existsSync(destDir)) {
31512
31580
  try {
31513
- fs7.renameSync(backupDir, destDir);
31581
+ fs8.renameSync(backupDir, destDir);
31514
31582
  } catch {
31515
31583
  }
31516
31584
  }
31517
31585
  throw swapErr;
31518
31586
  }
31519
31587
  } finally {
31520
- fs7.rmSync(tmpDir, { recursive: true, force: true });
31588
+ fs8.rmSync(tmpDir, { recursive: true, force: true });
31521
31589
  }
31522
31590
  return {
31523
31591
  alias,
@@ -31599,8 +31667,8 @@ var DaemonSupervisor = class {
31599
31667
  this.migrateFlatLayout();
31600
31668
  if (process.env.PRLL_CLIP_RUNTIME_ENABLED === "true") {
31601
31669
  this.clipManager = new ClipProcessManager({
31602
- clipsDir: path8.join(this.config.rootStateDir, "clips"),
31603
- dataDir: path8.join(this.config.rootStateDir, "clip-data")
31670
+ clipsDir: path9.join(this.config.rootStateDir, "clips"),
31671
+ dataDir: path9.join(this.config.rootStateDir, "clip-data")
31604
31672
  });
31605
31673
  try {
31606
31674
  await this.clipManager.loadInstalledClips();
@@ -31827,15 +31895,15 @@ var DaemonSupervisor = class {
31827
31895
  */
31828
31896
  migrateFlatLayout() {
31829
31897
  const root = this.config.rootStateDir;
31830
- const agentsDir = path8.join(root, "agents");
31831
- const flatWorkspace = path8.join(root, "workspace");
31832
- if (!fs8.existsSync(flatWorkspace) || fs8.existsSync(agentsDir))
31898
+ const agentsDir = path9.join(root, "agents");
31899
+ const flatWorkspace = path9.join(root, "workspace");
31900
+ if (!fs9.existsSync(flatWorkspace) || fs9.existsSync(agentsDir))
31833
31901
  return;
31834
31902
  let ownerAgentId;
31835
- const sessionsDir = path8.join(root, "sessions");
31836
- if (fs8.existsSync(sessionsDir)) {
31903
+ const sessionsDir = path9.join(root, "sessions");
31904
+ if (fs9.existsSync(sessionsDir)) {
31837
31905
  try {
31838
- for (const file of fs8.readdirSync(sessionsDir)) {
31906
+ for (const file of fs9.readdirSync(sessionsDir)) {
31839
31907
  if (!file.endsWith(".json"))
31840
31908
  continue;
31841
31909
  const decoded = Buffer.from(file.replace(".json", ""), "base64url").toString();
@@ -31849,13 +31917,13 @@ var DaemonSupervisor = class {
31849
31917
  }
31850
31918
  }
31851
31919
  const targetId = ownerAgentId ?? "_orphan";
31852
- const targetDir = path8.join(agentsDir, targetId);
31920
+ const targetDir = path9.join(agentsDir, targetId);
31853
31921
  try {
31854
- fs8.mkdirSync(targetDir, { recursive: true });
31922
+ fs9.mkdirSync(targetDir, { recursive: true });
31855
31923
  for (const sub of ["workspace", "sessions", "dispatch-context"]) {
31856
- const src = path8.join(root, sub);
31857
- if (fs8.existsSync(src)) {
31858
- fs8.renameSync(src, path8.join(targetDir, sub));
31924
+ const src = path9.join(root, sub);
31925
+ if (fs9.existsSync(src)) {
31926
+ fs9.renameSync(src, path9.join(targetDir, sub));
31859
31927
  }
31860
31928
  }
31861
31929
  this.log.info(`migrated legacy flat state \u2192 agents/${targetId}/`);
@@ -31950,7 +32018,7 @@ var DaemonSupervisor = class {
31950
32018
  });
31951
32019
  return true;
31952
32020
  }
31953
- const clipsDir = path8.join(this.config.rootStateDir, "clips");
32021
+ const clipsDir = path9.join(this.config.rootStateDir, "clips");
31954
32022
  let source = data.source_ref;
31955
32023
  if (data.version) {
31956
32024
  let sourceHasVersion = false;
@@ -32136,9 +32204,9 @@ var DaemonSupervisor = class {
32136
32204
  const isK8s = !!process.env.KUBERNETES_SERVICE_HOST;
32137
32205
  const claudeHome = isK8s ? agentClaudeHomeFor(this.config.rootClaudeHome, agentId) : this.config.rootClaudeHome;
32138
32206
  try {
32139
- fs8.mkdirSync(stateDir, { recursive: true });
32207
+ fs9.mkdirSync(stateDir, { recursive: true });
32140
32208
  if (isK8s) {
32141
- fs8.mkdirSync(claudeHome, { recursive: true });
32209
+ fs9.mkdirSync(claudeHome, { recursive: true });
32142
32210
  this.ensureSharedCredentialLink(claudeHome, agentId);
32143
32211
  }
32144
32212
  } catch (err) {
@@ -32276,31 +32344,31 @@ var DaemonSupervisor = class {
32276
32344
  });
32277
32345
  }
32278
32346
  ensureSharedCredentialLink(agentClaudeHome, agentId) {
32279
- const sharedCredentials = path8.resolve(sharedClaudeCredentialsFileFor(this.config.rootClaudeHome));
32347
+ const sharedCredentials = path9.resolve(sharedClaudeCredentialsFileFor(this.config.rootClaudeHome));
32280
32348
  const agentCredentials = agentClaudeCredentialsFileFor(agentClaudeHome);
32281
- const agentCredentialsDir = path8.dirname(agentCredentials);
32282
- fs8.mkdirSync(path8.dirname(sharedCredentials), { recursive: true });
32283
- fs8.mkdirSync(agentCredentialsDir, { recursive: true });
32349
+ const agentCredentialsDir = path9.dirname(agentCredentials);
32350
+ fs9.mkdirSync(path9.dirname(sharedCredentials), { recursive: true });
32351
+ fs9.mkdirSync(agentCredentialsDir, { recursive: true });
32284
32352
  try {
32285
- const existing = fs8.lstatSync(agentCredentials);
32353
+ const existing = fs9.lstatSync(agentCredentials);
32286
32354
  if (existing.isSymbolicLink()) {
32287
- const currentTarget = fs8.readlinkSync(agentCredentials);
32288
- if (path8.resolve(agentCredentialsDir, currentTarget) === sharedCredentials) {
32355
+ const currentTarget = fs9.readlinkSync(agentCredentials);
32356
+ if (path9.resolve(agentCredentialsDir, currentTarget) === sharedCredentials) {
32289
32357
  return;
32290
32358
  }
32291
- fs8.unlinkSync(agentCredentials);
32359
+ fs9.unlinkSync(agentCredentials);
32292
32360
  } else if (existing.isDirectory()) {
32293
32361
  this.log.warn(`agent ${agentId}: credential path is a directory, cannot link ${agentCredentials}`);
32294
32362
  return;
32295
32363
  } else {
32296
- fs8.unlinkSync(agentCredentials);
32364
+ fs9.unlinkSync(agentCredentials);
32297
32365
  }
32298
32366
  } catch (err) {
32299
32367
  if (err.code !== "ENOENT") {
32300
32368
  throw err;
32301
32369
  }
32302
32370
  }
32303
- fs8.symlinkSync(sharedCredentials, agentCredentials);
32371
+ fs9.symlinkSync(sharedCredentials, agentCredentials);
32304
32372
  }
32305
32373
  };
32306
32374
 
@@ -32309,8 +32377,8 @@ init_updater();
32309
32377
 
32310
32378
  // ts/daemon/dist/cli.js
32311
32379
  init_config();
32312
- import * as fs10 from "node:fs";
32313
- import * as path10 from "node:path";
32380
+ import * as fs11 from "node:fs";
32381
+ import * as path11 from "node:path";
32314
32382
  import * as os3 from "node:os";
32315
32383
  import * as readline from "node:readline";
32316
32384
  import { spawn as spawn4, execSync } from "node:child_process";
@@ -32318,15 +32386,15 @@ var CONFIG_DIR = daemonConfigDir();
32318
32386
  var CONFIG_PATH = daemonConfigPath();
32319
32387
  function readConfig() {
32320
32388
  try {
32321
- return JSON.parse(fs10.readFileSync(CONFIG_PATH, "utf-8"));
32389
+ return JSON.parse(fs11.readFileSync(CONFIG_PATH, "utf-8"));
32322
32390
  } catch {
32323
32391
  return null;
32324
32392
  }
32325
32393
  }
32326
32394
  function writeConfig(config) {
32327
- fs10.mkdirSync(CONFIG_DIR, { recursive: true, mode: 448 });
32328
- fs10.writeFileSync(CONFIG_PATH, JSON.stringify(config, null, 2), { mode: 384 });
32329
- fs10.chmodSync(CONFIG_PATH, 384);
32395
+ fs11.mkdirSync(CONFIG_DIR, { recursive: true, mode: 448 });
32396
+ fs11.writeFileSync(CONFIG_PATH, JSON.stringify(config, null, 2), { mode: 384 });
32397
+ fs11.chmodSync(CONFIG_PATH, 384);
32330
32398
  }
32331
32399
  function prompt(question) {
32332
32400
  const rl = readline.createInterface({ input: process.stdin, output: process.stdout });
@@ -32345,10 +32413,10 @@ function isLinux() {
32345
32413
  }
32346
32414
  var PLIST_LABEL = "com.parall.daemon";
32347
32415
  function plistPath() {
32348
- return path10.join(os3.homedir(), "Library", "LaunchAgents", `${PLIST_LABEL}.plist`);
32416
+ return path11.join(os3.homedir(), "Library", "LaunchAgents", `${PLIST_LABEL}.plist`);
32349
32417
  }
32350
32418
  function systemdUnitPath() {
32351
- return path10.join(os3.homedir(), ".config", "systemd", "user", "parall-daemon.service");
32419
+ return path11.join(os3.homedir(), ".config", "systemd", "user", "parall-daemon.service");
32352
32420
  }
32353
32421
  function getDaemonBin() {
32354
32422
  try {
@@ -32358,7 +32426,7 @@ function getDaemonBin() {
32358
32426
  }
32359
32427
  }
32360
32428
  function generatePlist(daemonBin) {
32361
- const logPath = path10.join(os3.homedir(), "Library", "Logs", "parall-daemon.log");
32429
+ const logPath = path11.join(os3.homedir(), "Library", "Logs", "parall-daemon.log");
32362
32430
  return `<?xml version="1.0" encoding="UTF-8"?>
32363
32431
  <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
32364
32432
  <plist version="1.0">
@@ -32407,16 +32475,16 @@ function installService() {
32407
32475
  }
32408
32476
  const bin = getDaemonBin();
32409
32477
  if (isMacOS()) {
32410
- const dir = path10.dirname(plistPath());
32411
- fs10.mkdirSync(dir, { recursive: true });
32412
- fs10.writeFileSync(plistPath(), generatePlist(bin));
32478
+ const dir = path11.dirname(plistPath());
32479
+ fs11.mkdirSync(dir, { recursive: true });
32480
+ fs11.writeFileSync(plistPath(), generatePlist(bin));
32413
32481
  execSync(`launchctl bootout gui/$(id -u) ${plistPath()} 2>/dev/null || true`);
32414
32482
  execSync(`launchctl bootstrap gui/$(id -u) ${plistPath()}`);
32415
32483
  console.log(`launchd agent installed: ${plistPath()}`);
32416
32484
  } else if (isLinux()) {
32417
- const dir = path10.dirname(systemdUnitPath());
32418
- fs10.mkdirSync(dir, { recursive: true });
32419
- fs10.writeFileSync(systemdUnitPath(), generateSystemdUnit(bin));
32485
+ const dir = path11.dirname(systemdUnitPath());
32486
+ fs11.mkdirSync(dir, { recursive: true });
32487
+ fs11.writeFileSync(systemdUnitPath(), generateSystemdUnit(bin));
32420
32488
  execSync("systemctl --user daemon-reload");
32421
32489
  execSync("systemctl --user enable --now parall-daemon");
32422
32490
  console.log(`systemd service installed: ${systemdUnitPath()}`);
@@ -32483,8 +32551,8 @@ function cmdLogs(lines) {
32483
32551
  child2.on("exit", (code) => process.exit(code ?? 0));
32484
32552
  return;
32485
32553
  }
32486
- const logPath = path10.join(os3.homedir(), "Library", "Logs", "parall-daemon.log");
32487
- if (!fs10.existsSync(logPath)) {
32554
+ const logPath = path11.join(os3.homedir(), "Library", "Logs", "parall-daemon.log");
32555
+ if (!fs11.existsSync(logPath)) {
32488
32556
  console.log("No log file found at", logPath);
32489
32557
  return;
32490
32558
  }
@@ -32494,14 +32562,14 @@ function cmdLogs(lines) {
32494
32562
  function cmdServiceUninstall() {
32495
32563
  if (isMacOS()) {
32496
32564
  execSync(`launchctl bootout gui/$(id -u) ${plistPath()} 2>/dev/null || true`);
32497
- if (fs10.existsSync(plistPath()))
32498
- fs10.unlinkSync(plistPath());
32565
+ if (fs11.existsSync(plistPath()))
32566
+ fs11.unlinkSync(plistPath());
32499
32567
  console.log("launchd agent uninstalled.");
32500
32568
  } else if (isLinux()) {
32501
32569
  execSync("systemctl --user stop parall-daemon 2>/dev/null || true");
32502
32570
  execSync("systemctl --user disable parall-daemon 2>/dev/null || true");
32503
- if (fs10.existsSync(systemdUnitPath()))
32504
- fs10.unlinkSync(systemdUnitPath());
32571
+ if (fs11.existsSync(systemdUnitPath()))
32572
+ fs11.unlinkSync(systemdUnitPath());
32505
32573
  execSync("systemctl --user daemon-reload");
32506
32574
  console.log("systemd service uninstalled.");
32507
32575
  } else {