lumnisai 0.5.22 → 0.5.24
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/dist/index.cjs +211 -0
- package/dist/index.d.cts +647 -10
- package/dist/index.d.mts +647 -10
- package/dist/index.d.ts +647 -10
- package/dist/index.mjs +211 -0
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -1083,6 +1083,31 @@ class EmailResource {
|
|
|
1083
1083
|
{ params: { user_id: userId } }
|
|
1084
1084
|
);
|
|
1085
1085
|
}
|
|
1086
|
+
// ==================== BYO Inboxes ====================
|
|
1087
|
+
/**
|
|
1088
|
+
* Connect a customer's own email inbox (Gmail/Outlook/IMAP) via Unipile.
|
|
1089
|
+
*
|
|
1090
|
+
* One call = one inbox. Returns a hosted-auth redirect URL; the user authes
|
|
1091
|
+
* there and the connect webhook creates the `ready` mailbox. Call once per
|
|
1092
|
+
* inbox to add multiple mailboxes.
|
|
1093
|
+
*/
|
|
1094
|
+
async connectInbox(request) {
|
|
1095
|
+
return this.http.post("/email/inboxes/connect", request);
|
|
1096
|
+
}
|
|
1097
|
+
/**
|
|
1098
|
+
* Update a single mailbox's send settings (per-mailbox daily cap, pause).
|
|
1099
|
+
*
|
|
1100
|
+
* PATCH semantics — only provided fields change. The per-mailbox cap is the
|
|
1101
|
+
* primary lever for BYO inboxes, which skip the InboxKit warmup ramp.
|
|
1102
|
+
* Requires admin role on the org.
|
|
1103
|
+
*/
|
|
1104
|
+
async updateMailbox(orgId, mailboxId, userId, update) {
|
|
1105
|
+
return this.http.patch(
|
|
1106
|
+
`/email/organizations/${encodeURIComponent(orgId)}/mailboxes/${encodeURIComponent(mailboxId)}`,
|
|
1107
|
+
update,
|
|
1108
|
+
{ params: { user_id: userId } }
|
|
1109
|
+
);
|
|
1110
|
+
}
|
|
1086
1111
|
// ==================== Teardown ====================
|
|
1087
1112
|
/**
|
|
1088
1113
|
* Teardown an email organization's infrastructure.
|
|
@@ -2845,6 +2870,71 @@ class ModelPreferencesResource {
|
|
|
2845
2870
|
}
|
|
2846
2871
|
}
|
|
2847
2872
|
|
|
2873
|
+
class OutreachResource {
|
|
2874
|
+
constructor(http) {
|
|
2875
|
+
this.http = http;
|
|
2876
|
+
}
|
|
2877
|
+
/**
|
|
2878
|
+
* List people at a funnel stage (connected/messaged/replied/meeting_booked),
|
|
2879
|
+
* or `stage='all'` for one row per person at their furthest stage.
|
|
2880
|
+
*
|
|
2881
|
+
* Pass `stats: true` to also get the per-channel funnel counts + conversion
|
|
2882
|
+
* ratios for the same scope (`userId`/`source`/`campaignId`) alongside the
|
|
2883
|
+
* people list. Pass `campaignId` to restrict to specific campaigns (this
|
|
2884
|
+
* excludes sequences).
|
|
2885
|
+
*
|
|
2886
|
+
* @example
|
|
2887
|
+
* ```typescript
|
|
2888
|
+
* const result = await client.outreach.listConnections({
|
|
2889
|
+
* userId: 'user@example.com',
|
|
2890
|
+
* stage: 'replied',
|
|
2891
|
+
* stats: true,
|
|
2892
|
+
* })
|
|
2893
|
+
* console.log(result.total, result.stats?.byChannel.linkedin.ratios.replyRate)
|
|
2894
|
+
* ```
|
|
2895
|
+
*/
|
|
2896
|
+
async listConnections(params) {
|
|
2897
|
+
const query = new URLSearchParams();
|
|
2898
|
+
query.append("user_id", params.userId);
|
|
2899
|
+
if (params.stage !== void 0)
|
|
2900
|
+
query.append("stage", params.stage);
|
|
2901
|
+
if (params.channel !== void 0)
|
|
2902
|
+
query.append("channel", params.channel);
|
|
2903
|
+
if (params.source !== void 0)
|
|
2904
|
+
query.append("source", params.source);
|
|
2905
|
+
if (params.campaignId)
|
|
2906
|
+
params.campaignId.forEach((id) => query.append("campaign_id", id));
|
|
2907
|
+
if (params.since !== void 0)
|
|
2908
|
+
query.append("since", params.since);
|
|
2909
|
+
if (params.stats !== void 0)
|
|
2910
|
+
query.append("stats", String(params.stats));
|
|
2911
|
+
if (params.limit !== void 0)
|
|
2912
|
+
query.append("limit", String(params.limit));
|
|
2913
|
+
if (params.offset !== void 0)
|
|
2914
|
+
query.append("offset", String(params.offset));
|
|
2915
|
+
return this.http.get(`/outreach?${query.toString()}`);
|
|
2916
|
+
}
|
|
2917
|
+
/**
|
|
2918
|
+
* Alias for `stage='connected'` — people who accepted a Lumnis-sent
|
|
2919
|
+
* connection request.
|
|
2920
|
+
*/
|
|
2921
|
+
async listAcceptedConnections(params) {
|
|
2922
|
+
const query = new URLSearchParams();
|
|
2923
|
+
query.append("user_id", params.userId);
|
|
2924
|
+
if (params.source !== void 0)
|
|
2925
|
+
query.append("source", params.source);
|
|
2926
|
+
if (params.campaignId)
|
|
2927
|
+
params.campaignId.forEach((id) => query.append("campaign_id", id));
|
|
2928
|
+
if (params.since !== void 0)
|
|
2929
|
+
query.append("since", params.since);
|
|
2930
|
+
if (params.limit !== void 0)
|
|
2931
|
+
query.append("limit", String(params.limit));
|
|
2932
|
+
if (params.offset !== void 0)
|
|
2933
|
+
query.append("offset", String(params.offset));
|
|
2934
|
+
return this.http.get(`/outreach/accepted?${query.toString()}`);
|
|
2935
|
+
}
|
|
2936
|
+
}
|
|
2937
|
+
|
|
2848
2938
|
var PeopleDataSource = /* @__PURE__ */ ((PeopleDataSource2) => {
|
|
2849
2939
|
PeopleDataSource2["PDL"] = "PDL";
|
|
2850
2940
|
PeopleDataSource2["CORESIGNAL"] = "CORESIGNAL";
|
|
@@ -3128,6 +3218,59 @@ class ResponsesResource {
|
|
|
3128
3218
|
throw new ValidationError("maxCommentsPerPost must be between 1 and 100");
|
|
3129
3219
|
}
|
|
3130
3220
|
}
|
|
3221
|
+
_validateCompetitorRepEngagementParams(params) {
|
|
3222
|
+
const company = this._getParamValue(params, "company", "company");
|
|
3223
|
+
const competitors = this._getParamValue(params, "competitors", "competitors");
|
|
3224
|
+
const engagementTypes = this._getParamValue(
|
|
3225
|
+
params,
|
|
3226
|
+
"engagementTypes",
|
|
3227
|
+
"engagement_types"
|
|
3228
|
+
);
|
|
3229
|
+
const hasCompany = typeof company === "string" && company.trim().length > 0;
|
|
3230
|
+
const hasCompetitors = Array.isArray(competitors) && competitors.length > 0;
|
|
3231
|
+
if (hasCompany === hasCompetitors) {
|
|
3232
|
+
throw new ValidationError(
|
|
3233
|
+
"Provide exactly one of `company` or `competitors` for competitor_rep_engagement."
|
|
3234
|
+
);
|
|
3235
|
+
}
|
|
3236
|
+
if (engagementTypes !== void 0) {
|
|
3237
|
+
if (!Array.isArray(engagementTypes) || engagementTypes.length === 0) {
|
|
3238
|
+
throw new ValidationError("engagementTypes must contain at least one value");
|
|
3239
|
+
}
|
|
3240
|
+
const validTypes = ["reactor", "commenter"];
|
|
3241
|
+
for (const type of engagementTypes) {
|
|
3242
|
+
if (!validTypes.includes(type)) {
|
|
3243
|
+
throw new ValidationError(
|
|
3244
|
+
`Invalid engagementTypes value: ${String(type)}. Expected 'reactor' and/or 'commenter'.`
|
|
3245
|
+
);
|
|
3246
|
+
}
|
|
3247
|
+
}
|
|
3248
|
+
}
|
|
3249
|
+
const limit = this._getParamValue(params, "limit", "limit");
|
|
3250
|
+
if (limit !== void 0 && (limit < 1 || limit > 1e3)) {
|
|
3251
|
+
throw new ValidationError("limit must be between 1 and 1000 for competitor_rep_engagement");
|
|
3252
|
+
}
|
|
3253
|
+
const maxCompetitors = this._getParamValue(params, "maxCompetitors", "max_competitors");
|
|
3254
|
+
if (maxCompetitors !== void 0 && (maxCompetitors < 1 || maxCompetitors > 50)) {
|
|
3255
|
+
throw new ValidationError("maxCompetitors must be between 1 and 50");
|
|
3256
|
+
}
|
|
3257
|
+
const maxRepsPerCompetitor = this._getParamValue(
|
|
3258
|
+
params,
|
|
3259
|
+
"maxRepsPerCompetitor",
|
|
3260
|
+
"max_reps_per_competitor"
|
|
3261
|
+
);
|
|
3262
|
+
if (maxRepsPerCompetitor !== void 0 && (maxRepsPerCompetitor < 1 || maxRepsPerCompetitor > 100)) {
|
|
3263
|
+
throw new ValidationError("maxRepsPerCompetitor must be between 1 and 100");
|
|
3264
|
+
}
|
|
3265
|
+
const maxEngagementsPerRep = this._getParamValue(
|
|
3266
|
+
params,
|
|
3267
|
+
"maxEngagementsPerRep",
|
|
3268
|
+
"max_engagements_per_rep"
|
|
3269
|
+
);
|
|
3270
|
+
if (maxEngagementsPerRep !== void 0 && (maxEngagementsPerRep < 1 || maxEngagementsPerRep > 1e3)) {
|
|
3271
|
+
throw new ValidationError("maxEngagementsPerRep must be between 1 and 1000");
|
|
3272
|
+
}
|
|
3273
|
+
}
|
|
3131
3274
|
_validateCriteriaParams(params, specializedAgent) {
|
|
3132
3275
|
if (!params)
|
|
3133
3276
|
return;
|
|
@@ -3228,6 +3371,8 @@ class ResponsesResource {
|
|
|
3228
3371
|
}
|
|
3229
3372
|
if (specializedAgent === "competitor_post_engagement")
|
|
3230
3373
|
this._validateCompetitorPostEngagementParams(rawParams);
|
|
3374
|
+
if (specializedAgent === "competitor_rep_engagement")
|
|
3375
|
+
this._validateCompetitorRepEngagementParams(rawParams);
|
|
3231
3376
|
}
|
|
3232
3377
|
_validateFileReference(uri) {
|
|
3233
3378
|
if (uri.startsWith("artifact_"))
|
|
@@ -3563,6 +3708,70 @@ class ResponsesResource {
|
|
|
3563
3708
|
request.specializedAgentParams = params;
|
|
3564
3709
|
return this.create(request);
|
|
3565
3710
|
}
|
|
3711
|
+
/**
|
|
3712
|
+
* Find a competitor's sales reps and surface the AUTHORS of the LinkedIn posts
|
|
3713
|
+
* those reps engage with — i.e. the prospects the competitor is actively
|
|
3714
|
+
* selling to. The INVERSE of {@link competitorPostEngagement}.
|
|
3715
|
+
*
|
|
3716
|
+
* **Discovery mode** — pass `company`: ReAct discovers competitors, then crawls
|
|
3717
|
+
* each one's reps and harvests their outgoing engagement.
|
|
3718
|
+
*
|
|
3719
|
+
* **Explicit mode** — pass `competitors`: skips discovery, uses your list.
|
|
3720
|
+
*
|
|
3721
|
+
* Requires `FIBER_API_KEY` + `CRUSTDATA_API_KEY`.
|
|
3722
|
+
*
|
|
3723
|
+
* @param query - Persona prompt for the prospect-authors (e.g. "VP Eng at AI-native startups…")
|
|
3724
|
+
* @param options - Exactly one of `company` or `competitors` is required
|
|
3725
|
+
* @returns Response; poll with `get()` then read `structuredResponse` as
|
|
3726
|
+
* {@link CompetitorRepEngagementOutput}. See `src/types/competitor-rep-engagement.ts`
|
|
3727
|
+
* for the full agent reference (pipeline, API keys, engagementData shape).
|
|
3728
|
+
*/
|
|
3729
|
+
async competitorRepEngagement(query, options) {
|
|
3730
|
+
const hasCompany = typeof options.company === "string" && options.company.trim().length > 0;
|
|
3731
|
+
const hasCompetitors = Array.isArray(options.competitors) && options.competitors.length > 0;
|
|
3732
|
+
if (hasCompany === hasCompetitors) {
|
|
3733
|
+
throw new ValidationError(
|
|
3734
|
+
"Provide exactly one of `company` or `competitors` for competitorRepEngagement."
|
|
3735
|
+
);
|
|
3736
|
+
}
|
|
3737
|
+
const request = {
|
|
3738
|
+
messages: [{ role: "user", content: query }],
|
|
3739
|
+
specializedAgent: "competitor_rep_engagement"
|
|
3740
|
+
};
|
|
3741
|
+
const params = {};
|
|
3742
|
+
if (options.company)
|
|
3743
|
+
params.company = options.company;
|
|
3744
|
+
if (options.competitors)
|
|
3745
|
+
params.competitors = options.competitors;
|
|
3746
|
+
if (options.companyContext)
|
|
3747
|
+
params.companyContext = options.companyContext;
|
|
3748
|
+
if (options.companyExamples)
|
|
3749
|
+
params.companyExamples = options.companyExamples;
|
|
3750
|
+
if (options.limit !== void 0)
|
|
3751
|
+
params.limit = options.limit;
|
|
3752
|
+
if (options.postsDateRange)
|
|
3753
|
+
params.postsDateRange = options.postsDateRange;
|
|
3754
|
+
if (options.engagementTypes)
|
|
3755
|
+
params.engagementTypes = options.engagementTypes;
|
|
3756
|
+
if (options.repTitles)
|
|
3757
|
+
params.repTitles = options.repTitles;
|
|
3758
|
+
if (options.maxRepsPerCompetitor !== void 0)
|
|
3759
|
+
params.maxRepsPerCompetitor = options.maxRepsPerCompetitor;
|
|
3760
|
+
if (options.maxEngagementsPerRep !== void 0)
|
|
3761
|
+
params.maxEngagementsPerRep = options.maxEngagementsPerRep;
|
|
3762
|
+
if (options.restrictEngagementToTenure !== void 0)
|
|
3763
|
+
params.restrictEngagementToTenure = options.restrictEngagementToTenure;
|
|
3764
|
+
if (options.excludeCompetitorEmployees !== void 0)
|
|
3765
|
+
params.excludeCompetitorEmployees = options.excludeCompetitorEmployees;
|
|
3766
|
+
if (options.expandExclusionViaDiscovery !== void 0)
|
|
3767
|
+
params.expandExclusionViaDiscovery = options.expandExclusionViaDiscovery;
|
|
3768
|
+
if (options.maxCompetitors !== void 0)
|
|
3769
|
+
params.maxCompetitors = options.maxCompetitors;
|
|
3770
|
+
if (options.thoroughEnrichment !== void 0)
|
|
3771
|
+
params.thoroughEnrichment = options.thoroughEnrichment;
|
|
3772
|
+
request.specializedAgentParams = params;
|
|
3773
|
+
return this.create(request);
|
|
3774
|
+
}
|
|
3566
3775
|
}
|
|
3567
3776
|
|
|
3568
3777
|
class SequencesResource {
|
|
@@ -4501,6 +4710,7 @@ class LumnisClient {
|
|
|
4501
4710
|
enrichment;
|
|
4502
4711
|
email;
|
|
4503
4712
|
crm;
|
|
4713
|
+
outreach;
|
|
4504
4714
|
_scopedUserId;
|
|
4505
4715
|
_defaultScope;
|
|
4506
4716
|
constructor(options = {}) {
|
|
@@ -4539,6 +4749,7 @@ class LumnisClient {
|
|
|
4539
4749
|
this.enrichment = new EnrichmentResource(this.http);
|
|
4540
4750
|
this.email = new EmailResource(this.http);
|
|
4541
4751
|
this.crm = new CrmResource(this.http);
|
|
4752
|
+
this.outreach = new OutreachResource(this.http);
|
|
4542
4753
|
}
|
|
4543
4754
|
forUser(userId) {
|
|
4544
4755
|
return new LumnisClient({
|