@xanots/sdk 0.0.4 → 0.0.5

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 (49) hide show
  1. package/CHANGELOG.md +9 -10
  2. package/README.md +4 -0
  3. package/dist/.build-fingerprint +1 -0
  4. package/dist/bin.js +4 -4
  5. package/dist/{chunk-AJ7JQ4OU.js → chunk-AAFBSOSD.js} +3 -3
  6. package/dist/{chunk-VWGJQTNA.js → chunk-APOR6TCV.js} +4 -4
  7. package/dist/{chunk-YYSJAAJM.js → chunk-F5T45NAM.js} +7 -2
  8. package/dist/{chunk-KGNJM4LN.js → chunk-IVP6TS26.js} +2 -2
  9. package/dist/{chunk-EAIR6VUL.js → chunk-KXCPZUUM.js} +3 -3
  10. package/dist/{chunk-7REDODS2.js → chunk-LLWK6H77.js} +20 -2
  11. package/dist/{chunk-DUC3PXDG.js → chunk-MS3BRZAZ.js} +26 -22
  12. package/dist/{chunk-VKD3EBKG.js → chunk-OARSPAIE.js} +7 -7
  13. package/dist/{chunk-ACQCK4DT.js → chunk-OR43PDCW.js} +2 -2
  14. package/dist/chunk-PGBK64U5.js +59 -0
  15. package/dist/{chunk-SWIXWJIY.js → chunk-QA5ICJ4M.js} +3 -3
  16. package/dist/{chunk-C56BC2FY.js → chunk-SG4UBJ47.js} +2 -2
  17. package/dist/{chunk-VTIL47DT.js → chunk-W5NOKYEG.js} +6 -2
  18. package/dist/{chunk-DGSF2Q5H.js → chunk-WJYB7DSI.js} +2 -2
  19. package/dist/{chunk-T6N3VMMO.js → chunk-ZGA5MUNC.js} +2 -2
  20. package/dist/cli.d.ts +8 -1
  21. package/dist/cli.js +3 -3
  22. package/dist/{codegen-command-Z7WQMOJ7.js → codegen-command-BLOS3GR3.js} +8 -8
  23. package/dist/{completion-4GYN752B.js → completion-GHP5RRLQ.js} +2 -2
  24. package/dist/{deploy-command-M2S4HHLC.js → deploy-command-XOH76USO.js} +11 -11
  25. package/dist/{env-target-GSFCYHKZ.js → env-target-POGJMD6Q.js} +6 -6
  26. package/dist/{ephemeral-command-6WJW7LP6.js → ephemeral-command-46SL27GJ.js} +13 -13
  27. package/dist/{init-command-GJUPWTKA.js → init-command-NCRPVFGE.js} +5 -5
  28. package/dist/internal.js +1 -1
  29. package/dist/{lock-commands-7IH7RSSP.js → lock-commands-6UONZW26.js} +4 -4
  30. package/dist/{login-command-QM5SBBI2.js → login-command-SG7IWTHW.js} +139 -36
  31. package/dist/{logout-command-THPASOHM.js → logout-command-J2AG5NKC.js} +2 -2
  32. package/dist/{marketplace-command-463DT7O7.js → marketplace-command-NKTQ3VPS.js} +3 -3
  33. package/dist/node.js +3 -3
  34. package/dist/{profile-command-EUWPVWED.js → profile-command-ZPC2DPFV.js} +3 -3
  35. package/dist/{release-command-M4CVNTWL.js → release-command-FKQ6E3TD.js} +10 -10
  36. package/dist/{sandbox-details-command-BRII3QHG.js → sandbox-details-command-DMY2KGA2.js} +4 -4
  37. package/dist/{sandbox-export-command-PCZ5FL4U.js → sandbox-export-command-R6QMEK3D.js} +5 -5
  38. package/dist/{test-command-U4G5Y3UM.js → test-command-56IAEYHX.js} +8 -8
  39. package/dist/{upgrade-command-CKJ4BS2P.js → upgrade-command-M2DZ3ZPD.js} +5 -5
  40. package/dist/{validate-command-S5N37JRP.js → validate-command-CIBQJND7.js} +5 -5
  41. package/dist/{workspace-command-RALSEJSW.js → workspace-command-HZS43PHJ.js} +10 -10
  42. package/guides/cli.md +1 -0
  43. package/guides/deploying.md +18 -0
  44. package/guides/environment.md +1 -1
  45. package/llms-full.txt +1 -1
  46. package/llms.txt +1 -1
  47. package/manifest.json +6 -2
  48. package/package.json +1 -1
  49. package/dist/chunk-ALNQCWAW.js +0 -29
package/CHANGELOG.md CHANGED
@@ -11,19 +11,18 @@ listed here.
11
11
 
12
12
  ---
13
13
 
14
- ## 0.0.4 — Agents get their instructions
14
+ ## 0.0.4 — The markdown your agents read
15
15
 
16
- _2026-08-25_ · [release notes](https://github.com/xanots/sdk/releases/tag/v0.0.4)
16
+ _2026-08-26_ · [release notes](https://github.com/xanots/sdk/releases/tag/v0.0.4)
17
17
 
18
- `knowledge()` lands: the markdown a Xano workspace's AI agents read before they act, authored as real `.md` files in your repo instead of typed into a console. Standing instructions, skills, and reference docs are now workspace source reviewed in a diff, versioned with the code they describe, and redeployed with it. Nothing changes for a workspace that declares none.
18
+ Knowledge is now workspace source: the markdown your Xano agents read before they act is authored as real `.md` files, reviewed in a diff, and deployed with the code it describes. Two commands join the CLI `xanots onboard` puts the scaffold's choices in a browser, and `xanots upgrade` answers the version question on purpose rather than nudging. Windows users should take this one regardless: every npm call in the package was failing before it reached npm.
19
19
 
20
- - `knowledge()` authors the instructions your agents follow
21
- - The body is a real markdown file, never a string in a def
22
- - `refs` ships a whole folder the agent searches on demand
23
- - `type` and `mode` decide what the agent actually receives
24
- - Authoring mistakes that used to deploy silently are now build errors
25
- - `xanots codegen` writes the markdown back out as files
26
- - Repeated releases update knowledge instead of duplicating it
20
+ - `knowledge()` author the markdown your Xano agents read
21
+ - `xanots onboard` pick the scaffold's look in a browser
22
+ - `xanots upgrade` the version question asked on purpose
23
+ - Every npm call failed on a current Node for Windows
24
+ - The guides ship in the tarball
25
+ - `CHANGELOG.md` ships, generated from the releases
27
26
 
28
27
  ---
29
28
 
package/README.md CHANGED
@@ -93,6 +93,10 @@ for you, and the target instance comes from your token rather than a flag.
93
93
  npx @xanots/sdk login
94
94
  ```
95
95
 
96
+ > On a remote shell, container, or Codespace — anywhere your browser can't reach this
97
+ > machine's `127.0.0.1` — add `--paste`. It prints the URL for you to open anywhere, and you
98
+ > paste the redirect back. See [Signing in & deploying](https://github.com/xanots/sdk/blob/main/guides/deploying.md).
99
+
96
100
  **2. Scaffold.** `init` writes a complete project: a Vite frontend under `frontend/` (React
97
101
  19 + shadcn/ui by default, or SvelteKit with `--framework svelte`), a XanoTS backend under
98
102
  `xano/`, and the `xano:export` / `xano:deploy` scripts already wired.
@@ -0,0 +1 @@
1
+ c0021219c47ba8aba005451538637f3d324faefad89c71468080cbe5bd443fa1
package/dist/bin.js CHANGED
@@ -1,15 +1,15 @@
1
1
  #!/usr/bin/env node
2
2
  import {
3
3
  maybeNotifyUpdate
4
- } from "./chunk-T6N3VMMO.js";
4
+ } from "./chunk-ZGA5MUNC.js";
5
5
  import {
6
6
  readVersion,
7
7
  run
8
- } from "./chunk-DUC3PXDG.js";
8
+ } from "./chunk-MS3BRZAZ.js";
9
9
  import {
10
10
  exitCodeOf,
11
11
  reportFailure
12
- } from "./chunk-KGNJM4LN.js";
12
+ } from "./chunk-IVP6TS26.js";
13
13
  import "./chunk-MFIHIS6B.js";
14
14
  import "./chunk-GNPVYOPB.js";
15
15
  import {
@@ -17,7 +17,7 @@ import {
17
17
  error
18
18
  } from "./chunk-EZG76F7R.js";
19
19
  import "./chunk-BPEEGJJA.js";
20
- import "./chunk-YYSJAAJM.js";
20
+ import "./chunk-F5T45NAM.js";
21
21
  import "./chunk-YUPQOLFX.js";
22
22
  import "./chunk-WHOJWOSV.js";
23
23
  import "./chunk-5XZ744TS.js";
@@ -1,9 +1,9 @@
1
1
  import {
2
2
  sandboxBaseUrl
3
- } from "./chunk-ACQCK4DT.js";
3
+ } from "./chunk-OR43PDCW.js";
4
4
  import {
5
5
  getAccessToken
6
- } from "./chunk-C56BC2FY.js";
6
+ } from "./chunk-SG4UBJ47.js";
7
7
  import {
8
8
  exportWorkspaceBundle
9
9
  } from "./chunk-QTNO2WD6.js";
@@ -115,4 +115,4 @@ export {
115
115
  fetchSandboxBundle,
116
116
  runSandboxExportCommand
117
117
  };
118
- //# sourceMappingURL=chunk-AJ7JQ4OU.js.map
118
+ //# sourceMappingURL=chunk-AAFBSOSD.js.map
@@ -1,10 +1,10 @@
1
1
  import {
2
2
  getEnvironment,
3
3
  readEphemeralState
4
- } from "./chunk-DGSF2Q5H.js";
4
+ } from "./chunk-WJYB7DSI.js";
5
5
  import {
6
6
  sandboxBaseUrl
7
- } from "./chunk-ACQCK4DT.js";
7
+ } from "./chunk-OR43PDCW.js";
8
8
  import {
9
9
  fetchReadOrExplain,
10
10
  httpFailure
@@ -66,7 +66,7 @@ async function resolveMetaTarget(auth, opts, deps = {}) {
66
66
  case "sandbox":
67
67
  return resolveSandbox(auth);
68
68
  case "ephemeral": {
69
- const resolveLive = deps.resolveLive ?? (await import("./ephemeral-command-6WJW7LP6.js")).resolveLive;
69
+ const resolveLive = deps.resolveLive ?? (await import("./ephemeral-command-46SL27GJ.js")).resolveLive;
70
70
  return resolveEphemeral(auth, opts.name, { ...deps, resolveLive });
71
71
  }
72
72
  }
@@ -75,4 +75,4 @@ async function resolveMetaTarget(auth, opts, deps = {}) {
75
75
  export {
76
76
  resolveMetaTarget
77
77
  };
78
- //# sourceMappingURL=chunk-VWGJQTNA.js.map
78
+ //# sourceMappingURL=chunk-APOR6TCV.js.map
@@ -73,7 +73,11 @@ var FLAGS = {
73
73
  guest: { spec: "--guest, -g", summary: "Mint a read-only guest session (browse only)" },
74
74
  "url-only": { spec: "--url-only, -u", summary: "Print the dashboard URL instead of opening a browser" },
75
75
  prompt: { spec: "--prompt", summary: "Print only the add-on wiring prompt, for piping to a coding agent" },
76
- port: { spec: "--port <n>", summary: "Fixed loopback callback port (default: ephemeral)" },
76
+ port: { spec: "--port <n>", summary: "Loopback callback port (default: 47100)" },
77
+ paste: {
78
+ spec: "--paste",
79
+ summary: "Sign in without the loopback callback: open the printed URL in any browser and paste the redirect back. For a host whose 127.0.0.1 the browser cannot reach \u2014 remote shell, container, Codespace. Needs a terminal."
80
+ },
77
81
  scope: { spec: '--scope "<list>"', summary: "OAuth scopes to request (default: the built-in set)" },
78
82
  runtime: { spec: "--runtime", summary: "After the round-trip, run each deployed function and report" },
79
83
  capture: { spec: "--capture", summary: "Write each round-tripped function's fetched JSON" },
@@ -481,6 +485,7 @@ var COMMANDS = {
481
485
  summary: "OAuth sign-in \u2014 shared cache, or --local per project",
482
486
  flags: [
483
487
  "local",
488
+ "paste",
484
489
  "port",
485
490
  "scope",
486
491
  "origin",
@@ -670,4 +675,4 @@ export {
670
675
  liveSubcommandNames,
671
676
  suggest
672
677
  };
673
- //# sourceMappingURL=chunk-YYSJAAJM.js.map
678
+ //# sourceMappingURL=chunk-F5T45NAM.js.map
@@ -19,7 +19,7 @@ import {
19
19
  liveSubcommandNames,
20
20
  renderArgs,
21
21
  suggest
22
- } from "./chunk-YYSJAAJM.js";
22
+ } from "./chunk-F5T45NAM.js";
23
23
 
24
24
  // src/emit/help.ts
25
25
  function table(rows, s, indent = " ", fixedWidth) {
@@ -245,4 +245,4 @@ export {
245
245
  reportFailure,
246
246
  exitCodeOf
247
247
  };
248
- //# sourceMappingURL=chunk-KGNJM4LN.js.map
248
+ //# sourceMappingURL=chunk-IVP6TS26.js.map
@@ -44,10 +44,10 @@ import {
44
44
  } from "./chunk-6DHJVLYP.js";
45
45
  import {
46
46
  readVersion
47
- } from "./chunk-DUC3PXDG.js";
47
+ } from "./chunk-MS3BRZAZ.js";
48
48
  import {
49
49
  UsageError
50
- } from "./chunk-KGNJM4LN.js";
50
+ } from "./chunk-IVP6TS26.js";
51
51
  import {
52
52
  blank,
53
53
  detail,
@@ -529,4 +529,4 @@ export {
529
529
  projectShellFiles,
530
530
  runInitCommand
531
531
  };
532
- //# sourceMappingURL=chunk-EAIR6VUL.js.map
532
+ //# sourceMappingURL=chunk-KXCPZUUM.js.map
@@ -130,6 +130,8 @@ var OpenIdProvider = class {
130
130
  configPromise;
131
131
  /** The client_id the resolved config uses — set once `build()` completes. */
132
132
  resolvedClientId;
133
+ /** The issuer the resolved config discovered — set once `build()` completes. */
134
+ resolvedIssuer;
133
135
  redirectUri() {
134
136
  if (!this.opts.redirectUri) {
135
137
  throw new Error("OpenIdProvider: redirectUri is required for the authorize/exchange flow.");
@@ -147,6 +149,19 @@ var OpenIdProvider = class {
147
149
  }
148
150
  return this.resolvedClientId;
149
151
  }
152
+ /**
153
+ * The authorization server's issuer, as resolved by discovery. Only the paste
154
+ * login mode needs it: a pasted BARE code carries no `iss`, and the AS
155
+ * advertises issuer support, so one has to be supplied for the response to
156
+ * validate at all. Same lifecycle guard as `clientId()` — valid once the
157
+ * configuration has resolved.
158
+ */
159
+ issuer() {
160
+ if (!this.resolvedIssuer) {
161
+ throw new Error("OpenIdProvider.issuer() called before the configuration was resolved.");
162
+ }
163
+ return this.resolvedIssuer;
164
+ }
150
165
  async build() {
151
166
  const server = new URL(this.opts.authHost);
152
167
  const options = server.protocol === "http:" ? { execute: [client.allowInsecureRequests] } : void 0;
@@ -166,13 +181,15 @@ var OpenIdProvider = class {
166
181
  });
167
182
  }
168
183
  this.resolvedClientId = clientId;
169
- return client.discovery(
184
+ const config = await client.discovery(
170
185
  server,
171
186
  clientId,
172
187
  { token_endpoint_auth_method: "none" },
173
188
  client.None(),
174
189
  options
175
190
  );
191
+ this.resolvedIssuer = config.serverMetadata().issuer;
192
+ return config;
176
193
  }
177
194
  config() {
178
195
  return this.configPromise ??= this.build();
@@ -180,6 +197,7 @@ var OpenIdProvider = class {
180
197
  async reset() {
181
198
  this.configPromise = void 0;
182
199
  this.resolvedClientId = void 0;
200
+ this.resolvedIssuer = void 0;
183
201
  if (this.opts.redirectUri) {
184
202
  clearClient({ authHost: this.opts.authHost, redirectUri: this.opts.redirectUri });
185
203
  }
@@ -465,4 +483,4 @@ export {
465
483
  resolveScope,
466
484
  assertHttpsOrigin
467
485
  };
468
- //# sourceMappingURL=chunk-7REDODS2.js.map
486
+ //# sourceMappingURL=chunk-LLWK6H77.js.map
@@ -9,7 +9,7 @@ import {
9
9
  unknownFlag,
10
10
  unknownHelpTopic,
11
11
  unknownSubcommand
12
- } from "./chunk-KGNJM4LN.js";
12
+ } from "./chunk-IVP6TS26.js";
13
13
  import {
14
14
  readLockFile,
15
15
  writeLockFile
@@ -30,7 +30,7 @@ import {
30
30
  getSubcommand,
31
31
  isCommand,
32
32
  suggest
33
- } from "./chunk-YYSJAAJM.js";
33
+ } from "./chunk-F5T45NAM.js";
34
34
  import {
35
35
  FILTER_NAMES,
36
36
  KNOWLEDGE_DIR,
@@ -395,6 +395,7 @@ function parseArgs(argv) {
395
395
  let authHost;
396
396
  let authFile;
397
397
  let useLocal = false;
398
+ let paste = false;
398
399
  let allWorkspaces = false;
399
400
  let guest = false;
400
401
  let urlOnly = false;
@@ -515,6 +516,8 @@ function parseArgs(argv) {
515
516
  authFile = arg.slice("--config=".length);
516
517
  } else if (arg === "--local") {
517
518
  useLocal = true;
519
+ } else if (arg === "--paste") {
520
+ paste = true;
518
521
  } else if (arg === "--all-workspaces") {
519
522
  allWorkspaces = true;
520
523
  } else if (arg === "--guest" || arg === "-g") {
@@ -686,6 +689,7 @@ function parseArgs(argv) {
686
689
  authHost,
687
690
  authFile,
688
691
  local: useLocal,
692
+ paste,
689
693
  allWorkspaces,
690
694
  guest,
691
695
  urlOnly,
@@ -928,11 +932,11 @@ async function run(argv) {
928
932
  return;
929
933
  }
930
934
  if (command === "init") {
931
- const { runInitCommand } = await import("./init-command-GJUPWTKA.js");
935
+ const { runInitCommand } = await import("./init-command-NCRPVFGE.js");
932
936
  return runInitCommand(args);
933
937
  }
934
938
  if (command === "completion") {
935
- const { isCompletionShell, runCompletionCommand, COMPLETION_SHELLS } = await import("./completion-4GYN752B.js");
939
+ const { isCompletionShell, runCompletionCommand, COMPLETION_SHELLS } = await import("./completion-GHP5RRLQ.js");
936
940
  const shell = args.positionals[0];
937
941
  if (shell === void 0 || !isCompletionShell(shell)) {
938
942
  throw new UsageError(
@@ -943,31 +947,31 @@ async function run(argv) {
943
947
  return runCompletionCommand(shell);
944
948
  }
945
949
  if (command === "upgrade") {
946
- const { runUpgradeCommand } = await import("./upgrade-command-CKJ4BS2P.js");
950
+ const { runUpgradeCommand } = await import("./upgrade-command-M2DZ3ZPD.js");
947
951
  return runUpgradeCommand(args);
948
952
  }
949
953
  if (command === "lock") {
950
- const { runLockCommand } = await import("./lock-commands-7IH7RSSP.js");
954
+ const { runLockCommand } = await import("./lock-commands-6UONZW26.js");
951
955
  return runLockCommand(args);
952
956
  }
953
957
  if (command === "login") {
954
- const { runLoginCommand } = await import("./login-command-QM5SBBI2.js");
958
+ const { runLoginCommand } = await import("./login-command-SG7IWTHW.js");
955
959
  return runLoginCommand(args);
956
960
  }
957
961
  if (command === "logout") {
958
- const { runLogoutCommand } = await import("./logout-command-THPASOHM.js");
962
+ const { runLogoutCommand } = await import("./logout-command-J2AG5NKC.js");
959
963
  return runLogoutCommand(args);
960
964
  }
961
965
  if (command === "deploy") {
962
- const { runDeployCommand } = await import("./deploy-command-M2S4HHLC.js");
966
+ const { runDeployCommand } = await import("./deploy-command-XOH76USO.js");
963
967
  return runDeployCommand(args);
964
968
  }
965
969
  if (command === "ephemeral") {
966
- const { runEphemeralCommand } = await import("./ephemeral-command-6WJW7LP6.js");
970
+ const { runEphemeralCommand } = await import("./ephemeral-command-46SL27GJ.js");
967
971
  return runEphemeralCommand(args);
968
972
  }
969
973
  if (command === "release") {
970
- const { runReleaseCommand } = await import("./release-command-M4CVNTWL.js");
974
+ const { runReleaseCommand } = await import("./release-command-FKQ6E3TD.js");
971
975
  return runReleaseCommand(args);
972
976
  }
973
977
  if (command === "sandbox") {
@@ -975,47 +979,47 @@ async function run(argv) {
975
979
  throw removedSubcommand("sandbox", "deploy");
976
980
  }
977
981
  if (args.subcommand === "details") {
978
- const { runSandboxDetailsCommand } = await import("./sandbox-details-command-BRII3QHG.js");
982
+ const { runSandboxDetailsCommand } = await import("./sandbox-details-command-DMY2KGA2.js");
979
983
  return runSandboxDetailsCommand(args);
980
984
  }
981
985
  if (args.subcommand === "export") {
982
- const { runSandboxExportCommand } = await import("./sandbox-export-command-PCZ5FL4U.js");
986
+ const { runSandboxExportCommand } = await import("./sandbox-export-command-R6QMEK3D.js");
983
987
  return runSandboxExportCommand(args);
984
988
  }
985
989
  if (args.subcommand === "codegen") {
986
- const { runCodegenCommand } = await import("./codegen-command-Z7WQMOJ7.js");
990
+ const { runCodegenCommand } = await import("./codegen-command-BLOS3GR3.js");
987
991
  return runCodegenCommand(args, { kind: "sandbox" });
988
992
  }
989
993
  throw unknownSubcommand("sandbox", args.subcommand);
990
994
  }
991
995
  if (command === "test") {
992
- const { runTestCommand } = await import("./test-command-U4G5Y3UM.js");
996
+ const { runTestCommand } = await import("./test-command-56IAEYHX.js");
993
997
  return runTestCommand(args);
994
998
  }
995
999
  if (command === "workspace") {
996
- const { runWorkspaceCommand } = await import("./workspace-command-RALSEJSW.js");
1000
+ const { runWorkspaceCommand } = await import("./workspace-command-HZS43PHJ.js");
997
1001
  return runWorkspaceCommand(args);
998
1002
  }
999
1003
  if (command === "codegen") {
1000
- const { runCodegenCommand } = await import("./codegen-command-Z7WQMOJ7.js");
1004
+ const { runCodegenCommand } = await import("./codegen-command-BLOS3GR3.js");
1001
1005
  return runCodegenCommand(args, { kind: "file" });
1002
1006
  }
1003
1007
  if (command === "profile") {
1004
1008
  if (args.subcommand !== "me") {
1005
1009
  throw unknownSubcommand("profile", args.subcommand);
1006
1010
  }
1007
- const { runProfileCommand } = await import("./profile-command-EUWPVWED.js");
1011
+ const { runProfileCommand } = await import("./profile-command-ZPC2DPFV.js");
1008
1012
  return runProfileCommand(args);
1009
1013
  }
1010
1014
  if (command === "whoami") {
1011
- const { runProfileCommand } = await import("./profile-command-EUWPVWED.js");
1015
+ const { runProfileCommand } = await import("./profile-command-ZPC2DPFV.js");
1012
1016
  return runProfileCommand(args);
1013
1017
  }
1014
1018
  if (command === "marketplace") {
1015
1019
  if (!["list", "search", "details", "install"].includes(args.subcommand ?? "")) {
1016
1020
  throw unknownSubcommand("marketplace", args.subcommand);
1017
1021
  }
1018
- const marketplace = await import("./marketplace-command-463DT7O7.js");
1022
+ const marketplace = await import("./marketplace-command-NKTQ3VPS.js");
1019
1023
  if (args.subcommand === "list") return marketplace.runMarketplaceListCommand(args);
1020
1024
  if (args.subcommand === "search") return marketplace.runMarketplaceSearchCommand(args);
1021
1025
  if (args.subcommand === "details") return marketplace.runMarketplaceDetailsCommand(args);
@@ -1025,7 +1029,7 @@ async function run(argv) {
1025
1029
  throw unknownCommand("push");
1026
1030
  }
1027
1031
  if (command === "validate") {
1028
- const { runValidateCommand } = await import("./validate-command-S5N37JRP.js");
1032
+ const { runValidateCommand } = await import("./validate-command-CIBQJND7.js");
1029
1033
  return runValidateCommand(args);
1030
1034
  }
1031
1035
  if (command !== "compile" && command !== "export" && command !== "paths" && command !== "routes") {
@@ -1290,4 +1294,4 @@ export {
1290
1294
  exportBundleJson,
1291
1295
  compileBundle
1292
1296
  };
1293
- //# sourceMappingURL=chunk-DUC3PXDG.js.map
1297
+ //# sourceMappingURL=chunk-MS3BRZAZ.js.map
@@ -18,7 +18,7 @@ import {
18
18
  } from "./chunk-ZOYMZZ3S.js";
19
19
  import {
20
20
  getAccessToken
21
- } from "./chunk-C56BC2FY.js";
21
+ } from "./chunk-SG4UBJ47.js";
22
22
  import {
23
23
  exportWorkspaceBundle
24
24
  } from "./chunk-QTNO2WD6.js";
@@ -27,7 +27,7 @@ import {
27
27
  resolveFrontendPreset,
28
28
  resolveThemeChoice,
29
29
  sanitizeAppName
30
- } from "./chunk-EAIR6VUL.js";
30
+ } from "./chunk-KXCPZUUM.js";
31
31
  import {
32
32
  XANO_DIR,
33
33
  resolveAiPresets,
@@ -71,10 +71,10 @@ import {
71
71
  import {
72
72
  loadDefault,
73
73
  readVersion
74
- } from "./chunk-DUC3PXDG.js";
74
+ } from "./chunk-MS3BRZAZ.js";
75
75
  import {
76
76
  UsageError
77
- } from "./chunk-KGNJM4LN.js";
77
+ } from "./chunk-IVP6TS26.js";
78
78
  import {
79
79
  blank,
80
80
  detail,
@@ -6731,7 +6731,7 @@ async function fetchBundle(args, source) {
6731
6731
  if (source.kind === "sandbox") {
6732
6732
  const auth3 = await getAccessToken(args);
6733
6733
  step("Reading the sandbox workspace");
6734
- const { fetchSandboxBundle } = await import("./sandbox-export-command-PCZ5FL4U.js");
6734
+ const { fetchSandboxBundle } = await import("./sandbox-export-command-R6QMEK3D.js");
6735
6735
  return {
6736
6736
  bundle: await fetchSandboxBundle(auth3),
6737
6737
  origin: { source: "sandbox", origin: auth3.instance }
@@ -6745,7 +6745,7 @@ async function fetchBundle(args, source) {
6745
6745
  );
6746
6746
  }
6747
6747
  const auth3 = await getAccessToken(args);
6748
- const { resolveLive, fetchEphemeralBundle } = await import("./ephemeral-command-6WJW7LP6.js");
6748
+ const { resolveLive, fetchEphemeralBundle } = await import("./ephemeral-command-46SL27GJ.js");
6749
6749
  const summary = await resolveLive(auth3, auth3.workspaceId, name);
6750
6750
  step(`Reading ephemeral "${name}"`);
6751
6751
  return {
@@ -7014,4 +7014,4 @@ export {
7014
7014
  verifyCrashEntry,
7015
7015
  blameGeneratedFile
7016
7016
  };
7017
- //# sourceMappingURL=chunk-VKD3EBKG.js.map
7017
+ //# sourceMappingURL=chunk-OARSPAIE.js.map
@@ -4,7 +4,7 @@ import {
4
4
  } from "./chunk-NDZFBZHC.js";
5
5
  import {
6
6
  getAccessToken
7
- } from "./chunk-C56BC2FY.js";
7
+ } from "./chunk-SG4UBJ47.js";
8
8
  import {
9
9
  isMachineOutput,
10
10
  writeJson
@@ -97,4 +97,4 @@ export {
97
97
  fetchSandboxDetails,
98
98
  runSandboxDetailsCommand
99
99
  };
100
- //# sourceMappingURL=chunk-ACQCK4DT.js.map
100
+ //# sourceMappingURL=chunk-OR43PDCW.js.map
@@ -0,0 +1,59 @@
1
+ import {
2
+ UsageError
3
+ } from "./chunk-IVP6TS26.js";
4
+ import {
5
+ style
6
+ } from "./chunk-EZG76F7R.js";
7
+
8
+ // src/emit/prompt.ts
9
+ import { createInterface } from "readline";
10
+ async function confirm(message, opts) {
11
+ if (process.stdin.isTTY !== true) {
12
+ throw new UsageError(
13
+ `Cannot ask for confirmation: stdin is not a terminal. Re-run with ${opts.flag} to confirm without being asked.`,
14
+ { helpFor: opts.helpFor }
15
+ );
16
+ }
17
+ const rl = createInterface({ input: process.stdin, output: process.stderr });
18
+ try {
19
+ const answer = await new Promise((res) => rl.question(`${style.yellow("?")} ${message} (y/N) `, res));
20
+ return /^y(es)?$/i.test(answer.trim());
21
+ } finally {
22
+ rl.close();
23
+ }
24
+ }
25
+ var MAX_EMPTY_ANSWERS = 3;
26
+ async function promptLine(message, opts) {
27
+ if (process.stdin.isTTY !== true) {
28
+ throw new UsageError(
29
+ `Cannot prompt: stdin is not a terminal. ${opts.noTtyHint}`,
30
+ { helpFor: opts.helpFor }
31
+ );
32
+ }
33
+ const rl = createInterface({ input: process.stdin, output: process.stderr });
34
+ try {
35
+ for (let attempt = 0; attempt < MAX_EMPTY_ANSWERS; attempt++) {
36
+ const onClose = () => settle(null);
37
+ let settle;
38
+ const answer = await new Promise((resolve) => {
39
+ settle = resolve;
40
+ rl.once("close", onClose);
41
+ rl.question(`${style.yellow("?")} ${message} `, resolve);
42
+ }).finally(() => rl.off("close", onClose));
43
+ if (answer === null) throw new UsageError(`Input ended before an answer arrived. ${opts.noTtyHint}`);
44
+ const trimmed = answer.trim();
45
+ if (trimmed !== "") return trimmed;
46
+ process.stderr.write(`${style.yellow("!")} A value is required.
47
+ `);
48
+ }
49
+ throw new UsageError(`No value entered. ${opts.noTtyHint}`, { helpFor: opts.helpFor });
50
+ } finally {
51
+ rl.close();
52
+ }
53
+ }
54
+
55
+ export {
56
+ confirm,
57
+ promptLine
58
+ };
59
+ //# sourceMappingURL=chunk-PGBK64U5.js.map
@@ -1,9 +1,9 @@
1
1
  import {
2
2
  compileBundle
3
- } from "./chunk-DUC3PXDG.js";
3
+ } from "./chunk-MS3BRZAZ.js";
4
4
  import {
5
5
  missingArgument
6
- } from "./chunk-KGNJM4LN.js";
6
+ } from "./chunk-IVP6TS26.js";
7
7
 
8
8
  // src/emit/bundle-input.ts
9
9
  import { existsSync, readFileSync } from "fs";
@@ -34,4 +34,4 @@ export {
34
34
  assertBundleInput,
35
35
  loadBundleText
36
36
  };
37
- //# sourceMappingURL=chunk-SWIXWJIY.js.map
37
+ //# sourceMappingURL=chunk-QA5ICJ4M.js.map
@@ -12,7 +12,7 @@ import {
12
12
  resolveAuthHost,
13
13
  resolveScope,
14
14
  writeCredential
15
- } from "./chunk-7REDODS2.js";
15
+ } from "./chunk-LLWK6H77.js";
16
16
  import {
17
17
  detail,
18
18
  hostLabel,
@@ -251,4 +251,4 @@ export {
251
251
  envMetaCredentialVarsSet,
252
252
  getAccessToken
253
253
  };
254
- //# sourceMappingURL=chunk-C56BC2FY.js.map
254
+ //# sourceMappingURL=chunk-SG4UBJ47.js.map
@@ -2,6 +2,9 @@
2
2
  import { createServer } from "http";
3
3
  import { spawn } from "child_process";
4
4
  var DEFAULT_TIMEOUT_MS = 5 * 60 * 1e3;
5
+ function loopbackRedirectUri(port, callbackPath) {
6
+ return `http://127.0.0.1:${port}${callbackPath}`;
7
+ }
5
8
  function formatDuration(ms) {
6
9
  const seconds = Math.round(ms / 1e3);
7
10
  if (seconds < 60) return `${seconds} second${seconds === 1 ? "" : "s"}`;
@@ -81,7 +84,7 @@ function startCallbackServer(opts) {
81
84
  });
82
85
  server.listen(port ?? 0, "127.0.0.1", () => {
83
86
  const boundPort = server.address().port;
84
- redirectUri = `http://127.0.0.1:${boundPort}${callbackPath}`;
87
+ redirectUri = loopbackRedirectUri(boundPort, callbackPath);
85
88
  resolveListener({
86
89
  redirectUri,
87
90
  waitForCallback,
@@ -119,7 +122,8 @@ function openBrowser(url) {
119
122
  }
120
123
 
121
124
  export {
125
+ loopbackRedirectUri,
122
126
  startCallbackServer,
123
127
  openBrowser
124
128
  };
125
- //# sourceMappingURL=chunk-VTIL47DT.js.map
129
+ //# sourceMappingURL=chunk-W5NOKYEG.js.map
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  ensureGitignored
3
- } from "./chunk-7REDODS2.js";
3
+ } from "./chunk-LLWK6H77.js";
4
4
  import {
5
5
  atomicWrite
6
6
  } from "./chunk-GNPVYOPB.js";
@@ -57,4 +57,4 @@ export {
57
57
  setEnvironment,
58
58
  clearEnvironment
59
59
  };
60
- //# sourceMappingURL=chunk-DGSF2Q5H.js.map
60
+ //# sourceMappingURL=chunk-WJYB7DSI.js.map
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  readVersion
3
- } from "./chunk-DUC3PXDG.js";
3
+ } from "./chunk-MS3BRZAZ.js";
4
4
  import {
5
5
  atomicWrite
6
6
  } from "./chunk-GNPVYOPB.js";
@@ -170,4 +170,4 @@ export {
170
170
  upgradeCommand,
171
171
  maybeNotifyUpdate
172
172
  };
173
- //# sourceMappingURL=chunk-T6N3VMMO.js.map
173
+ //# sourceMappingURL=chunk-ZGA5MUNC.js.map
package/dist/cli.d.ts CHANGED
@@ -141,8 +141,15 @@ interface ParsedArgs {
141
141
  urlOnly: boolean;
142
142
  /** `marketplace details --prompt`: print the add-on's agent prompt alone, for piping. */
143
143
  prompt: boolean;
144
- /** `login --port <n>`: fixed loopback callback port (default: an ephemeral port). */
144
+ /** `login --port <n>`: loopback callback port (default: `DEFAULT_PORT`, 47100). */
145
145
  port: number | undefined;
146
+ /**
147
+ * `login --paste`: skip the loopback callback server and read the redirect back
148
+ * from the user, for a host whose 127.0.0.1 the browser cannot reach (remote
149
+ * shell, container, Codespace). Distinct from `XANO_NO_BROWSER`, which only
150
+ * suppresses the browser launch and still needs the redirect to arrive.
151
+ */
152
+ paste: boolean;
146
153
  /** `login --scope "<space list>"`: OAuth scopes to request (default: the built-in xano-cli set). */
147
154
  scope: string | undefined;
148
155
  /** `validate --runtime`: after import + round-trip, run each deployed function and report. */