@curviate/cli 0.18.0 → 0.19.0
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/CHANGELOG.md +41 -0
- package/dist/cli.js +9 -9
- package/dist/{company-BC72KZ5G.js → company-XEEBBCRZ.js} +391 -11
- package/dist/feed-KAUDRE5K.js +127 -0
- package/dist/group-LPVVJ2JX.js +236 -0
- package/dist/{inbox-DRJ6ENXC.js → inbox-BXCWHGWP.js} +61 -3
- package/dist/notification-RYFDHM3G.js +219 -0
- package/dist/{post-N3GQDIQJ.js → post-HK6HHIKV.js} +94 -1
- package/dist/{profile-XWSRUYRW.js → profile-PES67647.js} +108 -2
- package/dist/{search-ZQUKLQ6T.js → search-O2LACGHE.js} +203 -2
- package/package.json +4 -4
package/CHANGELOG.md
CHANGED
|
@@ -8,6 +8,47 @@ a new command or flag is a minor; a breaking command/flag/exit-code change is a
|
|
|
8
8
|
|
|
9
9
|
## [Unreleased]
|
|
10
10
|
|
|
11
|
+
## [0.19.0] - 2026-07-29
|
|
12
|
+
|
|
13
|
+
A minor release closing the remaining SDK-parity gap: 25 new commands across seven
|
|
14
|
+
existing command groups plus three brand-new command groups. No breaking changes,
|
|
15
|
+
built against `@curviate/sdk` 0.18.1 (unchanged; every new command was already
|
|
16
|
+
covered by the published SDK, so no SDK bump was required).
|
|
17
|
+
|
|
18
|
+
### Added
|
|
19
|
+
|
|
20
|
+
- **`inbox search`** — search chats via `messaging.searchChats`.
|
|
21
|
+
- **`search groups`, `search services`, `search service-parameters`** — new search
|
|
22
|
+
surfaces for groups, services, and service search parameters.
|
|
23
|
+
- **`post saved`, `post save`, `post unsave`** — list, save, and unsave posts.
|
|
24
|
+
- **`company managed`, `company followers`, `company chats`, `company chat`,
|
|
25
|
+
`company messages`, `company message`, `company search-chats`** — company-inbox
|
|
26
|
+
and managed-company read/write surface.
|
|
27
|
+
- **`profile subscription`, `profile analytics`, `profile visitors`, `profile ssi`**
|
|
28
|
+
— account-scoped profile insight subcommands (subscription status, post/profile
|
|
29
|
+
analytics, visitor list, Social Selling Index).
|
|
30
|
+
- **`group` command group** — new top-level group closing the LinkedIn Groups gap.
|
|
31
|
+
- **`feed`, `feed home`** — new command group to read the connected account's
|
|
32
|
+
LinkedIn home feed as agent-actionable posts.
|
|
33
|
+
- **`notification`, `notification list`, `notification delete`,
|
|
34
|
+
`notification show-less`** — new command group to read and act on LinkedIn
|
|
35
|
+
notification cards.
|
|
36
|
+
|
|
37
|
+
Parity with the SDK surface is now 145/0 (no known gaps).
|
|
38
|
+
|
|
39
|
+
## [0.18.1] - 2026-07-18
|
|
40
|
+
|
|
41
|
+
A patch aligning `company reply` with the company-inbox chat-id cutover. No breaking changes, built against `@curviate/sdk` 0.18.1.
|
|
42
|
+
|
|
43
|
+
### Fixed
|
|
44
|
+
|
|
45
|
+
- **`company reply <id> <chat_id> "<text>"`** now takes the normal `2-…` conversation
|
|
46
|
+
id that `company chats` returns; the endpoint resolves the page mailbox internally from
|
|
47
|
+
the company identifier, so the earlier `COMPANY_` chat-id requirement is gone. `--preview`
|
|
48
|
+
now always prints a "Will send as company page `<id>`" notice derived from the resolved
|
|
49
|
+
identifier (previously it went silent for a bare `2-…` id). Reply-only and admin-gated,
|
|
50
|
+
otherwise unchanged.
|
|
51
|
+
|
|
11
52
|
## [0.18.0] - 2026-07-17
|
|
12
53
|
|
|
13
54
|
A minor release adding the `company reply` command. No breaking changes, built against `@curviate/sdk` 0.18.0.
|
package/dist/cli.js
CHANGED
|
@@ -42,9 +42,6 @@ var REMOVED_COMMANDS = {
|
|
|
42
42
|
},
|
|
43
43
|
webhook: {
|
|
44
44
|
"state-diff": "`webhook state-diff` was removed with no replacement."
|
|
45
|
-
},
|
|
46
|
-
company: {
|
|
47
|
-
followers: "`company followers` was removed with no replacement."
|
|
48
45
|
}
|
|
49
46
|
};
|
|
50
47
|
function successorHint(group, token) {
|
|
@@ -255,20 +252,23 @@ var main = defineCommand({
|
|
|
255
252
|
// ---------------------------------------------------------------------------
|
|
256
253
|
// Noun groups — lazy-loaded on first invocation.
|
|
257
254
|
// ---------------------------------------------------------------------------
|
|
258
|
-
profile: () => import("./profile-
|
|
259
|
-
company: () => import("./company-
|
|
255
|
+
profile: () => import("./profile-PES67647.js").then((m) => m.profileCommand),
|
|
256
|
+
company: () => import("./company-XEEBBCRZ.js").then((m) => m.companyCommand),
|
|
260
257
|
job: () => import("./job-EIXBJXLW.js").then((m) => m.jobCommand),
|
|
261
258
|
connect: () => import("./connect-6PU7QCOL.js").then((m) => m.connectCommand),
|
|
262
|
-
search: () => import("./search-
|
|
263
|
-
inbox: () => import("./inbox-
|
|
259
|
+
search: () => import("./search-O2LACGHE.js").then((m) => m.searchCommand),
|
|
260
|
+
inbox: () => import("./inbox-BXCWHGWP.js").then((m) => m.inboxCommand),
|
|
264
261
|
inboxes: () => import("./inboxes-MTPWLP5F.js").then((m) => m.inboxesCommand),
|
|
265
262
|
message: () => import("./message-UWMRE2SJ.js").then((m) => m.messageCommand),
|
|
266
|
-
post: () => import("./post-
|
|
263
|
+
post: () => import("./post-HK6HHIKV.js").then((m) => m.postCommand),
|
|
267
264
|
comment: () => import("./comment-VT6PO4MN.js").then((m) => m.commentCommand),
|
|
268
265
|
account: () => import("./account-EGJJNBXW.js").then((m) => m.accountCommand),
|
|
269
266
|
webhook: () => import("./webhook-QFSZN3P2.js").then((m) => m.webhookCommand),
|
|
270
267
|
"sales-nav": () => import("./sales-nav-TMXWDKSE.js").then((m) => m.salesNavCommand),
|
|
271
|
-
recruiter: () => import("./recruiter-MVPSTH2V.js").then((m) => m.recruiterCommand)
|
|
268
|
+
recruiter: () => import("./recruiter-MVPSTH2V.js").then((m) => m.recruiterCommand),
|
|
269
|
+
group: () => import("./group-LPVVJ2JX.js").then((m) => m.groupCommand),
|
|
270
|
+
feed: () => import("./feed-KAUDRE5K.js").then((m) => m.feedCommand),
|
|
271
|
+
notification: () => import("./notification-RYFDHM3G.js").then((m) => m.notificationCommand)
|
|
272
272
|
},
|
|
273
273
|
async run() {
|
|
274
274
|
const { runMain } = await import("citty");
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import {
|
|
3
|
-
sentAsNotice
|
|
4
|
-
willSendAsNotice
|
|
3
|
+
sentAsNotice
|
|
5
4
|
} from "./chunk-KVV6LZ7E.js";
|
|
6
5
|
import {
|
|
7
6
|
resolveTextOrStdin
|
|
@@ -262,6 +261,186 @@ async function runCompanyFollowInvite(client, flags, out) {
|
|
|
262
261
|
await handleSdkError(err, outOpts, out);
|
|
263
262
|
}
|
|
264
263
|
}
|
|
264
|
+
async function runCompanyManaged(client, flags, out) {
|
|
265
|
+
rejectPreviewOnRead(flags.preview, out);
|
|
266
|
+
const accountId = requireAccount(flags.account, out);
|
|
267
|
+
const ns = client.account(accountId);
|
|
268
|
+
const outOpts = resolveOutputOpts(flags);
|
|
269
|
+
const params = {};
|
|
270
|
+
if (flags.limit) params["limit"] = parseInt(flags.limit, 10);
|
|
271
|
+
if (flags.cursor) params["cursor"] = flags.cursor;
|
|
272
|
+
try {
|
|
273
|
+
if (flags.all) {
|
|
274
|
+
const maxPages = flags["max-pages"] ? parseInt(flags["max-pages"], 10) : 100;
|
|
275
|
+
const fn = (p) => ns.companies.managed(p);
|
|
276
|
+
for await (const item of streamAll(fn, params, {
|
|
277
|
+
maxPages,
|
|
278
|
+
out,
|
|
279
|
+
pageDelayMs: pageDelayFromFlags(flags)
|
|
280
|
+
})) {
|
|
281
|
+
out.stdout.write(JSON.stringify(item) + "\n");
|
|
282
|
+
}
|
|
283
|
+
return;
|
|
284
|
+
}
|
|
285
|
+
const result = await ns.companies.managed(params);
|
|
286
|
+
renderSuccess(result, outOpts, out);
|
|
287
|
+
} catch (err) {
|
|
288
|
+
await handleSdkError(err, outOpts, out);
|
|
289
|
+
}
|
|
290
|
+
}
|
|
291
|
+
async function runCompanyFollowers(client, flags, out) {
|
|
292
|
+
rejectPreviewOnRead(flags.preview, out);
|
|
293
|
+
const accountId = requireAccount(flags.account, out);
|
|
294
|
+
const ns = client.account(accountId);
|
|
295
|
+
const outOpts = resolveOutputOpts(flags);
|
|
296
|
+
const params = {};
|
|
297
|
+
if (flags.limit) params["limit"] = parseInt(flags.limit, 10);
|
|
298
|
+
if (flags.cursor) params["cursor"] = flags.cursor;
|
|
299
|
+
try {
|
|
300
|
+
const identifier = await resolveCompanyId(ns, flags.id ?? "");
|
|
301
|
+
if (flags.all) {
|
|
302
|
+
const maxPages = flags["max-pages"] ? parseInt(flags["max-pages"], 10) : 100;
|
|
303
|
+
const fn = (p) => ns.companies.followers(identifier, p);
|
|
304
|
+
for await (const item of streamAll(fn, params, {
|
|
305
|
+
maxPages,
|
|
306
|
+
out,
|
|
307
|
+
pageDelayMs: pageDelayFromFlags(flags)
|
|
308
|
+
})) {
|
|
309
|
+
out.stdout.write(JSON.stringify(item) + "\n");
|
|
310
|
+
}
|
|
311
|
+
return;
|
|
312
|
+
}
|
|
313
|
+
const result = await ns.companies.followers(identifier, params);
|
|
314
|
+
renderSuccess(result, outOpts, out);
|
|
315
|
+
} catch (err) {
|
|
316
|
+
await handleSdkError(err, outOpts, out);
|
|
317
|
+
}
|
|
318
|
+
}
|
|
319
|
+
async function runCompanyChats(client, flags, out) {
|
|
320
|
+
rejectPreviewOnRead(flags.preview, out);
|
|
321
|
+
const accountId = requireAccount(flags.account, out);
|
|
322
|
+
const ns = client.account(accountId);
|
|
323
|
+
const outOpts = resolveOutputOpts(flags);
|
|
324
|
+
const params = {};
|
|
325
|
+
if (flags.limit) params["limit"] = parseInt(flags.limit, 10);
|
|
326
|
+
if (flags.cursor) params["cursor"] = flags.cursor;
|
|
327
|
+
try {
|
|
328
|
+
const identifier = await resolveCompanyId(ns, flags.id ?? "");
|
|
329
|
+
if (flags.all) {
|
|
330
|
+
const maxPages = flags["max-pages"] ? parseInt(flags["max-pages"], 10) : 100;
|
|
331
|
+
const fn = (p) => ns.companies.chats(identifier, p);
|
|
332
|
+
for await (const item of streamAll(fn, params, {
|
|
333
|
+
maxPages,
|
|
334
|
+
out,
|
|
335
|
+
pageDelayMs: pageDelayFromFlags(flags)
|
|
336
|
+
})) {
|
|
337
|
+
out.stdout.write(JSON.stringify(item) + "\n");
|
|
338
|
+
}
|
|
339
|
+
return;
|
|
340
|
+
}
|
|
341
|
+
const result = await ns.companies.chats(identifier, params);
|
|
342
|
+
renderSuccess(result, outOpts, out);
|
|
343
|
+
} catch (err) {
|
|
344
|
+
await handleSdkError(err, outOpts, out);
|
|
345
|
+
}
|
|
346
|
+
}
|
|
347
|
+
async function runCompanyChat(client, flags, out) {
|
|
348
|
+
rejectPreviewOnRead(flags.preview, out);
|
|
349
|
+
if (flags.all) {
|
|
350
|
+
out.stderr.write("error: --all is not supported on non-paginated commands.\n");
|
|
351
|
+
process.exit(2);
|
|
352
|
+
}
|
|
353
|
+
const accountId = requireAccount(flags.account, out);
|
|
354
|
+
const ns = client.account(accountId);
|
|
355
|
+
const outOpts = resolveOutputOpts(flags);
|
|
356
|
+
const chatId = flags.chatId ?? "";
|
|
357
|
+
try {
|
|
358
|
+
const identifier = await resolveCompanyId(ns, flags.id ?? "");
|
|
359
|
+
const result = await ns.companies.chat(identifier, chatId);
|
|
360
|
+
renderSuccess(result, outOpts, out);
|
|
361
|
+
} catch (err) {
|
|
362
|
+
await handleSdkError(err, outOpts, out);
|
|
363
|
+
}
|
|
364
|
+
}
|
|
365
|
+
async function runCompanyMessages(client, flags, out) {
|
|
366
|
+
rejectPreviewOnRead(flags.preview, out);
|
|
367
|
+
const accountId = requireAccount(flags.account, out);
|
|
368
|
+
const ns = client.account(accountId);
|
|
369
|
+
const outOpts = resolveOutputOpts(flags);
|
|
370
|
+
const chatId = flags.chatId ?? "";
|
|
371
|
+
const params = {};
|
|
372
|
+
if (flags.limit) params["limit"] = parseInt(flags.limit, 10);
|
|
373
|
+
if (flags.cursor) params["cursor"] = flags.cursor;
|
|
374
|
+
try {
|
|
375
|
+
const identifier = await resolveCompanyId(ns, flags.id ?? "");
|
|
376
|
+
if (flags.all) {
|
|
377
|
+
const maxPages = flags["max-pages"] ? parseInt(flags["max-pages"], 10) : 100;
|
|
378
|
+
const fn = (p) => ns.companies.messages(identifier, chatId, p);
|
|
379
|
+
for await (const item of streamAll(fn, params, {
|
|
380
|
+
maxPages,
|
|
381
|
+
out,
|
|
382
|
+
pageDelayMs: pageDelayFromFlags(flags)
|
|
383
|
+
})) {
|
|
384
|
+
out.stdout.write(JSON.stringify(item) + "\n");
|
|
385
|
+
}
|
|
386
|
+
return;
|
|
387
|
+
}
|
|
388
|
+
const result = await ns.companies.messages(identifier, chatId, params);
|
|
389
|
+
renderSuccess(result, outOpts, out);
|
|
390
|
+
} catch (err) {
|
|
391
|
+
await handleSdkError(err, outOpts, out);
|
|
392
|
+
}
|
|
393
|
+
}
|
|
394
|
+
async function runCompanyMessage(client, flags, out) {
|
|
395
|
+
rejectPreviewOnRead(flags.preview, out);
|
|
396
|
+
if (flags.all) {
|
|
397
|
+
out.stderr.write("error: --all is not supported on non-paginated commands.\n");
|
|
398
|
+
process.exit(2);
|
|
399
|
+
}
|
|
400
|
+
const accountId = requireAccount(flags.account, out);
|
|
401
|
+
const ns = client.account(accountId);
|
|
402
|
+
const outOpts = resolveOutputOpts(flags);
|
|
403
|
+
const chatId = flags.chatId ?? "";
|
|
404
|
+
const messageId = flags.messageId ?? "";
|
|
405
|
+
try {
|
|
406
|
+
const identifier = await resolveCompanyId(ns, flags.id ?? "");
|
|
407
|
+
const result = await ns.companies.message(identifier, chatId, messageId);
|
|
408
|
+
renderSuccess(result, outOpts, out);
|
|
409
|
+
} catch (err) {
|
|
410
|
+
await handleSdkError(err, outOpts, out);
|
|
411
|
+
}
|
|
412
|
+
}
|
|
413
|
+
async function runCompanySearchChats(client, flags, out) {
|
|
414
|
+
rejectPreviewOnRead(flags.preview, out);
|
|
415
|
+
const accountId = requireAccount(flags.account, out);
|
|
416
|
+
const ns = client.account(accountId);
|
|
417
|
+
const outOpts = resolveOutputOpts(flags);
|
|
418
|
+
const params = {};
|
|
419
|
+
if (flags.query) params["query"] = flags.query;
|
|
420
|
+
if (flags.topic) params["topic"] = flags.topic;
|
|
421
|
+
if (flags.unread !== void 0) params["unread"] = flags.unread;
|
|
422
|
+
if (flags.limit) params["limit"] = parseInt(flags.limit, 10);
|
|
423
|
+
if (flags.cursor) params["cursor"] = flags.cursor;
|
|
424
|
+
try {
|
|
425
|
+
const identifier = await resolveCompanyId(ns, flags.id ?? "");
|
|
426
|
+
if (flags.all) {
|
|
427
|
+
const maxPages = flags["max-pages"] ? parseInt(flags["max-pages"], 10) : 100;
|
|
428
|
+
const fn = (p) => ns.companies.searchChats(identifier, p);
|
|
429
|
+
for await (const item of streamAll(fn, params, {
|
|
430
|
+
maxPages,
|
|
431
|
+
out,
|
|
432
|
+
pageDelayMs: pageDelayFromFlags(flags)
|
|
433
|
+
})) {
|
|
434
|
+
out.stdout.write(JSON.stringify(item) + "\n");
|
|
435
|
+
}
|
|
436
|
+
return;
|
|
437
|
+
}
|
|
438
|
+
const result = await ns.companies.searchChats(identifier, params);
|
|
439
|
+
renderSuccess(result, outOpts, out);
|
|
440
|
+
} catch (err) {
|
|
441
|
+
await handleSdkError(err, outOpts, out);
|
|
442
|
+
}
|
|
443
|
+
}
|
|
265
444
|
async function runCompanyReply(client, flags, out, _readStdin) {
|
|
266
445
|
const accountId = requireAccount(flags.account, out);
|
|
267
446
|
const ns = client.account(accountId);
|
|
@@ -295,8 +474,8 @@ async function runCompanyReply(client, flags, out, _readStdin) {
|
|
|
295
474
|
}))
|
|
296
475
|
});
|
|
297
476
|
out.stdout.write(JSON.stringify(preview) + "\n");
|
|
298
|
-
|
|
299
|
-
|
|
477
|
+
out.stderr.write(`Will send as company page ${identifier}
|
|
478
|
+
`);
|
|
300
479
|
return;
|
|
301
480
|
}
|
|
302
481
|
const attachmentPayloads = attachBuffers.map((buf, i) => toAttachmentPayload(attachPaths[i], buf));
|
|
@@ -316,7 +495,7 @@ var companyEmployeesCommand = defineCommand({
|
|
|
316
495
|
meta: { name: "employees", description: "List people who currently work at the company." },
|
|
317
496
|
args: {
|
|
318
497
|
...GLOBAL_FLAGS,
|
|
319
|
-
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id)
|
|
498
|
+
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id), a slug/URL is resolved to the numeric id first." },
|
|
320
499
|
keywords: { type: "string", description: "Free-text keyword filter across employee profile fields." },
|
|
321
500
|
location: { type: "string", description: "Opaque location id from `search parameters --type LOCATION`." }
|
|
322
501
|
},
|
|
@@ -342,7 +521,7 @@ var companyPostsCommand = defineCommand({
|
|
|
342
521
|
meta: { name: "posts", description: "List the company's posts." },
|
|
343
522
|
args: {
|
|
344
523
|
...GLOBAL_FLAGS,
|
|
345
|
-
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id)
|
|
524
|
+
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id), a slug/URL is resolved to the numeric id first." }
|
|
346
525
|
},
|
|
347
526
|
async run({ args }) {
|
|
348
527
|
const flags = args;
|
|
@@ -366,7 +545,7 @@ var companyJobsCommand = defineCommand({
|
|
|
366
545
|
meta: { name: "jobs", description: "List the company's open job postings." },
|
|
367
546
|
args: {
|
|
368
547
|
...GLOBAL_FLAGS,
|
|
369
|
-
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id)
|
|
548
|
+
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id), a slug/URL is resolved to the numeric id first." },
|
|
370
549
|
keywords: { type: "string", description: "Free-text keyword filter across job postings." }
|
|
371
550
|
},
|
|
372
551
|
async run({ args }) {
|
|
@@ -445,17 +624,204 @@ var companyFollowInviteCommand = defineCommand({
|
|
|
445
624
|
await runCompanyFollowInvite(client, { ...flags, account: flags.account ?? cfg.account }, out);
|
|
446
625
|
}
|
|
447
626
|
});
|
|
627
|
+
var companyManagedCommand = defineCommand({
|
|
628
|
+
meta: { name: "managed", description: "List the company pages the connected account administers. An empty result is valid, the account administers no pages." },
|
|
629
|
+
args: { ...GLOBAL_FLAGS },
|
|
630
|
+
async run({ args }) {
|
|
631
|
+
const flags = args;
|
|
632
|
+
const cfg = await resolveEffectiveConfig({
|
|
633
|
+
apiKey: flags["api-key"],
|
|
634
|
+
baseUrl: flags["base-url"],
|
|
635
|
+
timeout: flags.timeout,
|
|
636
|
+
account: flags.account,
|
|
637
|
+
profile: flags.profile
|
|
638
|
+
});
|
|
639
|
+
if (!cfg.apiKey) {
|
|
640
|
+
process.stderr.write("error: no API key \u2014 run `curviate login` or pass --api-key.\n");
|
|
641
|
+
process.exit(3);
|
|
642
|
+
}
|
|
643
|
+
const client = createClient({ apiKey: cfg.apiKey, baseUrl: cfg.baseUrl, timeout: cfg.timeout });
|
|
644
|
+
const out = buildOutputStreams();
|
|
645
|
+
await runCompanyManaged(client, { ...flags, account: flags.account ?? cfg.account }, out);
|
|
646
|
+
}
|
|
647
|
+
});
|
|
648
|
+
var companyFollowersCommand = defineCommand({
|
|
649
|
+
meta: { name: "followers", description: "List a company page's followers, newest first. Admin-gated: the account must administer the page (see `company managed`)." },
|
|
650
|
+
args: {
|
|
651
|
+
...GLOBAL_FLAGS,
|
|
652
|
+
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id), a slug/URL is resolved to the numeric id first." }
|
|
653
|
+
},
|
|
654
|
+
async run({ args }) {
|
|
655
|
+
const flags = args;
|
|
656
|
+
const cfg = await resolveEffectiveConfig({
|
|
657
|
+
apiKey: flags["api-key"],
|
|
658
|
+
baseUrl: flags["base-url"],
|
|
659
|
+
timeout: flags.timeout,
|
|
660
|
+
account: flags.account,
|
|
661
|
+
profile: flags.profile
|
|
662
|
+
});
|
|
663
|
+
if (!cfg.apiKey) {
|
|
664
|
+
process.stderr.write("error: no API key \u2014 run `curviate login` or pass --api-key.\n");
|
|
665
|
+
process.exit(3);
|
|
666
|
+
}
|
|
667
|
+
const client = createClient({ apiKey: cfg.apiKey, baseUrl: cfg.baseUrl, timeout: cfg.timeout });
|
|
668
|
+
const out = buildOutputStreams();
|
|
669
|
+
await runCompanyFollowers(client, { ...flags, account: flags.account ?? cfg.account }, out);
|
|
670
|
+
}
|
|
671
|
+
});
|
|
672
|
+
var companyChatsCommand = defineCommand({
|
|
673
|
+
meta: {
|
|
674
|
+
name: "chats",
|
|
675
|
+
description: "List the conversations in a company page's admin message inbox, newest-activity-first. Admin-gated. Beta."
|
|
676
|
+
},
|
|
677
|
+
args: {
|
|
678
|
+
...GLOBAL_FLAGS,
|
|
679
|
+
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id), a slug/URL is resolved to the numeric id first." }
|
|
680
|
+
},
|
|
681
|
+
async run({ args }) {
|
|
682
|
+
const flags = args;
|
|
683
|
+
const cfg = await resolveEffectiveConfig({
|
|
684
|
+
apiKey: flags["api-key"],
|
|
685
|
+
baseUrl: flags["base-url"],
|
|
686
|
+
timeout: flags.timeout,
|
|
687
|
+
account: flags.account,
|
|
688
|
+
profile: flags.profile
|
|
689
|
+
});
|
|
690
|
+
if (!cfg.apiKey) {
|
|
691
|
+
process.stderr.write("error: no API key \u2014 run `curviate login` or pass --api-key.\n");
|
|
692
|
+
process.exit(3);
|
|
693
|
+
}
|
|
694
|
+
const client = createClient({ apiKey: cfg.apiKey, baseUrl: cfg.baseUrl, timeout: cfg.timeout });
|
|
695
|
+
const out = buildOutputStreams();
|
|
696
|
+
await runCompanyChats(client, { ...flags, account: flags.account ?? cfg.account }, out);
|
|
697
|
+
}
|
|
698
|
+
});
|
|
699
|
+
var companyChatCommand = defineCommand({
|
|
700
|
+
meta: {
|
|
701
|
+
name: "chat",
|
|
702
|
+
description: "Retrieve one conversation from a company page's admin inbox. Admin-gated. Beta."
|
|
703
|
+
},
|
|
704
|
+
args: {
|
|
705
|
+
...GLOBAL_FLAGS,
|
|
706
|
+
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id), a slug/URL is resolved to the numeric id first." },
|
|
707
|
+
chatId: { type: "positional", description: "The 2-\u2026 chat id from `company chats`, passed through verbatim." }
|
|
708
|
+
},
|
|
709
|
+
async run({ args }) {
|
|
710
|
+
const flags = args;
|
|
711
|
+
const cfg = await resolveEffectiveConfig({
|
|
712
|
+
apiKey: flags["api-key"],
|
|
713
|
+
baseUrl: flags["base-url"],
|
|
714
|
+
timeout: flags.timeout,
|
|
715
|
+
account: flags.account,
|
|
716
|
+
profile: flags.profile
|
|
717
|
+
});
|
|
718
|
+
if (!cfg.apiKey) {
|
|
719
|
+
process.stderr.write("error: no API key \u2014 run `curviate login` or pass --api-key.\n");
|
|
720
|
+
process.exit(3);
|
|
721
|
+
}
|
|
722
|
+
const client = createClient({ apiKey: cfg.apiKey, baseUrl: cfg.baseUrl, timeout: cfg.timeout });
|
|
723
|
+
const out = buildOutputStreams();
|
|
724
|
+
await runCompanyChat(client, { ...flags, account: flags.account ?? cfg.account }, out);
|
|
725
|
+
}
|
|
726
|
+
});
|
|
727
|
+
var companyMessagesCommand = defineCommand({
|
|
728
|
+
meta: {
|
|
729
|
+
name: "messages",
|
|
730
|
+
description: "List a company-inbox conversation's messages, newest first. Admin-gated."
|
|
731
|
+
},
|
|
732
|
+
args: {
|
|
733
|
+
...GLOBAL_FLAGS,
|
|
734
|
+
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id), a slug/URL is resolved to the numeric id first." },
|
|
735
|
+
chatId: { type: "positional", description: "The 2-\u2026 chat id from `company chats`, passed through verbatim." }
|
|
736
|
+
},
|
|
737
|
+
async run({ args }) {
|
|
738
|
+
const flags = args;
|
|
739
|
+
const cfg = await resolveEffectiveConfig({
|
|
740
|
+
apiKey: flags["api-key"],
|
|
741
|
+
baseUrl: flags["base-url"],
|
|
742
|
+
timeout: flags.timeout,
|
|
743
|
+
account: flags.account,
|
|
744
|
+
profile: flags.profile
|
|
745
|
+
});
|
|
746
|
+
if (!cfg.apiKey) {
|
|
747
|
+
process.stderr.write("error: no API key \u2014 run `curviate login` or pass --api-key.\n");
|
|
748
|
+
process.exit(3);
|
|
749
|
+
}
|
|
750
|
+
const client = createClient({ apiKey: cfg.apiKey, baseUrl: cfg.baseUrl, timeout: cfg.timeout });
|
|
751
|
+
const out = buildOutputStreams();
|
|
752
|
+
await runCompanyMessages(client, { ...flags, account: flags.account ?? cfg.account }, out);
|
|
753
|
+
}
|
|
754
|
+
});
|
|
755
|
+
var companyMessageCommand = defineCommand({
|
|
756
|
+
meta: {
|
|
757
|
+
name: "message",
|
|
758
|
+
description: "Retrieve one message from a company-inbox conversation. Admin-gated. See also: `company reply` (send)."
|
|
759
|
+
},
|
|
760
|
+
args: {
|
|
761
|
+
...GLOBAL_FLAGS,
|
|
762
|
+
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id), a slug/URL is resolved to the numeric id first." },
|
|
763
|
+
chatId: { type: "positional", description: "The 2-\u2026 chat id from `company chats`, passed through verbatim." },
|
|
764
|
+
messageId: { type: "positional", description: "The message id from `company messages`, passed through verbatim." }
|
|
765
|
+
},
|
|
766
|
+
async run({ args }) {
|
|
767
|
+
const flags = args;
|
|
768
|
+
const cfg = await resolveEffectiveConfig({
|
|
769
|
+
apiKey: flags["api-key"],
|
|
770
|
+
baseUrl: flags["base-url"],
|
|
771
|
+
timeout: flags.timeout,
|
|
772
|
+
account: flags.account,
|
|
773
|
+
profile: flags.profile
|
|
774
|
+
});
|
|
775
|
+
if (!cfg.apiKey) {
|
|
776
|
+
process.stderr.write("error: no API key \u2014 run `curviate login` or pass --api-key.\n");
|
|
777
|
+
process.exit(3);
|
|
778
|
+
}
|
|
779
|
+
const client = createClient({ apiKey: cfg.apiKey, baseUrl: cfg.baseUrl, timeout: cfg.timeout });
|
|
780
|
+
const out = buildOutputStreams();
|
|
781
|
+
await runCompanyMessage(client, { ...flags, account: flags.account ?? cfg.account }, out);
|
|
782
|
+
}
|
|
783
|
+
});
|
|
784
|
+
var companySearchChatsCommand = defineCommand({
|
|
785
|
+
meta: {
|
|
786
|
+
name: "search-chats",
|
|
787
|
+
description: "Search or filter a company page's admin inbox. Exactly one mode per call: free-text <query>, --topic, or --unread; mutually exclusive, enforced server-side. Admin-gated."
|
|
788
|
+
},
|
|
789
|
+
args: {
|
|
790
|
+
...GLOBAL_FLAGS,
|
|
791
|
+
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id), a slug/URL is resolved to the numeric id first." },
|
|
792
|
+
query: { type: "positional", required: false, description: "Free-text term, matches participant names and message content." },
|
|
793
|
+
topic: { type: "string", description: "Filter mode, one inbox topic card: 1-5 or its name (Service request, Request a demo, Support, Careers, Other)." },
|
|
794
|
+
unread: { type: "boolean", description: "Filter mode, unread conversations only." }
|
|
795
|
+
},
|
|
796
|
+
async run({ args }) {
|
|
797
|
+
const flags = args;
|
|
798
|
+
const cfg = await resolveEffectiveConfig({
|
|
799
|
+
apiKey: flags["api-key"],
|
|
800
|
+
baseUrl: flags["base-url"],
|
|
801
|
+
timeout: flags.timeout,
|
|
802
|
+
account: flags.account,
|
|
803
|
+
profile: flags.profile
|
|
804
|
+
});
|
|
805
|
+
if (!cfg.apiKey) {
|
|
806
|
+
process.stderr.write("error: no API key \u2014 run `curviate login` or pass --api-key.\n");
|
|
807
|
+
process.exit(3);
|
|
808
|
+
}
|
|
809
|
+
const client = createClient({ apiKey: cfg.apiKey, baseUrl: cfg.baseUrl, timeout: cfg.timeout });
|
|
810
|
+
const out = buildOutputStreams();
|
|
811
|
+
await runCompanySearchChats(client, { ...flags, account: flags.account ?? cfg.account }, out);
|
|
812
|
+
}
|
|
813
|
+
});
|
|
448
814
|
var companyReplyCommand = defineCommand({
|
|
449
815
|
meta: {
|
|
450
816
|
name: "reply",
|
|
451
|
-
description: "Reply to a company-inbox conversation, as the page (write, admin-gated: the account must administer the page).
|
|
817
|
+
description: "Reply to a company-inbox conversation, as the page (write, admin-gated: the account must administer the page). Takes the normal 2-\u2026 chat id from `company chats`; the endpoint resolves the page mailbox internally from the company id. Reply-only, this cannot start a new conversation on the page's behalf. See also: `company chats` (the read that returns the chat id) and `message send` (the personal equivalent)."
|
|
452
818
|
},
|
|
453
819
|
args: {
|
|
454
820
|
...WRITE_FLAGS,
|
|
455
821
|
id: { type: "positional", description: "Company identifier (URL, slug, or numeric id), resolved to the numeric id first, including under --preview." },
|
|
456
822
|
chatId: {
|
|
457
823
|
type: "positional",
|
|
458
|
-
description: "
|
|
824
|
+
description: "The 2-\u2026 chat id from `company chats`, passed through verbatim (no client-side check)."
|
|
459
825
|
},
|
|
460
826
|
text: { type: "positional", description: "Reply text. Pass - to read from stdin (e.g. via heredoc or pipe)." },
|
|
461
827
|
attach: { type: "string", description: "File to attach (repeatable)." }
|
|
@@ -491,7 +857,14 @@ var companyCommand = defineCommand({
|
|
|
491
857
|
jobs: companyJobsCommand,
|
|
492
858
|
"invitable-followers": companyInvitableFollowersCommand,
|
|
493
859
|
"follow-invite": companyFollowInviteCommand,
|
|
494
|
-
reply: companyReplyCommand
|
|
860
|
+
reply: companyReplyCommand,
|
|
861
|
+
managed: companyManagedCommand,
|
|
862
|
+
followers: companyFollowersCommand,
|
|
863
|
+
chats: companyChatsCommand,
|
|
864
|
+
chat: companyChatCommand,
|
|
865
|
+
messages: companyMessagesCommand,
|
|
866
|
+
message: companyMessageCommand,
|
|
867
|
+
"search-chats": companySearchChatsCommand
|
|
495
868
|
},
|
|
496
869
|
async run({ args }) {
|
|
497
870
|
const flags = args;
|
|
@@ -513,11 +886,18 @@ var companyCommand = defineCommand({
|
|
|
513
886
|
});
|
|
514
887
|
export {
|
|
515
888
|
companyCommand,
|
|
889
|
+
runCompanyChat,
|
|
890
|
+
runCompanyChats,
|
|
516
891
|
runCompanyEmployees,
|
|
517
892
|
runCompanyFollowInvite,
|
|
893
|
+
runCompanyFollowers,
|
|
518
894
|
runCompanyGet,
|
|
519
895
|
runCompanyInvitableFollowers,
|
|
520
896
|
runCompanyJobs,
|
|
897
|
+
runCompanyManaged,
|
|
898
|
+
runCompanyMessage,
|
|
899
|
+
runCompanyMessages,
|
|
521
900
|
runCompanyPosts,
|
|
522
|
-
runCompanyReply
|
|
901
|
+
runCompanyReply,
|
|
902
|
+
runCompanySearchChats
|
|
523
903
|
};
|
|
@@ -0,0 +1,127 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import {
|
|
3
|
+
pageDelayFromFlags,
|
|
4
|
+
streamAll
|
|
5
|
+
} from "./chunk-EEMJDJ4W.js";
|
|
6
|
+
import {
|
|
7
|
+
createClient,
|
|
8
|
+
renderError,
|
|
9
|
+
renderSuccess,
|
|
10
|
+
renderUnexpectedError,
|
|
11
|
+
resolveEffectiveConfig
|
|
12
|
+
} from "./chunk-M33MI53G.js";
|
|
13
|
+
import {
|
|
14
|
+
GLOBAL_FLAGS
|
|
15
|
+
} from "./chunk-TMU3CSPR.js";
|
|
16
|
+
|
|
17
|
+
// src/commands/feed.ts
|
|
18
|
+
import { defineCommand } from "citty";
|
|
19
|
+
function buildOutputStreams() {
|
|
20
|
+
return {
|
|
21
|
+
stdout: { write: (s) => process.stdout.write(s) },
|
|
22
|
+
stderr: { write: (s) => process.stderr.write(s) }
|
|
23
|
+
};
|
|
24
|
+
}
|
|
25
|
+
function requireAccount(account, out) {
|
|
26
|
+
if (!account) {
|
|
27
|
+
out.stderr.write("error: --account is required for this command. Set it via --account, CURVIATE_ACCOUNT, or `curviate config set-account`.\n");
|
|
28
|
+
process.exit(2);
|
|
29
|
+
}
|
|
30
|
+
return account;
|
|
31
|
+
}
|
|
32
|
+
function rejectPreviewOnRead(preview, out) {
|
|
33
|
+
if (preview) {
|
|
34
|
+
out.stderr.write("error: --preview is only valid on write commands (mutations). Reads just run.\n");
|
|
35
|
+
process.exit(2);
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
function resolveOutputOpts(flags) {
|
|
39
|
+
return {
|
|
40
|
+
json: (flags.json ?? false) || !process.stdout.isTTY,
|
|
41
|
+
isTTY: process.stdout.isTTY ?? false,
|
|
42
|
+
fields: flags.fields,
|
|
43
|
+
verbose: flags.verbose ?? false
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
async function handleSdkError(err, outOpts, out) {
|
|
47
|
+
const { CurviateError } = await import("@curviate/sdk");
|
|
48
|
+
if (err instanceof CurviateError) {
|
|
49
|
+
const { getExitCode } = await import("./exit-codes-63JE5GM5.js");
|
|
50
|
+
renderError(err, outOpts, out);
|
|
51
|
+
process.exit(getExitCode(err.code));
|
|
52
|
+
}
|
|
53
|
+
renderUnexpectedError(err, out);
|
|
54
|
+
process.exit(1);
|
|
55
|
+
}
|
|
56
|
+
async function runFeedHome(client, flags, out) {
|
|
57
|
+
rejectPreviewOnRead(flags.preview, out);
|
|
58
|
+
const accountId = requireAccount(flags.account, out);
|
|
59
|
+
const ns = client.account(accountId);
|
|
60
|
+
const outOpts = resolveOutputOpts(flags);
|
|
61
|
+
const all = flags.all ?? false;
|
|
62
|
+
const maxPages = flags["max-pages"] ? parseInt(flags["max-pages"], 10) : 100;
|
|
63
|
+
const params = {};
|
|
64
|
+
if (flags.sort) params["sort"] = flags.sort;
|
|
65
|
+
if (flags.limit) params["limit"] = parseInt(flags.limit, 10);
|
|
66
|
+
if (flags.cursor) params["cursor"] = flags.cursor;
|
|
67
|
+
try {
|
|
68
|
+
if (all) {
|
|
69
|
+
const fn = (p) => ns.feed.home(p);
|
|
70
|
+
for await (const item of streamAll(fn, params, {
|
|
71
|
+
maxPages,
|
|
72
|
+
out,
|
|
73
|
+
pageDelayMs: pageDelayFromFlags(flags)
|
|
74
|
+
})) {
|
|
75
|
+
out.stdout.write(JSON.stringify(item) + "\n");
|
|
76
|
+
}
|
|
77
|
+
} else {
|
|
78
|
+
const result = await ns.feed.home(params);
|
|
79
|
+
renderSuccess(result, outOpts, out);
|
|
80
|
+
}
|
|
81
|
+
} catch (err) {
|
|
82
|
+
await handleSdkError(err, outOpts, out);
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
var FEED_ARGS = {
|
|
86
|
+
...GLOBAL_FLAGS,
|
|
87
|
+
sort: {
|
|
88
|
+
type: "string",
|
|
89
|
+
description: "Sort order: recent (default, reverse-chronological, always available) or relevant (LinkedIn's ranked 'top' feed, shared throttled budget). Ignored when --cursor is supplied."
|
|
90
|
+
}
|
|
91
|
+
};
|
|
92
|
+
var feedHomeCommand = defineCommand({
|
|
93
|
+
meta: { name: "home", description: "Read the connected account's LinkedIn home feed as agent-actionable posts." },
|
|
94
|
+
args: FEED_ARGS,
|
|
95
|
+
async run({ args }) {
|
|
96
|
+
const flags = args;
|
|
97
|
+
const cfg = await resolveEffectiveConfig({
|
|
98
|
+
apiKey: flags["api-key"],
|
|
99
|
+
baseUrl: flags["base-url"],
|
|
100
|
+
timeout: flags.timeout,
|
|
101
|
+
account: flags.account,
|
|
102
|
+
profile: flags.profile
|
|
103
|
+
});
|
|
104
|
+
if (!cfg.apiKey) {
|
|
105
|
+
process.stderr.write("error: no API key \u2014 run `curviate login` or pass --api-key.\n");
|
|
106
|
+
process.exit(3);
|
|
107
|
+
}
|
|
108
|
+
const client = createClient({ apiKey: cfg.apiKey, baseUrl: cfg.baseUrl, timeout: cfg.timeout });
|
|
109
|
+
const out = buildOutputStreams();
|
|
110
|
+
await runFeedHome(client, { ...flags, account: flags.account ?? cfg.account }, out);
|
|
111
|
+
}
|
|
112
|
+
});
|
|
113
|
+
var feedCommand = defineCommand({
|
|
114
|
+
meta: { name: "feed", description: "Read the connected account's LinkedIn home feed as agent-actionable posts." },
|
|
115
|
+
subCommands: {
|
|
116
|
+
home: feedHomeCommand
|
|
117
|
+
},
|
|
118
|
+
async run() {
|
|
119
|
+
process.stderr.write(
|
|
120
|
+
"Usage: curviate feed <subcommand>\n home [--sort recent|relevant] [--limit] [--cursor] [--all]\n"
|
|
121
|
+
);
|
|
122
|
+
}
|
|
123
|
+
});
|
|
124
|
+
export {
|
|
125
|
+
feedCommand,
|
|
126
|
+
runFeedHome
|
|
127
|
+
};
|