@vm0/cli 9.132.10 → 9.134.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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@vm0/cli",
3
- "version": "9.132.10",
3
+ "version": "9.134.1",
4
4
  "description": "CLI application",
5
5
  "repository": {
6
6
  "type": "git",
package/zero.js CHANGED
@@ -30,6 +30,7 @@ import {
30
30
  deployZeroSchedule,
31
31
  disableZeroSchedule,
32
32
  downloadSlackFile,
33
+ downloadTelegramFile,
33
34
  downloadWebFile,
34
35
  enableZeroSchedule,
35
36
  extractSecretNamesFromApis,
@@ -112,7 +113,7 @@ import {
112
113
  upsertZeroOrgModelProvider,
113
114
  withErrorHandler,
114
115
  zeroAgentCustomSkillNameSchema
115
- } from "./chunk-PUKA5E32.js";
116
+ } from "./chunk-2MZO4LKL.js";
116
117
  import {
117
118
  __toESM,
118
119
  init_esm_shims
@@ -13922,7 +13923,7 @@ var FEATURE_SWITCHES = {
13922
13923
  },
13923
13924
  ["auditLink" /* AuditLink */]: {
13924
13925
  maintainer: "ethan@vm0.ai",
13925
- description: "Show audit log links in Slack messages",
13926
+ description: "Show audit log links in integration replies",
13926
13927
  enabled: false
13927
13928
  },
13928
13929
  ["audioInput" /* AudioInput */]: {
@@ -13950,6 +13951,12 @@ var FEATURE_SWITCHES = {
13950
13951
  description: "Replace the Invite people button in the agent chat page header with a New button that creates a new chat thread",
13951
13952
  enabled: false
13952
13953
  },
13954
+ ["chatArtifactsDrawer" /* ChatArtifactsDrawer */]: {
13955
+ maintainer: "ethan@vm0.ai",
13956
+ description: "Show an artifacts button in the chat header that opens a drawer listing uploaded files grouped by run",
13957
+ enabled: false,
13958
+ enabledOrgIdHashes: STAFF_ORG_ID_HASHES
13959
+ },
13953
13960
  ["chatThreadReadIndicator" /* ChatThreadReadIndicator */]: {
13954
13961
  maintainer: "ethan@vm0.ai",
13955
13962
  description: "Show the unread watermark dot and bold title for chat threads with unread messages in the sidebar",
@@ -13997,6 +14004,12 @@ var FEATURE_SWITCHES = {
13997
14004
  enabled: false,
13998
14005
  enabledOrgIdHashes: STAFF_ORG_ID_HASHES
13999
14006
  },
14007
+ ["telegramIntegration" /* TelegramIntegration */]: {
14008
+ maintainer: "ethan@vm0.ai",
14009
+ description: "Show the Telegram integration settings UI. The backend Telegram routes do not consult this frontend rollout flag.",
14010
+ enabled: false,
14011
+ enabledOrgIdHashes: STAFF_ORG_ID_HASHES
14012
+ },
14000
14013
  ["trinity" /* Trinity */]: {
14001
14014
  maintainer: "ethan@vm0.ai",
14002
14015
  description: "Embed the voice-chat mic toggle + voice-mode layout into the agent chat page. Gates the mic launcher, composer swap, and status/subtitle/task-card UI.",
@@ -16723,6 +16736,65 @@ Examples:
16723
16736
  Download a file: zero slack download-file <file-id> -o /tmp/out.png`
16724
16737
  );
16725
16738
 
16739
+ // src/commands/zero/telegram/index.ts
16740
+ init_esm_shims();
16741
+
16742
+ // src/commands/zero/telegram/download-file.ts
16743
+ init_esm_shims();
16744
+ import { join as join2 } from "path";
16745
+ import { tmpdir as tmpdir2 } from "os";
16746
+ function defaultOutPath2(fileId) {
16747
+ return join2(tmpdir2(), `telegram-${fileId}`);
16748
+ }
16749
+ var downloadFileCommand2 = new Command().name("download-file").description("Download a Telegram file by id using the bot token").argument("<file-id>", "Telegram file id from a [Telegram file] block").option(
16750
+ "-o, --out <path>",
16751
+ "Output path for the downloaded file (default: /tmp/telegram-<file-id>)"
16752
+ ).requiredOption(
16753
+ "--bot-id <bot-id>",
16754
+ "Telegram bot id from the [Telegram file] block"
16755
+ ).addHelpText(
16756
+ "after",
16757
+ `
16758
+ Examples:
16759
+ Download to default temp path: zero telegram download-file AgACAgUAAxkBAA --bot-id 123456789
16760
+ Download to explicit path: zero telegram download-file AgACAgUAAxkBAA --bot-id 123456789 -o /tmp/photo.jpg
16761
+
16762
+ Output:
16763
+ Prints a JSON object to stdout on success:
16764
+ {"path":"/tmp/telegram-AgACAgUAAxkBAA","mimetype":"image/jpeg","size":12345}
16765
+
16766
+ How to read the downloaded file:
16767
+ - Images (png/jpg/gif/webp/svg): open the file path with your image viewing tool
16768
+ - Videos (mp4/mov/webm): extract frames first with
16769
+ ffmpeg -i <path> -vf "fps=1" -q:v 2 /tmp/<file-id>_frame_%03d.jpg
16770
+ then view the extracted frames
16771
+ - PDF/text/csv/json/markdown: read the file directly
16772
+
16773
+ Notes:
16774
+ - Uses the Telegram bot token on the server side
16775
+ - Streams the file bytes directly to disk`
16776
+ ).action(
16777
+ withErrorHandler(
16778
+ async (fileId, options) => {
16779
+ const outPath = options.out ?? defaultOutPath2(fileId);
16780
+ const result = await downloadTelegramFile(
16781
+ fileId,
16782
+ options.botId,
16783
+ outPath
16784
+ );
16785
+ console.log(JSON.stringify(result));
16786
+ }
16787
+ )
16788
+ );
16789
+
16790
+ // src/commands/zero/telegram/index.ts
16791
+ var zeroTelegramCommand = new Command().name("telegram").description("Download files from Telegram as the bot").addCommand(downloadFileCommand2).addHelpText(
16792
+ "after",
16793
+ `
16794
+ Examples:
16795
+ Download a file: zero telegram download-file <file-id> --bot-id <bot-id> -o /tmp/out.jpg`
16796
+ );
16797
+
16726
16798
  // src/commands/zero/variable/index.ts
16727
16799
  init_esm_shims();
16728
16800
 
@@ -16971,7 +17043,7 @@ init_esm_shims();
16971
17043
  // src/lib/skill-directory.ts
16972
17044
  init_esm_shims();
16973
17045
  import { readFileSync as readFileSync7, readdirSync } from "fs";
16974
- import { join as join2 } from "path";
17046
+ import { join as join3 } from "path";
16975
17047
  var IGNORED_NAMES = /* @__PURE__ */ new Set(["node_modules", ".git", ".DS_Store"]);
16976
17048
  function readSkillDirectory(dirPath) {
16977
17049
  const files = [];
@@ -16981,11 +17053,11 @@ function readSkillDirectory(dirPath) {
16981
17053
  if (entry.name.startsWith(".") || IGNORED_NAMES.has(entry.name)) continue;
16982
17054
  const relPath = prefix ? `${prefix}/${entry.name}` : entry.name;
16983
17055
  if (entry.isDirectory()) {
16984
- walk(join2(dir, entry.name), relPath);
17056
+ walk(join3(dir, entry.name), relPath);
16985
17057
  } else {
16986
17058
  files.push({
16987
17059
  path: relPath,
16988
- content: readFileSync7(join2(dir, entry.name), "utf-8")
17060
+ content: readFileSync7(join3(dir, entry.name), "utf-8")
16989
17061
  });
16990
17062
  }
16991
17063
  }
@@ -17747,12 +17819,12 @@ init_esm_shims();
17747
17819
  import { execFile } from "child_process";
17748
17820
  import { readFile, unlink } from "fs/promises";
17749
17821
  import { randomUUID } from "crypto";
17750
- import { join as join3 } from "path";
17751
- import { tmpdir as tmpdir2 } from "os";
17822
+ import { join as join4 } from "path";
17823
+ import { tmpdir as tmpdir3 } from "os";
17752
17824
  import { promisify } from "util";
17753
17825
  var execFileAsync = promisify(execFile);
17754
17826
  async function captureScreenshot() {
17755
- const tmpPath = join3(tmpdir2(), `vm0-screenshot-${randomUUID()}.jpg`);
17827
+ const tmpPath = join4(tmpdir3(), `vm0-screenshot-${randomUUID()}.jpg`);
17756
17828
  try {
17757
17829
  await execFileAsync("screencapture", ["-x", "-t", "jpg", tmpPath]);
17758
17830
  const info = await getScreenInfo();
@@ -17781,7 +17853,7 @@ async function captureScreenshot() {
17781
17853
  }
17782
17854
  }
17783
17855
  async function captureRegionScreenshot(region) {
17784
- const tmpPath = join3(tmpdir2(), `vm0-zoom-${randomUUID()}.jpg`);
17856
+ const tmpPath = join4(tmpdir3(), `vm0-zoom-${randomUUID()}.jpg`);
17785
17857
  try {
17786
17858
  const regionArg = `${region.x},${region.y},${region.width},${region.height}`;
17787
17859
  await execFileAsync("screencapture", [
@@ -18473,7 +18545,7 @@ var hostStopCommand = new Command().name("stop").description("Stop and unregiste
18473
18545
  // src/commands/zero/computer-use/client.ts
18474
18546
  init_esm_shims();
18475
18547
  import { writeFile, mkdir } from "fs/promises";
18476
- import { join as join4 } from "path";
18548
+ import { join as join5 } from "path";
18477
18549
 
18478
18550
  // src/lib/computer-use/client.ts
18479
18551
  init_esm_shims();
@@ -18541,7 +18613,7 @@ var clientScreenshotCommand = new Command().name("screenshot").description("Capt
18541
18613
  const dir = "/tmp/computer-use";
18542
18614
  await mkdir(dir, { recursive: true });
18543
18615
  const timestamp = Date.now();
18544
- const filePath = join4(dir, `screenshot-${timestamp}.${data.format}`);
18616
+ const filePath = join5(dir, `screenshot-${timestamp}.${data.format}`);
18545
18617
  const buffer = Buffer.from(data.image, "base64");
18546
18618
  await writeFile(filePath, buffer);
18547
18619
  process.stdout.write(`${filePath}
@@ -18569,7 +18641,7 @@ var clientZoomCommand = new Command().name("zoom").description("Capture a region
18569
18641
  const dir = "/tmp/computer-use";
18570
18642
  await mkdir(dir, { recursive: true });
18571
18643
  const timestamp = Date.now();
18572
- const filePath = join4(dir, `zoom-${timestamp}.${data.format}`);
18644
+ const filePath = join5(dir, `zoom-${timestamp}.${data.format}`);
18573
18645
  const buffer = Buffer.from(data.image, "base64");
18574
18646
  await writeFile(filePath, buffer);
18575
18647
  process.stdout.write(`${filePath}
@@ -18766,12 +18838,12 @@ init_esm_shims();
18766
18838
 
18767
18839
  // src/commands/zero/web/download-file.ts
18768
18840
  init_esm_shims();
18769
- import { join as join5 } from "path";
18770
- import { tmpdir as tmpdir3 } from "os";
18771
- function defaultOutPath2(fileId) {
18772
- return join5(tmpdir3(), `web-${fileId}`);
18841
+ import { join as join6 } from "path";
18842
+ import { tmpdir as tmpdir4 } from "os";
18843
+ function defaultOutPath3(fileId) {
18844
+ return join6(tmpdir4(), `web-${fileId}`);
18773
18845
  }
18774
- var downloadFileCommand2 = new Command().name("download-file").description("Download a web-uploaded file by id").argument("<file-id>", "File id (UUID returned by the upload API)").option(
18846
+ var downloadFileCommand3 = new Command().name("download-file").description("Download a web-uploaded file by id").argument("<file-id>", "File id (UUID returned by the upload API)").option(
18775
18847
  "-o, --out <path>",
18776
18848
  "Output path for the downloaded file (default: /tmp/web-<file-id>)"
18777
18849
  ).addHelpText(
@@ -18797,7 +18869,7 @@ Notes:
18797
18869
  - Streams the file bytes directly to disk`
18798
18870
  ).action(
18799
18871
  withErrorHandler(async (fileId, options) => {
18800
- const outPath = options.out ?? defaultOutPath2(fileId);
18872
+ const outPath = options.out ?? defaultOutPath3(fileId);
18801
18873
  const result = await downloadWebFile(fileId, outPath);
18802
18874
  console.log(JSON.stringify(result));
18803
18875
  })
@@ -18821,7 +18893,7 @@ Notes:
18821
18893
  - Returned URL is permanent (serves a short-lived signed redirect on access)
18822
18894
  - Safe to persist in chat messages or share over external channels
18823
18895
  - Max file size: 1 GB
18824
- - Allowed types: png / jpeg / gif / webp / svg / mp4 / webm / mov / pdf / txt / csv / md / json`
18896
+ - Allowed types: png / jpeg / gif / webp / svg / mp4 / webm / mov / pdf / txt / csv / md / html / json`
18825
18897
  ).action(
18826
18898
  withErrorHandler(
18827
18899
  async (options) => {
@@ -18834,7 +18906,7 @@ Notes:
18834
18906
  );
18835
18907
 
18836
18908
  // src/commands/zero/web/index.ts
18837
- var zeroWebCommand = new Command().name("web").description("Upload and download files via the web chat endpoint").addCommand(downloadFileCommand2).addCommand(uploadFileCommand2).addHelpText(
18909
+ var zeroWebCommand = new Command().name("web").description("Upload and download files via the web chat endpoint").addCommand(downloadFileCommand3).addCommand(uploadFileCommand2).addHelpText(
18838
18910
  "after",
18839
18911
  `
18840
18912
  Examples:
@@ -18854,6 +18926,7 @@ var COMMAND_CAPABILITY_MAP = {
18854
18926
  search: "chat-message:read",
18855
18927
  chat: "chat-message:write",
18856
18928
  slack: "slack:write",
18929
+ telegram: "file:read",
18857
18930
  whoami: null,
18858
18931
  "developer-support": null,
18859
18932
  "computer-use": "computer-use:write",
@@ -18870,6 +18943,7 @@ var DEFAULT_COMMANDS = [
18870
18943
  zeroSecretCommand,
18871
18944
  zeroChatCommand,
18872
18945
  zeroSlackCommand,
18946
+ zeroTelegramCommand,
18873
18947
  zeroVariableCommand,
18874
18948
  zeroLogsCommand,
18875
18949
  zeroSearchCommand,
@@ -18896,12 +18970,13 @@ function registerZeroCommands(prog, commands) {
18896
18970
  var program = new Command();
18897
18971
  program.name("zero").description(
18898
18972
  "Zero CLI \u2014 interact with the zero platform from inside the sandbox"
18899
- ).version("9.132.10").addHelpText(
18973
+ ).version("9.134.1").addHelpText(
18900
18974
  "after",
18901
18975
  `
18902
18976
  Examples:
18903
18977
  Check a connector? zero doctor check-connector --env-name <ENV_NAME>
18904
18978
  Send a Slack message? zero slack message send --help
18979
+ Download Telegram? zero telegram download-file --help
18905
18980
  Set up a schedule? zero schedule setup --help
18906
18981
  Update yourself? zero agent --help
18907
18982
  Manage custom skills? zero skill --help