@withone/cli 2.9.0 → 2.9.2

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.md CHANGED
@@ -24,7 +24,7 @@
24
24
  <a href="https://withone.ai/knowledge"><img src="https://img.shields.io/endpoint?url=https%3A%2F%2Fapi.withone.ai%2Fopen%2Fcount%2Ftools" alt="tools"></a>
25
25
  </p>
26
26
 
27
- One gives your AI agent authenticated access to 750+ platforms - Gmail, Slack, Shopify, HubSpot, Stripe, Notion, and everything else - through a single interface. No API keys to juggle, no OAuth flows to build, no request formats to memorize. Connect a platform once, and your agent can search for actions, read the docs, and execute API calls in seconds.
27
+ One gives your AI agent authenticated access to 1000+ platforms - Gmail, Slack, Shopify, HubSpot, Stripe, Notion, and everything else - through a single interface. No API keys to juggle, no OAuth flows to build, no request formats to memorize. Connect a platform once, and your agent can search for actions, read the docs, and execute API calls in seconds.
28
28
 
29
29
  ## Install
30
30
 
@@ -50,10 +50,14 @@ one logout # Clear credentials (with scope picker and confirmation)
50
50
 
51
51
  The browser consent page names the key and tags it with where this CLI is installed (scope, project path, machine, OS user, CLI version, chosen harnesses, and the per-install device id unless telemetry is off) so you can find and revoke it from Settings → API keys. The terminal prints exactly what will be sent before the browser opens.
52
52
 
53
- Requires Node.js 18+. `one sync` additionally needs Node 20+, because its
54
- local SQLite engine (`better-sqlite3`, an optional dependency) ships prebuilt
55
- binaries only for Node 20 and above. On Node 18 every other command works
56
- normally; `one sync` reports that the engine isn't installed.
53
+ Requires Node.js 22.23.4+, 24.22.1+ or 26.12.1+. Older Node versions trust the
54
+ compromised eMudhra intermediate CA certificates (October 2026), so a network
55
+ attacker could intercept the CLI's traffic and your API key. On them the CLI
56
+ refuses to run and prints the command that updates Node for how you installed
57
+ it. Node 18, 20, 23 and 25 are end-of-life and never got the fix.
58
+
59
+ If you can't update Node yet, `ONE_ALLOW_UNPATCHED_NODE=1` runs the CLI anyway,
60
+ with a security warning on every run. You remain exposed while it is set.
57
61
 
58
62
  ## Quick start
59
63
 
@@ -247,7 +251,7 @@ Shows the connection details and asks for confirmation before deleting. Use `--f
247
251
 
248
252
  ### `one platforms`
249
253
 
250
- Browse all 750+ available platforms.
254
+ Browse all 1000+ available platforms.
251
255
 
252
256
  ```bash
253
257
  one platforms # all platforms
package/bin/cli.js CHANGED
@@ -1,5 +1,11 @@
1
1
  #!/usr/bin/env node
2
2
 
3
- import { program } from '../dist/index.js';
3
+ import { requirePatchedNode } from '../dist/node-check.js';
4
+
5
+ // eMudhra CA compromise: refuse to run before any connection opens on a Node
6
+ // that still trusts the leaked intermediates (see src/node-check.ts).
7
+ requirePatchedNode();
8
+
9
+ const { program } = await import('../dist/index.js');
4
10
 
5
11
  program.parse();
@@ -0,0 +1,79 @@
1
+ // src/node-check.ts
2
+ var FIXED_IN = {
3
+ 22: [23, 4],
4
+ 24: [22, 1],
5
+ 26: [12, 1]
6
+ };
7
+ var FIRST_LINE_WITH_FIX = 27;
8
+ var RECOMMENDED_LINE = 24;
9
+ var REQUIRED_NODE = "22.23.4+, 24.22.1+ or 26.12.1+";
10
+ var REQUIRED_NODE_RANGE = "^22.23.4 || ^24.22.1 || >=26.12.1";
11
+ var ALLOW_UNPATCHED_ENV = "ONE_ALLOW_UNPATCHED_NODE";
12
+ function parseVersion(version) {
13
+ const [major, minor, patch] = version.split(".").map((part) => Number.parseInt(part, 10));
14
+ return [major, minor, patch ?? 0];
15
+ }
16
+ function nodeHasTlsFix(version = process.versions.node) {
17
+ const [major, minor, patch] = parseVersion(version);
18
+ if (!Number.isFinite(major)) return false;
19
+ if (major >= FIRST_LINE_WITH_FIX) return true;
20
+ const fixed = FIXED_IN[major];
21
+ if (!fixed) return false;
22
+ const [fixedMinor, fixedPatch] = fixed;
23
+ return minor > fixedMinor || minor === fixedMinor && patch >= fixedPatch;
24
+ }
25
+ function upgradeCommand(version = process.versions.node, execPath = process.execPath) {
26
+ const [major] = parseVersion(version);
27
+ const line = FIXED_IN[major] ? major : RECOMMENDED_LINE;
28
+ const path = execPath.replace(/\\/g, "/");
29
+ if (/\/\.nvm\/versions\/node\//.test(path)) return `nvm install ${line} && nvm alias default ${line}`;
30
+ if (/\/AppData\/(Roaming|Local)\/nvm\//i.test(path)) return `nvm install ${line} && nvm use ${line}`;
31
+ if (/\/\.?volta\//i.test(path)) return `volta install node@${line}`;
32
+ if (/fnm/i.test(path)) return `fnm install ${line} && fnm default ${line}`;
33
+ const brew = path.match(/\/Cellar\/(node(?:@\d+)?)\//);
34
+ if (brew) {
35
+ const formula = brew[1] === "node" || FIXED_IN[major] ? brew[1] : `node@${line}`;
36
+ return formula === brew[1] ? `brew upgrade ${formula}` : `brew install ${formula}`;
37
+ }
38
+ return `download Node.js ${line} from https://nodejs.org`;
39
+ }
40
+ function unpatchedNodeMessage(version = process.versions.node) {
41
+ return `Node.js v${version} trusts the compromised eMudhra certificates, so a network attacker could intercept One's traffic and your API key. The One CLI requires Node.js ${REQUIRED_NODE} (Node 18, 20, 23 and 25 never got the fix).`;
42
+ }
43
+ function requirePatchedNode() {
44
+ if (nodeHasTlsFix()) return;
45
+ const message = unpatchedNodeMessage();
46
+ const upgrade = upgradeCommand();
47
+ const agent = process.argv.includes("--agent") || process.env.ONE_AGENT === "1";
48
+ if (process.env[ALLOW_UNPATCHED_ENV] === "1") {
49
+ if (!agent) process.stderr.write(`Warning: ${message} Running anyway because ${ALLOW_UNPATCHED_ENV}=1.
50
+ `);
51
+ return;
52
+ }
53
+ if (agent) {
54
+ const error = {
55
+ error: `${message} Ask the user to update Node.js: ${upgrade}`,
56
+ code: "NODE_UPGRADE_REQUIRED",
57
+ currentNode: process.versions.node,
58
+ requiredNode: REQUIRED_NODE_RANGE,
59
+ upgrade
60
+ };
61
+ process.stdout.write(`${JSON.stringify(error)}
62
+ `);
63
+ } else {
64
+ process.stderr.write(`Error: ${message}
65
+ To update: ${upgrade}
66
+ `);
67
+ }
68
+ process.exit(1);
69
+ }
70
+
71
+ export {
72
+ REQUIRED_NODE,
73
+ REQUIRED_NODE_RANGE,
74
+ ALLOW_UNPATCHED_ENV,
75
+ nodeHasTlsFix,
76
+ upgradeCommand,
77
+ unpatchedNodeMessage,
78
+ requirePatchedNode
79
+ };
package/dist/index.d.ts CHANGED
@@ -1,4 +1,5 @@
1
1
  import { Command } from 'commander';
2
+ export { nodeHasTlsFix } from './node-check.js';
2
3
 
3
4
  declare const program: Command;
4
5
 
package/dist/index.js CHANGED
@@ -1,3 +1,6 @@
1
+ import {
2
+ nodeHasTlsFix
3
+ } from "./chunk-FYTWXGPJ.js";
1
4
  import {
2
5
  ApiError,
3
6
  FLOW_SCHEMA,
@@ -1127,7 +1130,7 @@ async function loginCommand() {
1127
1130
  console.log(pc16.cyan(" \u250C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500"));
1128
1131
  console.log(pc16.cyan(" \u2502"));
1129
1132
  console.log(pc16.cyan(" \u2502 The One CLI (`one`) is now installed on this machine. It"));
1130
- console.log(pc16.cyan(" \u2502 lets you interact with 750+ third-party platforms (Gmail,"));
1133
+ console.log(pc16.cyan(" \u2502 lets you interact with 1000+ third-party platforms (Gmail,"));
1131
1134
  console.log(pc16.cyan(" \u2502 Slack, Shopify, HubSpot, Stripe, GitHub, etc.) through"));
1132
1135
  console.log(pc16.cyan(" \u2502 their APIs. Whenever you need to interact with any"));
1133
1136
  console.log(pc16.cyan(" \u2502 third-party platform or external service, use the `one`"));
@@ -1730,7 +1733,7 @@ function printOnboardingPrompt() {
1730
1733
  console.log(pc3.cyan(" \u250C\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500"));
1731
1734
  console.log(pc3.cyan(" \u2502"));
1732
1735
  console.log(pc3.cyan(" \u2502 The One CLI (`one`) is now installed on this machine. It"));
1733
- console.log(pc3.cyan(" \u2502 lets you interact with 750+ third-party platforms (Gmail,"));
1736
+ console.log(pc3.cyan(" \u2502 lets you interact with 1000+ third-party platforms (Gmail,"));
1734
1737
  console.log(pc3.cyan(" \u2502 Slack, Shopify, HubSpot, Stripe, GitHub, etc.) through"));
1735
1738
  console.log(pc3.cyan(" \u2502 their APIs. Whenever you need to interact with any"));
1736
1739
  console.log(pc3.cyan(" \u2502 third-party platform or external service, use the `one`"));
@@ -1904,7 +1907,7 @@ async function promptConnectIntegrations(apiKey, connParams) {
1904
1907
  label: i.label,
1905
1908
  hint: i.hint
1906
1909
  })),
1907
- { value: "more", label: "Browse all 750+ platforms" },
1910
+ { value: "more", label: "Browse all 1000+ platforms" },
1908
1911
  { value: "skip", label: "Skip for now", hint: "you can always run one add later" }
1909
1912
  ];
1910
1913
  const message = first ? "Connect your first integration?" : "Connect another?";
@@ -10825,7 +10828,7 @@ Before using any feature, read its guide section first: \`one guide actions\`, \
10825
10828
 
10826
10829
  ## Features
10827
10830
 
10828
- ### 1. Actions \u2014 Execute API calls on 750+ platforms
10831
+ ### 1. Actions \u2014 Execute API calls on 1000+ platforms
10829
10832
  Find the actions a task needs with their docs, in one call, then execute them. This is the core workflow.
10830
10833
 
10831
10834
  **Quick start:**
@@ -10917,6 +10920,7 @@ Request specific sections:
10917
10920
  - **Always use \`--agent\` flag** for structured JSON output
10918
10921
  - Platform names are **lowercase**; multi-word names use dashes (e.g., \`hubspot\`, \`google-calendar\`)
10919
10922
  - Always use the **exact action ID** from a find answer \u2014 don't guess
10923
+ - Requires Node.js 22.23.4+, 24.22.1+ or 26.12.1+. Older Node trusts the compromised eMudhra CA certificates, so every command exits 1 there with \`"code": "NODE_UPGRADE_REQUIRED"\` and an \`upgrade\` field holding the command for the user's setup. Don't retry: show the user that command and ask them to update Node.js
10920
10924
  - Always read **knowledge** before executing any action
10921
10925
  - Connection keys come from \`one connection list\` \u2014 don't hardcode them
10922
10926
  - \`connection list\` also reports an \`access\` field per connection (\`full\` / \`methods\` / \`actions\`, plus a \`level\`: full, read-write, read-only, custom, none) \u2014 what One enforces for this key, narrowed by \`one config\`. Read it before planning so you don't propose an action that will be refused. \`accessSource: "local"\` means One did not report it, so it is unverified
@@ -12092,7 +12096,7 @@ function buildStep1() {
12092
12096
  nextCommand: "one onboard --step 2",
12093
12097
  message: `# One CLI \u2014 Agent Onboarding
12094
12098
 
12095
- You now have access to the One CLI. It connects you to 750+ platforms
12099
+ You now have access to the One CLI. It connects you to 1000+ platforms
12096
12100
  (Gmail, Slack, Stripe, Notion, etc.) \u2014 you'll learn the details shortly.
12097
12101
 
12098
12102
  IMPORTANT: Your only task right now is to send the message below to the
@@ -12102,7 +12106,7 @@ Do not offer demos yet. Just send this message and wait for their reply:
12102
12106
  ---
12103
12107
 
12104
12108
  I just got access to the One CLI \u2014 it connects me to your platforms like
12105
- Gmail, Slack, Stripe, and 750+ others so I can work with them directly.
12109
+ Gmail, Slack, Stripe, and 1000+ others so I can work with them directly.
12106
12110
  I'll show you what I can do in a moment.
12107
12111
 
12108
12112
  First, one quick setup step: right now only this conversation knows about
@@ -12131,7 +12135,7 @@ If they declined, skip this section.
12131
12135
  ## One CLI \u2014 Platform Integrations
12132
12136
 
12133
12137
  The One CLI (\`one\`) is installed and configured on this machine. It is a
12134
- command-line tool that gives AI agents the ability to interact with 750+
12138
+ command-line tool that gives AI agents the ability to interact with 1000+
12135
12139
  third-party platforms (Gmail, Slack, Shopify, HubSpot, Stripe, GitHub,
12136
12140
  Notion, Salesforce, etc.) through a single, unified interface.
12137
12141
 
@@ -12225,7 +12229,7 @@ function buildStep3(connections) {
12225
12229
  The user can connect any of these popular platforms:
12226
12230
  Gmail, Google Calendar, Slack, Notion, Shopify, Stripe, HubSpot, GitHub,
12227
12231
  Salesforce, QuickBooks, Asana, Jira, Linear, Intercom, Zendesk, Twilio,
12228
- and 750+ more. Run \`one platforms\` for the full list.`);
12232
+ and 1000+ more. Run \`one platforms\` for the full list.`);
12229
12233
  sections.push("## Onboarding complete!\n\nYou're all set. Use `one --agent guide` any time you need the full reference.");
12230
12234
  return {
12231
12235
  step: 3,
@@ -12256,7 +12260,7 @@ platform before you can start using actions. Suggest they run:
12256
12260
  one add slack
12257
12261
  one add <any-platform>
12258
12262
 
12259
- Run \`one platforms\` to see all 750+ available platforms.`;
12263
+ Run \`one platforms\` to see all 1000+ available platforms.`;
12260
12264
  }
12261
12265
  const header = `## Current State
12262
12266
 
@@ -12972,7 +12976,7 @@ silenceWarningsInAgentMode();
12972
12976
  var require2 = createRequire(import.meta.url);
12973
12977
  var { version } = require2("../package.json");
12974
12978
  var program = new Command();
12975
- program.name("one").option("--agent", "Machine-readable JSON output (no colors, spinners, or prompts)").description(`One CLI \u2014 Connect AI agents to 750+ platforms through one interface.
12979
+ program.name("one").option("--agent", "Machine-readable JSON output (no colors, spinners, or prompts)").description(`One CLI \u2014 Connect AI agents to 1000+ platforms through one interface.
12976
12980
 
12977
12981
  Setup:
12978
12982
  one login Authenticate via browser; the consent page records where this CLI is installed
@@ -13048,7 +13052,7 @@ program.name("one").option("--agent", "Machine-readable JSON output (no colors,
13048
13052
  -d '{"to":"j@example.com","subject":"Hello","body":"Hi!","connectionKey":"live::gmail::default::abc123"}'
13049
13053
 
13050
13054
  Platform names are lowercase; multi-word names use dashes (e.g. hubspot, ship-station, google-calendar).
13051
- Run 'one platforms' to browse all 750+ available platforms.`).version(version);
13055
+ Run 'one platforms' to browse all 1000+ available platforms.`).version(version);
13052
13056
  var updateCheckPromise;
13053
13057
  program.hook("preAction", (thisCommand, actionCommand) => {
13054
13058
  const opts = program.opts();
@@ -13441,5 +13445,6 @@ program.command("list").alias("ls").description("Shortcut for: connection list")
13441
13445
  await connectionListCommand(options);
13442
13446
  });
13443
13447
  export {
13448
+ nodeHasTlsFix,
13444
13449
  program
13445
13450
  };
@@ -0,0 +1,36 @@
1
+ /**
2
+ * Refuses to run on a Node.js that still trusts the compromised eMudhra
3
+ * intermediate CAs (October 2026, RUSTSEC-2026-0381).
4
+ *
5
+ * Eight eMudhra/emSign intermediates were created with 8-bit private keys, so
6
+ * anyone can compute them and sign a certificate for any domain, including
7
+ * api.withone.ai. Node.js blocks them inside the TLS handshake from 22.23.4,
8
+ * 24.22.1 and 26.12.1 (nodejs/node#66871). On any older Node, a network
9
+ * attacker can intercept the CLI's traffic and the user's API key, and nothing
10
+ * in userland can block the intermediates the way Node's fix does.
11
+ *
12
+ * Built as its own entry so bin/cli.js can run it before loading the rest of
13
+ * the CLI, and before any connection opens.
14
+ */
15
+ declare const REQUIRED_NODE = "22.23.4+, 24.22.1+ or 26.12.1+";
16
+ declare const REQUIRED_NODE_RANGE = "^22.23.4 || ^24.22.1 || >=26.12.1";
17
+ /** Set to 1 to run on an unpatched Node anyway, with a warning on every run. */
18
+ declare const ALLOW_UNPATCHED_ENV = "ONE_ALLOW_UNPATCHED_NODE";
19
+ /** True when this Node version rejects chains through the compromised eMudhra intermediates. */
20
+ declare function nodeHasTlsFix(version?: string): boolean;
21
+ /**
22
+ * The command that updates Node for however it was installed, judged from the
23
+ * path of the running binary. A line that got the fix stays on its line; any
24
+ * other moves to the recommended one.
25
+ */
26
+ declare function upgradeCommand(version?: string, execPath?: string): string;
27
+ declare function unpatchedNodeMessage(version?: string): string;
28
+ /**
29
+ * Exits with an error on an unpatched Node; returns on a patched one. In agent
30
+ * mode the error is JSON on stdout with a code agents can act on. With
31
+ * ONE_ALLOW_UNPATCHED_NODE=1 it warns and returns instead (silently in agent
32
+ * mode, where stderr would corrupt the JSON for harnesses that merge streams).
33
+ */
34
+ declare function requirePatchedNode(): void;
35
+
36
+ export { ALLOW_UNPATCHED_ENV, REQUIRED_NODE, REQUIRED_NODE_RANGE, nodeHasTlsFix, requirePatchedNode, unpatchedNodeMessage, upgradeCommand };
@@ -0,0 +1,18 @@
1
+ import {
2
+ ALLOW_UNPATCHED_ENV,
3
+ REQUIRED_NODE,
4
+ REQUIRED_NODE_RANGE,
5
+ nodeHasTlsFix,
6
+ requirePatchedNode,
7
+ unpatchedNodeMessage,
8
+ upgradeCommand
9
+ } from "./chunk-FYTWXGPJ.js";
10
+ export {
11
+ ALLOW_UNPATCHED_ENV,
12
+ REQUIRED_NODE,
13
+ REQUIRED_NODE_RANGE,
14
+ nodeHasTlsFix,
15
+ requirePatchedNode,
16
+ unpatchedNodeMessage,
17
+ upgradeCommand
18
+ };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@withone/cli",
3
- "version": "2.9.0",
3
+ "version": "2.9.2",
4
4
  "description": "CLI for managing One",
5
5
  "type": "module",
6
6
  "files": [
@@ -52,6 +52,6 @@
52
52
  "url": "https://github.com/withoneai/cli"
53
53
  },
54
54
  "engines": {
55
- "node": ">=18"
55
+ "node": "^22.23.4 || ^24.22.1 || >=26.12.1"
56
56
  }
57
57
  }
@@ -20,7 +20,7 @@ description: |
20
20
 
21
21
  # One CLI
22
22
 
23
- You have access to the One CLI which lets you interact with 750+ third-party platforms through their APIs. Always include the `--agent` flag right after `one` for structured JSON output.
23
+ You have access to the One CLI which lets you interact with 1000+ third-party platforms through their APIs. Always include the `--agent` flag right after `one` for structured JSON output.
24
24
 
25
25
  If the user wants a separate API key / connections for a specific project (vs. their default), walk them through running `one init` from that project folder and picking the "project" scope — see `references/scoping.md`. For monorepo subprojects (where a parent already has `.git`/`package.json`), have them `mkdir .one` in the subproject first so the config is keyed to that dir, not the monorepo root.
26
26
 
@@ -171,6 +171,8 @@ All segments are validated before any execution. Failed actions don't block othe
171
171
 
172
172
  All errors return JSON: `{"error": "message"}`. Parse output as JSON and check for the `error` key.
173
173
 
174
+ The CLI requires Node.js 22.23.4+, 24.22.1+ or 26.12.1+ (older Node trusts the compromised eMudhra CA certificates). On an older Node every command exits 1 with `"code": "NODE_UPGRADE_REQUIRED"` and an `upgrade` field holding the command for the user's setup. Don't retry: show the user that command and ask them to update Node.js.
175
+
174
176
  ## Important Rules
175
177
 
176
178
  - Always use `--agent` flag for structured JSON output