@tinycloud/cli 0.9.1-beta.3 → 0.9.1-beta.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.
@@ -26068,7 +26068,7 @@ async function verifyPkhSignature(did, payload, signature) {
26068
26068
  }
26069
26069
  function verifyDidKeySignature(did, payload, signature) {
26070
26070
  const publicKey = ed25519PublicKeyFromDidKey2(did);
26071
- const signatureBytes = decodeBase64Url3(signature);
26071
+ const signatureBytes = decodeBase64Url4(signature);
26072
26072
  if (signatureBytes.length !== 64) {
26073
26073
  throw new LocationRecordValidationError(
26074
26074
  "did:key signature must be a base64url Ed25519 signature"
@@ -26098,7 +26098,7 @@ function ed25519PublicKeyFromDidKey2(did) {
26098
26098
  "did:key must be an Ed25519 public key"
26099
26099
  );
26100
26100
  }
26101
- function decodeBase64Url3(value) {
26101
+ function decodeBase64Url4(value) {
26102
26102
  const alphabet2 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_";
26103
26103
  const bytes2 = [];
26104
26104
  let buffer = 0;
@@ -34703,6 +34703,9 @@ function inputUrl(value, stdin) {
34703
34703
  if (value === void 0 || value.length === 0) throw new CLIError("INVALID_ARGUMENT", "a share URL or - is required", 2);
34704
34704
  return Promise.resolve(value);
34705
34705
  }
34706
+ function jsonOutput(options, command) {
34707
+ return options.json === true || command.optsWithGlobals().json === true;
34708
+ }
34706
34709
  function expires(value) {
34707
34710
  try {
34708
34711
  return new Date(Date.now() + parseDuration(value));
@@ -34753,8 +34756,9 @@ function assertAggregateInputLimit(inputs, maxBytes) {
34753
34756
  }
34754
34757
  function registerShareCommand(program) {
34755
34758
  const share = program.command("share").description("Publish and consume TinyCloud Share links");
34756
- share.command("publish <files...>").description("Publish one or more bounded files as a Share").option("--name <filename>", "Filename for stdin input").option("--to <target>", "Share target", "anyone").option("--notify", "Request idempotent email delivery for addressed targets").option("--expires <duration>", "Share lifetime", "7d").option("--max-bytes <bytes>", "Bound input bytes").option("--media-type <type>", "Media type for a single input").option("--action <actions...>", "Addressed permission: read, list, or edit").option("--prefix", "Publish multiple inputs beneath one addressed prefix").option("--binary", "Allow non-UTF-8 bearer content").option("--inline", "Embed the sealed envelope in the URL fragment").option("--compact", "Use a CID-addressed compact link (default)").option("--json", "Print versioned redacted JSON").option("--registry <url>", "Authenticated registry upload endpoint", DEFAULT_REGISTRY).option("--viewer-origin <origin>", "Canonical HTTPS viewer origin", SHARE_ORIGIN).option("--insecure-registry", "Allow an explicit localhost HTTP registry for hermetic tests").action(async (files, options) => {
34759
+ share.command("publish <files...>").description("Publish one or more bounded files as a Share").option("--name <filename>", "Filename for stdin input").option("--to <target>", "Share target", "anyone").option("--notify", "Request idempotent email delivery for addressed targets").option("--expires <duration>", "Share lifetime", "7d").option("--max-bytes <bytes>", "Bound input bytes").option("--media-type <type>", "Media type for a single input").option("--action <actions...>", "Addressed permission: read, list, or edit").option("--prefix", "Publish multiple inputs beneath one addressed prefix").option("--binary", "Allow non-UTF-8 bearer content").option("--inline", "Embed the sealed envelope in the URL fragment").option("--compact", "Use a CID-addressed compact link (default)").option("--json", "Print versioned redacted JSON").option("--registry <url>", "Authenticated registry upload endpoint", DEFAULT_REGISTRY).option("--viewer-origin <origin>", "Canonical HTTPS viewer origin", SHARE_ORIGIN).option("--insecure-registry", "Allow an explicit localhost HTTP registry for hermetic tests").action(async (files, options, command) => {
34757
34760
  try {
34761
+ const json = jsonOutput(options, command);
34758
34762
  if (options.inline && options.compact) throw new CLIError("INVALID_ARGUMENT", "--inline and --compact are mutually exclusive", 2);
34759
34763
  const maxBytes = byteLimit(options.maxBytes);
34760
34764
  if (files.length === 0 || files.includes("-") && files.length > 1) throw new CLIError("INVALID_ARGUMENT", "stdin must be the only publish input", 2);
@@ -34786,7 +34790,7 @@ function registerShareCommand(program) {
34786
34790
  ...publishServices()
34787
34791
  });
34788
34792
  if ("state" in result) {
34789
- if (options.json) {
34793
+ if (json) {
34790
34794
  writeJson2({ protocol: "tinycloud-share", version: 1, authorization: authorizationRequiredJson(result) });
34791
34795
  process.exitCode = 6;
34792
34796
  return;
@@ -34799,25 +34803,27 @@ function registerShareCommand(program) {
34799
34803
  const delivery = await notifyShare({ shareId: record.shareId, recipient: target.address, record, adapter: shareServices.delivery });
34800
34804
  if (delivery.state === "partial-failure") process.exitCode = 9;
34801
34805
  }
34802
- if (options.json) writeJson2(redactPublishedShare(result));
34806
+ if (json) writeJson2(redactPublishedShare(result));
34803
34807
  else publishHuman(result);
34804
34808
  } catch (error) {
34805
34809
  handleError(shareCliError(error));
34806
34810
  }
34807
34811
  });
34808
- share.command("inspect [url]").description("Verify a share link and print safe metadata").option("--stdin", "Read the complete URL from stdin").option("--json", "Print versioned redacted JSON").option("--registry <url>", "Registry read endpoint", DEFAULT_READ_REGISTRY).option("--viewer-origin <origin>", "Require this canonical Share origin", SHARE_ORIGIN).action(async (url, options) => {
34812
+ share.command("inspect [url]").description("Verify a share link and print safe metadata").option("--stdin", "Read the complete URL from stdin").option("--json", "Print versioned redacted JSON").option("--registry <url>", "Registry read endpoint", DEFAULT_READ_REGISTRY).option("--viewer-origin <origin>", "Require this canonical Share origin", SHARE_ORIGIN).action(async (url, options, command) => {
34809
34813
  try {
34814
+ const json = jsonOutput(options, command);
34810
34815
  const link2 = await inputUrl(url, options.stdin === true);
34811
34816
  const result = await inspectShare(link2, { registryBaseUrl: options.registry, expectedOrigin: options.viewerOrigin, ...fetchServices() });
34812
- if (options.json) writeJson2(result);
34817
+ if (json) writeJson2(result);
34813
34818
  else inspectHuman(result);
34814
34819
  } catch (error) {
34815
34820
  handleError(shareCliError(error));
34816
34821
  }
34817
34822
  });
34818
- share.command("receive [url]").description("Verify and receive a share link").option("--stdin", "Read the complete URL from stdin").option("--output <directory>", "Create the file in this directory").option("--stdout", "Write verified plaintext bytes to stdout").option("--force", "Allow replacing an existing non-symlink output").option("--max-bytes <bytes>", "Bound received content bytes").option("--resume-token <token>", "Resume a previously returned recipient authorization step").option("--authorization-proof-file <path>", "Read the JSON authorization proof from a file").option("--json", "Print versioned redacted JSON").option("--registry <url>", "Registry read endpoint", DEFAULT_READ_REGISTRY).option("--viewer-origin <origin>", "Require this canonical Share origin", SHARE_ORIGIN).option("--legacy", "Read a legacy tc1: link (read-only)").action(async (url, options) => {
34823
+ share.command("receive [url]").description("Verify and receive a share link").option("--stdin", "Read the complete URL from stdin").option("--output <directory>", "Create the file in this directory").option("--stdout", "Write verified plaintext bytes to stdout").option("--force", "Allow replacing an existing non-symlink output").option("--max-bytes <bytes>", "Bound received content bytes").option("--resume-token <token>", "Resume a previously returned recipient authorization step").option("--authorization-proof-file <path>", "Read the JSON authorization proof from a file").option("--json", "Print versioned redacted JSON").option("--registry <url>", "Registry read endpoint", DEFAULT_READ_REGISTRY).option("--viewer-origin <origin>", "Require this canonical Share origin", SHARE_ORIGIN).option("--legacy", "Read a legacy tc1: link (read-only)").action(async (url, options, command) => {
34819
34824
  try {
34820
- if (options.stdout && options.json) throw new CLIError("INVALID_ARGUMENT", "--stdout and --json are mutually exclusive", 2);
34825
+ const json = jsonOutput(options, command);
34826
+ if (options.stdout && json) throw new CLIError("INVALID_ARGUMENT", "--stdout and --json are mutually exclusive", 2);
34821
34827
  const maxBytes = byteLimit(options.maxBytes);
34822
34828
  const link2 = await inputUrl(url, options.stdin === true);
34823
34829
  const proof = await authorizationProof(options);
@@ -34829,7 +34835,7 @@ function registerShareCommand(program) {
34829
34835
  return;
34830
34836
  }
34831
34837
  const output2 = await writeShareOutput(options.output ?? ".", "share.md", bytes, options.force === true);
34832
- if (options.json) writeJson2({ protocol: "tinycloud-share", version: 1, legacy: true, path: output2 });
34838
+ if (json) writeJson2({ protocol: "tinycloud-share", version: 1, legacy: true, path: output2 });
34833
34839
  else receiveHuman(output2);
34834
34840
  return;
34835
34841
  }
@@ -34843,7 +34849,7 @@ function registerShareCommand(program) {
34843
34849
  ...proof === void 0 ? {} : { authorizationProof: proof }
34844
34850
  });
34845
34851
  if ("state" in result) {
34846
- if (options.json) {
34852
+ if (json) {
34847
34853
  writeJson2({ protocol: "tinycloud-share", version: 1, authorization: authorizationRequiredJson(result) });
34848
34854
  process.exitCode = 6;
34849
34855
  return;
@@ -34855,14 +34861,15 @@ function registerShareCommand(program) {
34855
34861
  return;
34856
34862
  }
34857
34863
  const output = await writeShareOutput(options.output ?? ".", result.metadata.display.filename ?? "share.md", result.bytes, options.force === true);
34858
- if (options.json) receiveJson(result, output);
34864
+ if (json) receiveJson(result, output);
34859
34865
  else receiveHuman(output);
34860
34866
  } catch (error) {
34861
34867
  handleError(shareCliError(error));
34862
34868
  }
34863
34869
  });
34864
- share.command("migrate [url]").description("Read a legacy tc1 link and re-mint a modern Share link").option("--stdin", "Read the complete legacy link from stdin").option("--name <filename>", "Filename for the migrated content", "migrated.md").option("--to <target>", "Modern Share target", "anyone").option("--notify", "Request idempotent email delivery for addressed targets").option("--expires <duration>", "Modern share lifetime", "7d").option("--max-bytes <bytes>", "Bound migrated content bytes").option("--inline", "Embed the sealed envelope in the URL fragment").option("--registry <url>", "Authenticated registry upload endpoint", DEFAULT_REGISTRY).option("--viewer-origin <origin>", "Canonical HTTPS viewer origin", SHARE_ORIGIN).option("--insecure-registry", "Allow an explicit localhost HTTP registry for hermetic tests").option("--json", "Print versioned redacted JSON").action(async (url, options) => {
34870
+ share.command("migrate [url]").description("Read a legacy tc1 link and re-mint a modern Share link").option("--stdin", "Read the complete legacy link from stdin").option("--name <filename>", "Filename for the migrated content", "migrated.md").option("--to <target>", "Modern Share target", "anyone").option("--notify", "Request idempotent email delivery for addressed targets").option("--expires <duration>", "Modern share lifetime", "7d").option("--max-bytes <bytes>", "Bound migrated content bytes").option("--inline", "Embed the sealed envelope in the URL fragment").option("--registry <url>", "Authenticated registry upload endpoint", DEFAULT_REGISTRY).option("--viewer-origin <origin>", "Canonical HTTPS viewer origin", SHARE_ORIGIN).option("--insecure-registry", "Allow an explicit localhost HTTP registry for hermetic tests").option("--json", "Print versioned redacted JSON").action(async (url, options, command) => {
34865
34871
  try {
34872
+ const json = jsonOutput(options, command);
34866
34873
  if (shareServices.legacyReader === void 0) throw new CLIError("UNSUPPORTED_LINK", "legacy migration requires an installed read-only tc1 adapter", 2);
34867
34874
  const link2 = await inputUrl(url, options.stdin === true);
34868
34875
  if (!isLegacyShareLink(link2)) throw new CLIError("UNSUPPORTED_LINK", "only tc1: links can be migrated", 2);
@@ -34898,41 +34905,44 @@ function registerShareCommand(program) {
34898
34905
  return result;
34899
34906
  }
34900
34907
  });
34901
- if (options.json) writeJson2({ protocol: "tinycloud-share", version: 1, legacy: true, migrated: redactPublishedShare(migrated.migrated) });
34908
+ if (json) writeJson2({ protocol: "tinycloud-share", version: 1, legacy: true, migrated: redactPublishedShare(migrated.migrated) });
34902
34909
  else publishHuman(migrated.migrated);
34903
34910
  } catch (error) {
34904
34911
  handleError(shareCliError(error));
34905
34912
  }
34906
34913
  });
34907
- share.command("list").description("List encrypted sender history without complete bearer URLs").option("--json", "Print versioned redacted JSON").action(async (options) => {
34914
+ share.command("list").description("List encrypted sender history without complete bearer URLs").option("--json", "Print versioned redacted JSON").action(async (options, command) => {
34908
34915
  try {
34916
+ const json = jsonOutput(options, command);
34909
34917
  if (shareServices.records === void 0) throw new CLIError("AUTH_REQUIRED", "sender history storage is not configured", 3);
34910
34918
  const result = await listShares(shareServices.records);
34911
- if (options.json) writeJson2({ protocol: "tinycloud-share", version: 1, shares: result });
34919
+ if (json) writeJson2({ protocol: "tinycloud-share", version: 1, shares: result });
34912
34920
  else process.stdout.write(result.map((item) => `${item.shareId} ${item.target} ${item.expiresAt}`).join("\n") + (result.length ? "\n" : ""));
34913
34921
  } catch (error) {
34914
34922
  handleError(shareCliError(error));
34915
34923
  }
34916
34924
  });
34917
- share.command("show <id>").description("Show one redacted sender-history record").option("--reveal-link", "Explicitly include the complete link").option("--json", "Print versioned redacted JSON").action(async (id, options) => {
34925
+ share.command("show <id>").description("Show one redacted sender-history record").option("--reveal-link", "Explicitly include the complete link").option("--json", "Print versioned redacted JSON").action(async (id, options, command) => {
34918
34926
  try {
34919
- if (options.revealLink && options.json) throw new CLIError("INVALID_ARGUMENT", "--reveal-link cannot be combined with --json", 2);
34927
+ const json = jsonOutput(options, command);
34928
+ if (options.revealLink && json) throw new CLIError("INVALID_ARGUMENT", "--reveal-link cannot be combined with --json", 2);
34920
34929
  if (shareServices.records === void 0) throw new CLIError("AUTH_REQUIRED", "sender history storage is not configured", 3);
34921
34930
  const result = await showShare({ storage: shareServices.records, shareId: id, revealLink: options.revealLink === true, link: options.revealLink ? await shareServices.linkFor?.(id) : void 0 });
34922
- if (options.json) writeJson2({ protocol: "tinycloud-share", version: 1, share: result });
34931
+ if (json) writeJson2({ protocol: "tinycloud-share", version: 1, share: result });
34923
34932
  else writeJson2(result);
34924
34933
  } catch (error) {
34925
34934
  handleError(shareCliError(error));
34926
34935
  }
34927
34936
  });
34928
- share.command("notify <id>").description("Retry idempotent delivery without recreating the share").requiredOption("--to <address>", "Recipient email").option("--json", "Print versioned JSON").action(async (id, options) => {
34937
+ share.command("notify <id>").description("Retry idempotent delivery without recreating the share").requiredOption("--to <address>", "Recipient email").option("--json", "Print versioned JSON").action(async (id, options, command) => {
34929
34938
  try {
34939
+ const json = jsonOutput(options, command);
34930
34940
  if (shareServices.delivery === void 0) throw new CLIError("AUTH_REQUIRED", "delivery authority is not configured", 3);
34931
34941
  if (shareServices.records === void 0) throw new CLIError("AUTH_REQUIRED", "sender history storage is not configured", 3);
34932
34942
  const record = await shareServices.records.get(id);
34933
34943
  if (record === void 0) throw new CLIError("NOT_FOUND", "share not found", 4);
34934
34944
  const result = await notifyShare({ shareId: id, recipient: options.to, record, adapter: shareServices.delivery });
34935
- if (options.json) writeJson2(result);
34945
+ if (json) writeJson2(result);
34936
34946
  else process.stdout.write(`${result.state}
34937
34947
  `);
34938
34948
  if (result.state === "partial-failure") process.exitCode = 9;
@@ -34940,8 +34950,9 @@ function registerShareCommand(program) {
34940
34950
  handleError(shareCliError(error));
34941
34951
  }
34942
34952
  });
34943
- share.command("revoke <id>").description("Revoke addressed shares; report bearer retention honestly").option("--ancestor", "Revoke the owner delegation ancestry").option("--json", "Print versioned JSON").action(async (id, options) => {
34953
+ share.command("revoke <id>").description("Revoke addressed shares; report bearer retention honestly").option("--ancestor", "Revoke the owner delegation ancestry").option("--json", "Print versioned JSON").action(async (id, options, command) => {
34944
34954
  try {
34955
+ const json = jsonOutput(options, command);
34945
34956
  if (shareServices.records === void 0) throw new CLIError("AUTH_REQUIRED", "sender history storage is not configured", 3);
34946
34957
  const record = shareServices.getRecord ? await shareServices.getRecord(id) : await shareServices.records.get(id);
34947
34958
  if (record === void 0) throw new CLIError("NOT_FOUND", "share not found", 4);
@@ -34949,7 +34960,7 @@ function registerShareCommand(program) {
34949
34960
  if (result.state === "unsupported") {
34950
34961
  throw new CLIError("UNSUPPORTED_TARGET", result.reason, 2);
34951
34962
  }
34952
- if (options.json) writeJson2({ protocol: "tinycloud-share", version: 1, result });
34963
+ if (json) writeJson2({ protocol: "tinycloud-share", version: 1, result });
34953
34964
  else process.stdout.write(`${result.state}
34954
34965
  `);
34955
34966
  } catch (error) {