@letterstory/cli 0.61.0 → 0.61.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/lib/cli.mjs CHANGED
@@ -55,7 +55,7 @@ import {
55
55
  } from "./commands.mjs";
56
56
 
57
57
  // Keep in sync with cli/package.json.
58
- export const VERSION = "0.61.0";
58
+ export const VERSION = "0.61.2";
59
59
 
60
60
  // Flags that never take a value. Listing them explicitly means `deploy get --json <id>`
61
61
  // can't accidentally swallow the id as --json's value.
@@ -123,8 +123,9 @@ const BOOLEAN_FLAGS = new Set([
123
123
  "no-enrich",
124
124
  // `offerings set-collection <id> --none` (the org itself is the subject again).
125
125
  "none",
126
- // `prospects import|source --one-per-company`.
126
+ // `prospects import|source --one-per-company`, `prospects source --enrich`.
127
127
  "one-per-company",
128
+ "enrich",
128
129
  // `targets update <id> --clear-framing`.
129
130
  "clear-framing",
130
131
  ]);
@@ -807,10 +808,13 @@ Sequences (multi-step cold email sent from your mailers; approving or enrolling
807
808
  sequences get <sequence-id> Flow, enrollments, who replied at each step
808
809
  sequences create --name <n> (--flow '<json>'|--flow-file <path>) [--mailer <mailer-id>]...
809
810
  [--[no-]opt-out-footer] [--[no-]postal-address-footer] [--[no-]unsubscribe-links] [--[no-]detect-reply-opt-outs]
810
- New draft sequence (nothing sends yet; rails default on, opt-out line off)
811
+ [--send-window-start <HH:MM>] [--send-window-end <HH:MM>] [--send-window-timezone <IANA tz>]
812
+ New draft sequence (nothing sends yet; rails default on, opt-out line off;
813
+ sends 9:00-17:00 in each recipient's inferred timezone, else the sender's)
811
814
  sequences update <sequence-id> [--name <n>] [--flow '<json>'|--flow-file <path>]
812
815
  [--status draft|active|paused|archived] [--mailer <mailer-id>]...
813
816
  [--[no-]opt-out-footer] [--[no-]postal-address-footer] [--[no-]unsubscribe-links] [--[no-]detect-reply-opt-outs]
817
+ [--send-window-start <HH:MM>] [--send-window-end <HH:MM>] [--send-window-timezone <IANA tz>]
814
818
  sequences pause|resume <sequence-id> Stop / restart sending
815
819
  sequences enroll <sequence-id> (--list <list-id> | --email <addr>... | --recipients '<json>'|--recipients-file <path>)
816
820
  sequences stop <sequence-id> <enrollment-id> Stop one recipient
@@ -829,7 +833,8 @@ Prospects (who you write to):
829
833
  prospects create-list --name <n>
830
834
  prospects import --csv-file <path|-> [--list <list-id>|--list-name <n>] [--one-per-company]
831
835
  prospects source --description <who you want> [--list <list-id>|--list-name <n>] [--limit <1..100>]
832
- [--one-per-company] Fill a list from paid data providers (background)
836
+ [--one-per-company] [--enrich] Fill a list from paid data providers (background);
837
+ --enrich starts enrichment as soon as the pull lands
833
838
  prospects enrich [--list <list-id>] [--status <s>] [--q <search>]
834
839
  Funding + competitors for un-enriched rows
835
840
  prospects update <prospect-id> [--status new|contacted|replied|unsubscribed|archived] [--name <n>]
@@ -60,6 +60,31 @@ const SEQUENCE_RAIL_ARGS = {
60
60
  unsubscribe_links: { flag: "unsubscribe-links", type: "bool", negate: "no-unsubscribe-links" },
61
61
  detect_reply_opt_outs: { flag: "detect-reply-opt-outs", type: "bool", negate: "no-detect-reply-opt-outs" },
62
62
  };
63
+
64
+ // A send-window edge from --<flag> HH:MM (or a raw minute of day) → the
65
+ // schema's minute-of-day number.
66
+ function windowMinute(flag) {
67
+ return (flags) => {
68
+ const raw = flagStr(flags[flag]);
69
+ if (raw === undefined) return undefined;
70
+ if (/^\d+$/.test(raw)) return Number(raw);
71
+ const match = /^(\d{1,2}):(\d{2})$/.exec(raw);
72
+ if (!match || Number(match[1]) > 23 || Number(match[2]) > 59) {
73
+ throw new CliError(`--${flag} takes HH:MM or a minute of day 0–1439 (got ${raw})`);
74
+ }
75
+ return Number(match[1]) * 60 + Number(match[2]);
76
+ };
77
+ }
78
+
79
+ // The send window, shared by create and update: when emails may go out
80
+ // (default 9:00–17:00), in each recipient's inferred timezone, falling back to
81
+ // the sender's --send-window-timezone when the location is unknown. Equal
82
+ // start and end turns the window off.
83
+ const SEQUENCE_WINDOW_ARGS = {
84
+ send_window_start_minute: { value: windowMinute("send-window-start") },
85
+ send_window_end_minute: { value: windowMinute("send-window-end") },
86
+ send_window_timezone: "send-window-timezone",
87
+ };
63
88
  const PROSPECT_STATUSES = ["new", "contacted", "replied", "unsubscribed", "archived"];
64
89
  const mailerIds = {
65
90
  value: (flags) => {
@@ -101,6 +126,7 @@ export const ARGS = {
101
126
  },
102
127
  mailer_ids: mailerIds,
103
128
  ...SEQUENCE_RAIL_ARGS,
129
+ ...SEQUENCE_WINDOW_ARGS,
104
130
  },
105
131
  update_sequence: {
106
132
  sequence_id: { positional: 0, label: "sequence-id", required: true },
@@ -109,6 +135,7 @@ export const ARGS = {
109
135
  status: { flag: "status", enum: SEQUENCE_STATUSES },
110
136
  mailer_ids: mailerIds,
111
137
  ...SEQUENCE_RAIL_ARGS,
138
+ ...SEQUENCE_WINDOW_ARGS,
112
139
  },
113
140
  enroll_in_sequence: {
114
141
  sequence_id: { positional: 0, label: "sequence-id", required: true },
@@ -176,6 +203,7 @@ export const ARGS = {
176
203
  list_name: "list-name",
177
204
  limit: { flag: "limit", type: "num" },
178
205
  one_per_company: { flag: "one-per-company", type: "bool" },
206
+ enrich: { flag: "enrich", type: "bool" },
179
207
  },
180
208
  enrich_prospects: {
181
209
  list_id: "list",
@@ -260,8 +288,8 @@ export const ARGS = {
260
288
 
261
289
  // Flags the computed `value` sources read (refuseUnknownFlags can't see them).
262
290
  const VALUE_FLAGS = {
263
- create_sequence: ["flow", "flow-file", "mailer"],
264
- update_sequence: ["flow", "flow-file", "mailer"],
291
+ create_sequence: ["flow", "flow-file", "mailer", "send-window-start", "send-window-end"],
292
+ update_sequence: ["flow", "flow-file", "mailer", "send-window-start", "send-window-end"],
265
293
  enroll_in_sequence: ["recipients", "recipients-file", "email"],
266
294
  update_review_item: ["body", "file"],
267
295
  import_prospects_csv: ["csv", "csv-file"],
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@letterstory/cli",
3
- "version": "0.61.0",
3
+ "version": "0.61.2",
4
4
  "description": "Spin up and manage Letterstory phantom blogs from your terminal.",
5
5
  "type": "module",
6
6
  "license": "UNLICENSED",