@signaliz/sdk 1.0.66 → 1.0.68
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/README.md +76 -49
- package/dist/{chunk-ZXSNNBID.mjs → chunk-T5GL6QM7.mjs} +677 -288
- package/dist/index.d.mts +205 -176
- package/dist/index.d.ts +205 -176
- package/dist/index.js +677 -288
- package/dist/index.mjs +1 -1
- package/dist/mcp-config.js +677 -288
- package/dist/mcp-config.mjs +1 -1
- package/package.json +6 -6
package/dist/mcp-config.js
CHANGED
|
@@ -78,8 +78,6 @@ function publicRetryDetails(body) {
|
|
|
78
78
|
...body?.retry_strategy !== void 0 ? { retry_strategy: body.retry_strategy } : {},
|
|
79
79
|
...body?.credits_used !== void 0 ? { credits_used: body.credits_used } : {},
|
|
80
80
|
...body?.credits_charged !== void 0 ? { credits_charged: body.credits_charged } : {},
|
|
81
|
-
...body?.live_provider_called !== void 0 ? { live_provider_called: body.live_provider_called } : {},
|
|
82
|
-
...body?.estimated_external_cost_usd !== void 0 ? { estimated_external_cost_usd: body.estimated_external_cost_usd } : {},
|
|
83
81
|
...body?.job_id !== void 0 ? { job_id: body.job_id } : {},
|
|
84
82
|
...body?.idempotency_key !== void 0 ? { idempotency_key: body.idempotency_key } : {},
|
|
85
83
|
...body?.verification_run_id !== void 0 ? { verification_run_id: body.verification_run_id } : {},
|
|
@@ -232,10 +230,10 @@ var HttpClient = class {
|
|
|
232
230
|
}),
|
|
233
231
|
signal: controller.signal
|
|
234
232
|
});
|
|
235
|
-
const
|
|
236
|
-
const data = safeJson(
|
|
233
|
+
const text2 = await res.text();
|
|
234
|
+
const data = safeJson(text2);
|
|
237
235
|
if (!res.ok) {
|
|
238
|
-
const err = parseError(res.status, data ?? { message:
|
|
236
|
+
const err = parseError(res.status, data ?? { message: text2 });
|
|
239
237
|
if (err.isRetryable && attempt < this.maxRetries) {
|
|
240
238
|
if (err.details?.retry_strategy === "same_run_recovery") throw err;
|
|
241
239
|
lastError = err;
|
|
@@ -249,7 +247,7 @@ var HttpClient = class {
|
|
|
249
247
|
code: "INVALID_JSON",
|
|
250
248
|
message: "MCP response was not valid JSON",
|
|
251
249
|
errorType: "provider_error",
|
|
252
|
-
details: { responseText:
|
|
250
|
+
details: { responseText: text2.slice(0, 500) }
|
|
253
251
|
});
|
|
254
252
|
}
|
|
255
253
|
const responseError = isRecord(data) && isRecord(data.error) ? data.error : null;
|
|
@@ -334,9 +332,9 @@ function requestIdempotencyKey(body, automaticIdempotency) {
|
|
|
334
332
|
function sleep(ms) {
|
|
335
333
|
return new Promise((r) => setTimeout(r, ms));
|
|
336
334
|
}
|
|
337
|
-
function safeJson(
|
|
335
|
+
function safeJson(text2) {
|
|
338
336
|
try {
|
|
339
|
-
return JSON.parse(
|
|
337
|
+
return JSON.parse(text2);
|
|
340
338
|
} catch {
|
|
341
339
|
return null;
|
|
342
340
|
}
|
|
@@ -372,10 +370,10 @@ function unwrapMcpResponse(data) {
|
|
|
372
370
|
}
|
|
373
371
|
const content = isRecord(result) ? result.content : void 0;
|
|
374
372
|
const firstContent = Array.isArray(content) ? content[0] : void 0;
|
|
375
|
-
const
|
|
376
|
-
if (typeof
|
|
377
|
-
const parsed = safeJson(
|
|
378
|
-
return unwrapMcpPayload(parsed ??
|
|
373
|
+
const text2 = isRecord(firstContent) ? firstContent.text : void 0;
|
|
374
|
+
if (typeof text2 === "string") {
|
|
375
|
+
const parsed = safeJson(text2);
|
|
376
|
+
return unwrapMcpPayload(parsed ?? text2);
|
|
379
377
|
}
|
|
380
378
|
return unwrapMcpPayload(result);
|
|
381
379
|
}
|
|
@@ -522,8 +520,8 @@ function assertCompanySignalRows(body) {
|
|
|
522
520
|
);
|
|
523
521
|
if (Array.isArray(body.signal_types)) {
|
|
524
522
|
body.signal_types.forEach(
|
|
525
|
-
(
|
|
526
|
-
|
|
523
|
+
(signalType2, index) => assertStringBytes(
|
|
524
|
+
signalType2,
|
|
527
525
|
`signal_types[${index}]`,
|
|
528
526
|
SIGNAL_TYPE_MAX_UTF8_BYTES,
|
|
529
527
|
index
|
|
@@ -533,9 +531,11 @@ function assertCompanySignalRows(body) {
|
|
|
533
531
|
requests.forEach((value, index) => {
|
|
534
532
|
if (!value || typeof value !== "object" || Array.isArray(value)) return;
|
|
535
533
|
const request = value;
|
|
534
|
+
const domain = request.domain ?? request.company_domain;
|
|
535
|
+
const domainField = request.domain !== void 0 ? "domain" : "company_domain";
|
|
536
536
|
assertStringBytes(
|
|
537
|
-
|
|
538
|
-
`requests[${index}]
|
|
537
|
+
domain,
|
|
538
|
+
`requests[${index}].${domainField}`,
|
|
539
539
|
DOMAIN_MAX_UTF8_BYTES,
|
|
540
540
|
index
|
|
541
541
|
);
|
|
@@ -615,6 +615,190 @@ function assertLargeCoreProductInputBounds(path2, body) {
|
|
|
615
615
|
);
|
|
616
616
|
}
|
|
617
617
|
|
|
618
|
+
// src/public-signal-row.ts
|
|
619
|
+
var PUBLIC_COMPANY_SIGNAL_MAX_COVERAGE_COUNT = 10;
|
|
620
|
+
function recordValue(value) {
|
|
621
|
+
return value && typeof value === "object" && !Array.isArray(value) ? value : {};
|
|
622
|
+
}
|
|
623
|
+
function text(value) {
|
|
624
|
+
return typeof value === "string" ? value.trim() : "";
|
|
625
|
+
}
|
|
626
|
+
function dateOnly(value) {
|
|
627
|
+
const raw = text(value);
|
|
628
|
+
const match = raw.match(/^\d{4}-\d{2}-\d{2}/);
|
|
629
|
+
if (!match) return "";
|
|
630
|
+
const parsed = /* @__PURE__ */ new Date(`${match[0]}T00:00:00.000Z`);
|
|
631
|
+
return Number.isFinite(parsed.getTime()) && parsed.toISOString().slice(0, 10) === match[0] ? match[0] : "";
|
|
632
|
+
}
|
|
633
|
+
function classificationSlug(value) {
|
|
634
|
+
const direct = text(value);
|
|
635
|
+
if (direct) return direct;
|
|
636
|
+
const classification = recordValue(value);
|
|
637
|
+
return text(classification.slug || classification.type || classification.name);
|
|
638
|
+
}
|
|
639
|
+
function signalType(signal) {
|
|
640
|
+
const raw = recordValue(signal.raw_data);
|
|
641
|
+
const generic = /* @__PURE__ */ new Set(["unclassified", "unknown", "other", "news", "signal"]);
|
|
642
|
+
for (const value of [
|
|
643
|
+
signal.signal_type,
|
|
644
|
+
classificationSlug(signal.signal_classification),
|
|
645
|
+
classificationSlug(signal.classification),
|
|
646
|
+
raw.signal_type,
|
|
647
|
+
classificationSlug(raw.signal_classification),
|
|
648
|
+
classificationSlug(raw.classification),
|
|
649
|
+
signal.type,
|
|
650
|
+
signal.category,
|
|
651
|
+
signal.event_type,
|
|
652
|
+
raw.type,
|
|
653
|
+
raw.category,
|
|
654
|
+
raw.event_type
|
|
655
|
+
]) {
|
|
656
|
+
const candidate = text(value);
|
|
657
|
+
if (candidate && !generic.has(candidate.toLowerCase())) return candidate;
|
|
658
|
+
}
|
|
659
|
+
return "";
|
|
660
|
+
}
|
|
661
|
+
function verifiedHttpsUrl(value) {
|
|
662
|
+
const candidate = text(value);
|
|
663
|
+
if (!candidate || /\s/.test(candidate)) return "";
|
|
664
|
+
try {
|
|
665
|
+
const parsed = new URL(candidate);
|
|
666
|
+
return parsed.protocol === "https:" && Boolean(parsed.hostname) && !parsed.username && !parsed.password ? candidate : "";
|
|
667
|
+
} catch {
|
|
668
|
+
return "";
|
|
669
|
+
}
|
|
670
|
+
}
|
|
671
|
+
function normalizedDomain(value) {
|
|
672
|
+
const normalized = text(value).toLowerCase().replace(/^https?:\/\//, "").replace(/^www\./, "").split(/[/?#]/)[0].replace(/\.$/, "");
|
|
673
|
+
return /^(?=.{3,253}$)(?:[a-z0-9](?:[a-z0-9-]{0,61}[a-z0-9])?\.)+[a-z]{2,63}$/i.test(normalized) ? normalized : "";
|
|
674
|
+
}
|
|
675
|
+
function firstValid(values, normalize) {
|
|
676
|
+
for (const value of values) {
|
|
677
|
+
const normalized = normalize(value);
|
|
678
|
+
if (normalized) return normalized;
|
|
679
|
+
}
|
|
680
|
+
return "";
|
|
681
|
+
}
|
|
682
|
+
function publicSignalRow(value, fallbackCompany) {
|
|
683
|
+
const signal = recordValue(value);
|
|
684
|
+
const raw = recordValue(signal.raw_data);
|
|
685
|
+
const company = recordValue(signal.company);
|
|
686
|
+
const rawCompany = recordValue(raw.company);
|
|
687
|
+
const fallback = recordValue(fallbackCompany);
|
|
688
|
+
const row = {
|
|
689
|
+
signal_type: signalType(signal),
|
|
690
|
+
signal_title: firstValid([
|
|
691
|
+
signal.signal_title,
|
|
692
|
+
raw.signal_title,
|
|
693
|
+
signal.title,
|
|
694
|
+
raw.title,
|
|
695
|
+
signal.headline,
|
|
696
|
+
raw.headline,
|
|
697
|
+
signal.name,
|
|
698
|
+
raw.name
|
|
699
|
+
], text),
|
|
700
|
+
signal_summary: firstValid([
|
|
701
|
+
signal.signal_summary,
|
|
702
|
+
raw.signal_summary,
|
|
703
|
+
signal.summary,
|
|
704
|
+
raw.summary,
|
|
705
|
+
signal.signal_content,
|
|
706
|
+
raw.signal_content,
|
|
707
|
+
signal.content,
|
|
708
|
+
raw.content,
|
|
709
|
+
signal.description,
|
|
710
|
+
raw.description
|
|
711
|
+
], text),
|
|
712
|
+
source: firstValid([
|
|
713
|
+
signal.canonical_source_url,
|
|
714
|
+
signal.source_url,
|
|
715
|
+
signal.verified_source_url,
|
|
716
|
+
signal.signal_source,
|
|
717
|
+
signal.source,
|
|
718
|
+
signal.url,
|
|
719
|
+
raw.canonical_source_url,
|
|
720
|
+
raw.source_url,
|
|
721
|
+
raw.verified_source_url,
|
|
722
|
+
raw.signal_source,
|
|
723
|
+
raw.source,
|
|
724
|
+
raw.url
|
|
725
|
+
], verifiedHttpsUrl),
|
|
726
|
+
date: firstValid([
|
|
727
|
+
signal.date,
|
|
728
|
+
signal.event_date,
|
|
729
|
+
signal.signal_date,
|
|
730
|
+
signal.published_date,
|
|
731
|
+
signal.published_at,
|
|
732
|
+
signal.detected_at,
|
|
733
|
+
signal.observed_at,
|
|
734
|
+
raw.date,
|
|
735
|
+
raw.event_date,
|
|
736
|
+
raw.signal_date,
|
|
737
|
+
raw.published_date,
|
|
738
|
+
raw.published_at,
|
|
739
|
+
raw.detected_at,
|
|
740
|
+
raw.observed_at
|
|
741
|
+
], dateOnly),
|
|
742
|
+
company_name: text(
|
|
743
|
+
signal.company_name || company.name || company.company_name || raw.company_name || rawCompany.name || rawCompany.company_name || fallback.company_name || fallback.name
|
|
744
|
+
),
|
|
745
|
+
domain: firstValid([
|
|
746
|
+
signal.company_domain,
|
|
747
|
+
signal.domain,
|
|
748
|
+
company.domain,
|
|
749
|
+
company.company_domain,
|
|
750
|
+
raw.company_domain,
|
|
751
|
+
raw.domain,
|
|
752
|
+
rawCompany.domain,
|
|
753
|
+
rawCompany.company_domain,
|
|
754
|
+
fallback.company_domain,
|
|
755
|
+
fallback.domain
|
|
756
|
+
], normalizedDomain)
|
|
757
|
+
};
|
|
758
|
+
return row.signal_type && row.source && row.date && row.company_name && row.domain ? row : null;
|
|
759
|
+
}
|
|
760
|
+
function publicSignalRows(value, fallbackCompany) {
|
|
761
|
+
if (!Array.isArray(value)) return [];
|
|
762
|
+
return value.flatMap((item) => {
|
|
763
|
+
const row = publicSignalRow(item, fallbackCompany);
|
|
764
|
+
return row ? [row] : [];
|
|
765
|
+
});
|
|
766
|
+
}
|
|
767
|
+
function companySignalEventIdentities(value, row) {
|
|
768
|
+
const signal = recordValue(value);
|
|
769
|
+
const raw = recordValue(signal.raw_data);
|
|
770
|
+
const eventId = text(
|
|
771
|
+
signal.event_id || signal.eventId || signal.fact_id || signal.factId || raw.event_id || raw.eventId || raw.fact_id || raw.factId
|
|
772
|
+
).toLowerCase();
|
|
773
|
+
return [
|
|
774
|
+
...eventId ? [`event:${eventId}`] : [],
|
|
775
|
+
`source:${row.source.toLowerCase()}`
|
|
776
|
+
];
|
|
777
|
+
}
|
|
778
|
+
function publicCompanySignalRows(value, fallbackCompany) {
|
|
779
|
+
if (!Array.isArray(value)) return [];
|
|
780
|
+
const seenEvents = /* @__PURE__ */ new Set();
|
|
781
|
+
const rows = [];
|
|
782
|
+
for (const item of value) {
|
|
783
|
+
const row = publicSignalRow(item, fallbackCompany);
|
|
784
|
+
if (!row) continue;
|
|
785
|
+
const identities = companySignalEventIdentities(item, row);
|
|
786
|
+
if (identities.some((identity) => seenEvents.has(identity))) continue;
|
|
787
|
+
identities.forEach((identity) => seenEvents.add(identity));
|
|
788
|
+
rows.push(row);
|
|
789
|
+
if (rows.length >= PUBLIC_COMPANY_SIGNAL_MAX_COVERAGE_COUNT) break;
|
|
790
|
+
}
|
|
791
|
+
return rows;
|
|
792
|
+
}
|
|
793
|
+
function oneSignalPerCompany(rows) {
|
|
794
|
+
const seen = /* @__PURE__ */ new Set();
|
|
795
|
+
return rows.filter((row) => {
|
|
796
|
+
if (seen.has(row.domain)) return false;
|
|
797
|
+
seen.add(row.domain);
|
|
798
|
+
return true;
|
|
799
|
+
});
|
|
800
|
+
}
|
|
801
|
+
|
|
618
802
|
// ../../supabase/functions/_shared/find-email-identity.ts
|
|
619
803
|
var LINKEDIN_PERSON_PROFILE_URL_PATTERN = "^[hH][tT][tT][pP][sS]://(?:[A-Za-z0-9-]+\\.)*[lL][iI][nN][kK][eE][dD][iI][nN]\\.[cC][oO][mM]/[iI][nN]/[^/?#]+/?(?:[?#].*)?$";
|
|
620
804
|
var LINKEDIN_PERSON_PROFILE_URL_REGEX = new RegExp(LINKEDIN_PERSON_PROFILE_URL_PATTERN);
|
|
@@ -646,6 +830,27 @@ var Signaliz = class {
|
|
|
646
830
|
constructor(config) {
|
|
647
831
|
this.client = new HttpClient(config);
|
|
648
832
|
}
|
|
833
|
+
/**
|
|
834
|
+
* The canonical Signal Awareness control plane used by the CLI and MCP.
|
|
835
|
+
* Manual runs accept a stable retry key and return an explicit billing
|
|
836
|
+
* receipt, including zero-credit available-data reuse.
|
|
837
|
+
*/
|
|
838
|
+
async signalAwareness(request) {
|
|
839
|
+
const data = await this.client.post(
|
|
840
|
+
"api/v1/signal-awareness",
|
|
841
|
+
signalAwarenessRequestBody(request)
|
|
842
|
+
);
|
|
843
|
+
return normalizeSignalAwarenessResponse(data);
|
|
844
|
+
}
|
|
845
|
+
async createSignalMonitor(monitor) {
|
|
846
|
+
return this.signalAwareness({ action: "create", monitor });
|
|
847
|
+
}
|
|
848
|
+
async listSignalMonitors(limit, offset) {
|
|
849
|
+
return this.signalAwareness({ action: "list", limit, offset });
|
|
850
|
+
}
|
|
851
|
+
async runSignalMonitor(monitorId, idempotencyKey) {
|
|
852
|
+
return this.signalAwareness({ action: "manual_run", monitorId, idempotencyKey });
|
|
853
|
+
}
|
|
649
854
|
async findEmail(params) {
|
|
650
855
|
const request = findEmailRequestBody(params);
|
|
651
856
|
assertFindEmailRequestIdentity(request);
|
|
@@ -715,14 +920,12 @@ var Signaliz = class {
|
|
|
715
920
|
error,
|
|
716
921
|
error_code: "INPUT_001",
|
|
717
922
|
retry_eligible: false,
|
|
718
|
-
credits_used: 0
|
|
719
|
-
live_provider_called: false
|
|
923
|
+
credits_used: 0
|
|
720
924
|
});
|
|
721
925
|
}
|
|
722
926
|
const request = compact({
|
|
723
927
|
email: email || void 0,
|
|
724
928
|
verification_run_id: options?.verificationRunId,
|
|
725
|
-
skip_cache: options?.skipCache,
|
|
726
929
|
dry_run: options?.dryRun,
|
|
727
930
|
idempotency_key: options?.idempotencyKey
|
|
728
931
|
});
|
|
@@ -807,19 +1010,38 @@ var Signaliz = class {
|
|
|
807
1010
|
);
|
|
808
1011
|
return normalizeSignalDiscoveryResult(params, data);
|
|
809
1012
|
}
|
|
1013
|
+
/** Signals First is the customer-facing name for open-ended discovery. */
|
|
1014
|
+
async discoverSignalsFirst(params) {
|
|
1015
|
+
return this.discoverSignals(params);
|
|
1016
|
+
}
|
|
1017
|
+
async startFlow(params) {
|
|
1018
|
+
validateSignalizFlowParams(params);
|
|
1019
|
+
const data = await this.client.post(
|
|
1020
|
+
"api/v1/flow",
|
|
1021
|
+
signalizFlowRequestBody(params)
|
|
1022
|
+
);
|
|
1023
|
+
return data.dry_run === true ? normalizeSignalizFlowPlanResult(data) : normalizeSignalizFlowStartResult(data);
|
|
1024
|
+
}
|
|
1025
|
+
async getFlow(runId) {
|
|
1026
|
+
const normalizedRunId = runId.trim();
|
|
1027
|
+
if (!normalizedRunId || normalizedRunId.length > 200) {
|
|
1028
|
+
throw new RangeError("runId must contain between 1 and 200 characters");
|
|
1029
|
+
}
|
|
1030
|
+
const data = await this.client.post(
|
|
1031
|
+
"api/v1/flow",
|
|
1032
|
+
{ run_id: normalizedRunId },
|
|
1033
|
+
{ automaticIdempotency: false }
|
|
1034
|
+
);
|
|
1035
|
+
return normalizeSignalizFlowStatus(data);
|
|
1036
|
+
}
|
|
810
1037
|
async enrichCompanies(companies, options) {
|
|
811
1038
|
validateBatchSize(companies);
|
|
812
1039
|
companies.forEach(validateCompanySignalParams);
|
|
813
1040
|
const requests = companies.map(companySignalRequestBody);
|
|
814
|
-
if (companies.length > 25 && requests.some((request) => request.include_candidate_evidence === true)) {
|
|
815
|
-
throw new RangeError(
|
|
816
|
-
"includeCandidateEvidence is not supported in Company Signals batches larger than 25 because rejected evidence diagnostics are intentionally excluded from durable scale storage; split diagnostic requests into batches of at most 25."
|
|
817
|
-
);
|
|
818
|
-
}
|
|
819
1041
|
const largeBatch = companySignalLargeBatchSubmission(requests);
|
|
820
1042
|
if (companies.length > 25 && !largeBatch) {
|
|
821
1043
|
throw new RangeError(
|
|
822
|
-
"Company Signals batches larger than 25 require homogeneous new-enrichment rows with
|
|
1044
|
+
"Company Signals batches larger than 25 require homogeneous new-enrichment rows with a domain only; split recovery or mixed-context rows into batches of at most 25."
|
|
823
1045
|
);
|
|
824
1046
|
}
|
|
825
1047
|
if (options?.dryRun === true) {
|
|
@@ -870,14 +1092,14 @@ var Signaliz = class {
|
|
|
870
1092
|
if (total !== companies.length) {
|
|
871
1093
|
throw new Error(`Company Signals batch returned ${total} results for ${companies.length} requests`);
|
|
872
1094
|
}
|
|
873
|
-
const
|
|
1095
|
+
const batch2 = finalizeCoreBatch(
|
|
874
1096
|
companies.length,
|
|
875
1097
|
startedAt,
|
|
876
1098
|
recoverableRowsToRound(rows, "Company Signals"),
|
|
877
1099
|
(item) => normalizeCompanySignalResult(companies[item.index], item.raw)
|
|
878
1100
|
);
|
|
879
1101
|
return compactKnownDuplicateBatch(
|
|
880
|
-
|
|
1102
|
+
batch2,
|
|
881
1103
|
dedupeExactBatchItems(
|
|
882
1104
|
requests,
|
|
883
1105
|
(request) => coreProductBatchRequestKey("api/v1/company-signals", request)
|
|
@@ -898,15 +1120,21 @@ var Signaliz = class {
|
|
|
898
1120
|
return batchItemFailure(item.index, error instanceof Error ? error.message : String(error), item.raw);
|
|
899
1121
|
}
|
|
900
1122
|
});
|
|
901
|
-
const
|
|
902
|
-
const succeeded = compactedResults.filter((item) => item.success).length;
|
|
903
|
-
return {
|
|
1123
|
+
const batch = {
|
|
904
1124
|
total: companies.length,
|
|
905
|
-
succeeded,
|
|
906
|
-
failed: companies.length -
|
|
1125
|
+
succeeded: results.filter((item) => item.success).length,
|
|
1126
|
+
failed: companies.length - results.filter((item) => item.success).length,
|
|
907
1127
|
durationMs: Date.now() - startedAt,
|
|
908
|
-
results
|
|
1128
|
+
results
|
|
909
1129
|
};
|
|
1130
|
+
return compactKnownDuplicateBatch(
|
|
1131
|
+
batch,
|
|
1132
|
+
dedupeExactBatchItems(
|
|
1133
|
+
requests,
|
|
1134
|
+
(request) => coreProductBatchRequestKey("api/v1/company-signals", request)
|
|
1135
|
+
).sourceIndexByInput,
|
|
1136
|
+
options?.compactDuplicates === true
|
|
1137
|
+
);
|
|
910
1138
|
}
|
|
911
1139
|
async resumeCompanySignalBatch(jobId, options) {
|
|
912
1140
|
const startedAt = Date.now();
|
|
@@ -935,7 +1163,7 @@ var Signaliz = class {
|
|
|
935
1163
|
async createSignalCopyBatch(requests, options) {
|
|
936
1164
|
validateBatchSize(requests);
|
|
937
1165
|
requests.forEach(validateSignalToCopyParams);
|
|
938
|
-
|
|
1166
|
+
validateLargeSignalCopyBatch(requests);
|
|
939
1167
|
if (options?.dryRun === true) {
|
|
940
1168
|
return this.runCoreProductDryRun(
|
|
941
1169
|
"api/v1/signal-to-copy",
|
|
@@ -948,7 +1176,7 @@ var Signaliz = class {
|
|
|
948
1176
|
if (options?.waitForResult === false) {
|
|
949
1177
|
return this.submitRecoverableCoreBatchJob(
|
|
950
1178
|
"api/v1/signal-to-copy",
|
|
951
|
-
requests.map(
|
|
1179
|
+
requests.map(durableSignalCopyRequestBody),
|
|
952
1180
|
"Signal to Copy",
|
|
953
1181
|
options.idempotencyKey,
|
|
954
1182
|
requests.map((_, index) => index)
|
|
@@ -956,7 +1184,7 @@ var Signaliz = class {
|
|
|
956
1184
|
}
|
|
957
1185
|
const job = await this.submitRecoverableCoreBatchJob(
|
|
958
1186
|
"api/v1/signal-to-copy",
|
|
959
|
-
requests.map(
|
|
1187
|
+
requests.map(durableSignalCopyRequestBody),
|
|
960
1188
|
"Signal to Copy",
|
|
961
1189
|
options?.idempotencyKey,
|
|
962
1190
|
requests.map((_, index) => index)
|
|
@@ -1494,8 +1722,6 @@ function batchItemFailure(index, error, raw) {
|
|
|
1494
1722
|
const retryStrategy = raw?.retry_strategy ?? raw?.retryStrategy;
|
|
1495
1723
|
const creditsUsed = raw?.credits_used ?? raw?.creditsUsed;
|
|
1496
1724
|
const creditsCharged = raw?.credits_charged ?? raw?.creditsCharged;
|
|
1497
|
-
const liveProviderCalled = raw?.live_provider_called ?? raw?.liveProviderCalled;
|
|
1498
|
-
const estimatedExternalCostUsd = raw?.estimated_external_cost_usd ?? raw?.estimatedExternalCostUsd;
|
|
1499
1725
|
const runId = [raw?.run_id, raw?.runId, raw?.signal_run_id, raw?.signalRunId].find((value) => typeof value === "string" && value.trim());
|
|
1500
1726
|
const verificationRunId = raw?.verification_run_id ?? raw?.verificationRunId;
|
|
1501
1727
|
const jobId = raw?.job_id ?? raw?.jobId;
|
|
@@ -1510,8 +1736,6 @@ function batchItemFailure(index, error, raw) {
|
|
|
1510
1736
|
...["new_idempotency_key", "same_run_recovery"].includes(String(retryStrategy)) ? { retryStrategy } : {},
|
|
1511
1737
|
...creditsUsed === 0 ? { creditsUsed: 0 } : {},
|
|
1512
1738
|
...creditsCharged === 0 ? { creditsCharged: 0 } : {},
|
|
1513
|
-
...liveProviderCalled === false ? { liveProviderCalled: false } : {},
|
|
1514
|
-
...estimatedExternalCostUsd === 0 ? { estimatedExternalCostUsd: 0 } : {},
|
|
1515
1739
|
...typeof runId === "string" && runId.trim() ? { runId: runId.trim() } : {},
|
|
1516
1740
|
...typeof verificationRunId === "string" && verificationRunId.trim() ? { verificationRunId: verificationRunId.trim() } : {},
|
|
1517
1741
|
...typeof jobId === "string" && jobId.trim() ? { jobId: jobId.trim() } : {},
|
|
@@ -1567,6 +1791,51 @@ function newBatchIdempotencyKey(label) {
|
|
|
1567
1791
|
function compact(input) {
|
|
1568
1792
|
return Object.fromEntries(Object.entries(input).filter(([, value]) => value !== void 0));
|
|
1569
1793
|
}
|
|
1794
|
+
var INTERNAL_PRODUCT_RESULT_KEYS = /* @__PURE__ */ new Set([
|
|
1795
|
+
"billing_metadata",
|
|
1796
|
+
"historical_billing_metadata",
|
|
1797
|
+
"result_returned_from",
|
|
1798
|
+
"fresh_enrichment_used",
|
|
1799
|
+
"live_provider_called",
|
|
1800
|
+
"openrouter_called",
|
|
1801
|
+
"byo_openrouter_used",
|
|
1802
|
+
"ai_provider_called",
|
|
1803
|
+
"byo_ai_used",
|
|
1804
|
+
"estimated_external_cost_usd",
|
|
1805
|
+
"included_provider_cost_usd",
|
|
1806
|
+
"would_have_charged_credits",
|
|
1807
|
+
"available_data_only",
|
|
1808
|
+
"available_data_input_count",
|
|
1809
|
+
"unique_available_data_input_count"
|
|
1810
|
+
]);
|
|
1811
|
+
var PUBLIC_PRODUCT_DATA_MEMO = /* @__PURE__ */ new WeakMap();
|
|
1812
|
+
function publicProductData(value, capability = "") {
|
|
1813
|
+
if (Array.isArray(value)) return value.map((item) => publicProductData(item, capability));
|
|
1814
|
+
if (!value || typeof value !== "object") return value;
|
|
1815
|
+
const source = value;
|
|
1816
|
+
const inferredCapability = String(source.capability || capability).toLowerCase();
|
|
1817
|
+
const cachedByCapability = PUBLIC_PRODUCT_DATA_MEMO.get(source);
|
|
1818
|
+
if (cachedByCapability?.has(inferredCapability)) return cachedByCapability.get(inferredCapability);
|
|
1819
|
+
const result = Object.fromEntries(Object.entries(source).flatMap(([key, raw]) => {
|
|
1820
|
+
const normalizedKey = key.toLowerCase();
|
|
1821
|
+
if (INTERNAL_PRODUCT_RESULT_KEYS.has(normalizedKey) || normalizedKey.includes("cache")) return [];
|
|
1822
|
+
if (typeof raw === "string" && (raw.toLowerCase().includes("cache") || raw === "available_data")) {
|
|
1823
|
+
if (["error", "message", "suggested_action", "failure_reason"].includes(normalizedKey)) {
|
|
1824
|
+
return [[key, "The result could not be finalized. Retry safely using the existing run or job ID."]];
|
|
1825
|
+
}
|
|
1826
|
+
if (["source", "email_source", "email_source_label", "verification_source", "provider_status"].includes(normalizedKey)) {
|
|
1827
|
+
const sourceLabel = inferredCapability.includes("verify") ? "email_verification" : inferredCapability.includes("find") ? "email_finder" : inferredCapability.includes("signal_to_copy") ? "signal_to_copy" : "company_signal_enrichment";
|
|
1828
|
+
return [[key, sourceLabel]];
|
|
1829
|
+
}
|
|
1830
|
+
return [];
|
|
1831
|
+
}
|
|
1832
|
+
return [[key, publicProductData(raw, inferredCapability)]];
|
|
1833
|
+
}));
|
|
1834
|
+
const memo = cachedByCapability || /* @__PURE__ */ new Map();
|
|
1835
|
+
memo.set(inferredCapability, result);
|
|
1836
|
+
if (!cachedByCapability) PUBLIC_PRODUCT_DATA_MEMO.set(source, memo);
|
|
1837
|
+
return result;
|
|
1838
|
+
}
|
|
1570
1839
|
function findEmailRequestBody(params) {
|
|
1571
1840
|
return compact({
|
|
1572
1841
|
run_id: params.runId,
|
|
@@ -1576,7 +1845,7 @@ function findEmailRequestBody(params) {
|
|
|
1576
1845
|
last_name: params.lastName,
|
|
1577
1846
|
linkedin_url: params.linkedinUrl,
|
|
1578
1847
|
company_name: params.companyName,
|
|
1579
|
-
|
|
1848
|
+
wait_for_result: params.waitForResult,
|
|
1580
1849
|
dry_run: params.dryRun,
|
|
1581
1850
|
idempotency_key: params.idempotencyKey
|
|
1582
1851
|
});
|
|
@@ -1591,11 +1860,10 @@ function assertFindEmailRequestIdentity(request) {
|
|
|
1591
1860
|
}
|
|
1592
1861
|
function verifyEmailBatchRequestBody(input, options) {
|
|
1593
1862
|
if (typeof input === "string") {
|
|
1594
|
-
return compact({ email: input
|
|
1863
|
+
return compact({ email: input });
|
|
1595
1864
|
}
|
|
1596
1865
|
return compact({
|
|
1597
1866
|
email: input.email,
|
|
1598
|
-
skip_cache: input.skipCache ?? options?.skipCache,
|
|
1599
1867
|
idempotency_key: input.idempotencyKey
|
|
1600
1868
|
});
|
|
1601
1869
|
}
|
|
@@ -1627,6 +1895,7 @@ function normalizeCoreProductDryRunResult(data) {
|
|
|
1627
1895
|
};
|
|
1628
1896
|
}
|
|
1629
1897
|
function normalizeFindEmailResult(data) {
|
|
1898
|
+
data = publicProductData(data, "find_email");
|
|
1630
1899
|
const processing = String(data.status || "").toLowerCase() === "processing";
|
|
1631
1900
|
const failed = coreProductResponseFailed(data);
|
|
1632
1901
|
const rawEmail = typeof data.email === "string" && data.email.trim() ? data.email.trim() : null;
|
|
@@ -1643,7 +1912,6 @@ function normalizeFindEmailResult(data) {
|
|
|
1643
1912
|
const verificationAgeDays = typeof data.verification_age_days === "number" && Number.isFinite(data.verification_age_days) ? data.verification_age_days : null;
|
|
1644
1913
|
const providerUsed = data.provider_used ?? data.provider ?? data.email_source ?? data.source ?? "unknown";
|
|
1645
1914
|
const verificationSource = data.verification_source ?? providerUsed;
|
|
1646
|
-
const billingMetadata = data.billing_metadata && typeof data.billing_metadata === "object" && !Array.isArray(data.billing_metadata) ? data.billing_metadata : void 0;
|
|
1647
1915
|
return {
|
|
1648
1916
|
success: processing || !failed && found,
|
|
1649
1917
|
found,
|
|
@@ -1666,20 +1934,10 @@ function normalizeFindEmailResult(data) {
|
|
|
1666
1934
|
verificationSource,
|
|
1667
1935
|
verificationObservedAt: typeof data.verification_observed_at === "string" ? data.verification_observed_at : void 0,
|
|
1668
1936
|
failureReason: data.failure_reason ?? (failed || !found ? "no_verified_email_found" : "none"),
|
|
1669
|
-
creditsUsed: data.credits_used
|
|
1670
|
-
creditsCharged: data.credits_charged
|
|
1671
|
-
|
|
1672
|
-
|
|
1673
|
-
historicalBillingMetadata: data.historical_billing_metadata,
|
|
1674
|
-
resultReturnedFrom: data.result_returned_from ?? billingMetadata?.result_returned_from,
|
|
1675
|
-
cacheHit: typeof data.cache_hit === "boolean" ? data.cache_hit : billingMetadata?.cache_hit,
|
|
1676
|
-
negativeCacheHit: data.negative_cache_hit,
|
|
1677
|
-
negativeCacheTtlSeconds: data.negative_cache_ttl_seconds,
|
|
1678
|
-
cacheTier: data.cache_tier,
|
|
1679
|
-
freshEnrichmentUsed: typeof data.fresh_enrichment_used === "boolean" ? data.fresh_enrichment_used : billingMetadata?.fresh_enrichment_used,
|
|
1680
|
-
liveProviderCalled: typeof data.live_provider_called === "boolean" ? data.live_provider_called : billingMetadata?.live_provider_called,
|
|
1681
|
-
openrouterCalled: typeof data.openrouter_called === "boolean" ? data.openrouter_called : billingMetadata?.openrouter_called,
|
|
1682
|
-
byoOpenrouterUsed: typeof data.byo_openrouter_used === "boolean" ? data.byo_openrouter_used : billingMetadata?.byo_openrouter_used,
|
|
1937
|
+
creditsUsed: data.credits_used,
|
|
1938
|
+
creditsCharged: data.credits_charged,
|
|
1939
|
+
billingReplayed: data.billing_replayed,
|
|
1940
|
+
idempotencyReplayed: data.idempotency_replayed,
|
|
1683
1941
|
error: processing || found ? void 0 : coreProductErrorMessage(data) ?? "No verified email found",
|
|
1684
1942
|
errorCode: processing || found ? void 0 : coreProductErrorCode(data) ?? "EMAIL_NOT_FOUND",
|
|
1685
1943
|
status: processing ? "processing" : "completed",
|
|
@@ -1691,18 +1949,17 @@ function normalizeFindEmailResult(data) {
|
|
|
1691
1949
|
doNotAutoResubmit: data.do_not_auto_resubmit === true,
|
|
1692
1950
|
recoveryMode: data.recovery_mode === "same_run" ? "same_run" : void 0,
|
|
1693
1951
|
recoveryStatus: ["pending", "completed"].includes(String(data.recovery_status)) ? data.recovery_status : void 0,
|
|
1694
|
-
cachePublicationStatus: data.cache_publication_status,
|
|
1695
|
-
cachePublicationRetryEligible: data.cache_publication_retry_eligible,
|
|
1696
1952
|
raw: data
|
|
1697
1953
|
};
|
|
1698
1954
|
}
|
|
1699
1955
|
function normalizeVerifyEmailResult(email, data) {
|
|
1956
|
+
data = publicProductData(data, "verify_email");
|
|
1700
1957
|
const failed = coreProductResponseFailed(data);
|
|
1701
1958
|
const malformed = data.is_malformed === true || data.verification_verdict === "malformed" || data.verification_status === "malformed" || data.deliverability_status === "malformed";
|
|
1702
|
-
const verificationStatus =
|
|
1959
|
+
const verificationStatus = normalizeVerifyEmailStatus(
|
|
1703
1960
|
failed ? malformed ? "malformed" : "error" : data.verification_status ?? data.verification_verdict ?? data.deliverability_status ?? "unknown"
|
|
1704
|
-
)
|
|
1705
|
-
const deliverabilityStatus =
|
|
1961
|
+
);
|
|
1962
|
+
const deliverabilityStatus = normalizeVerifyEmailStatus(data.deliverability_status ?? verificationStatus);
|
|
1706
1963
|
const verified = !failed && (data.email_verified === true || ["valid", "deliverable"].includes(verificationStatus));
|
|
1707
1964
|
const isCatchAll = data.email_is_catch_all ?? data.is_catch_all ?? data.catch_all ?? data.diagnostics?.is_catch_all ?? false;
|
|
1708
1965
|
const verifiedForSending = !failed && data.verified_for_sending === true;
|
|
@@ -1723,10 +1980,12 @@ function normalizeVerifyEmailResult(email, data) {
|
|
|
1723
1980
|
verifiedForSending,
|
|
1724
1981
|
verificationStatus,
|
|
1725
1982
|
deliverabilityStatus,
|
|
1726
|
-
verificationVerdict:
|
|
1983
|
+
verificationVerdict: normalizeVerifyEmailStatus(
|
|
1984
|
+
failed ? malformed ? "malformed" : "error" : data.verification_verdict ?? verificationStatus
|
|
1985
|
+
),
|
|
1727
1986
|
isRoleAccount: data.is_role_account === true || data.email_is_role_account === true || data.role === true,
|
|
1728
1987
|
quality: typeof data.quality === "string" ? data.quality : null,
|
|
1729
|
-
recommendation:
|
|
1988
|
+
recommendation: normalizeVerifyEmailRecommendation(data.recommendation, verificationStatus, verifiedForSending),
|
|
1730
1989
|
smtpStatus: data.smtp_status ?? (isCatchAll ? "accept_all" : verifiedForSending ? "accepted" : "not_checked"),
|
|
1731
1990
|
providerStatus: data.provider_status ?? verificationStatus,
|
|
1732
1991
|
failureReason: data.failure_reason ?? (verifiedForSending ? "none" : isCatchAll ? "catch_all_domain_not_send_safe" : "verification_not_send_safe"),
|
|
@@ -1735,54 +1994,49 @@ function normalizeVerifyEmailResult(email, data) {
|
|
|
1735
1994
|
verificationSource: data.verification_source,
|
|
1736
1995
|
verificationObservedAt: typeof data.verification_observed_at === "string" ? data.verification_observed_at : void 0,
|
|
1737
1996
|
billingReplayed: data.billing_replayed,
|
|
1997
|
+
idempotencyReplayed: data.idempotency_replayed,
|
|
1738
1998
|
creditsUsed: data.credits_used,
|
|
1739
|
-
billingMetadata: data.billing_metadata,
|
|
1740
|
-
historicalBillingMetadata: data.historical_billing_metadata,
|
|
1741
|
-
resultReturnedFrom: data.result_returned_from,
|
|
1742
|
-
cacheHit: data.cache_hit,
|
|
1743
|
-
negativeCacheHit: data.negative_cache_hit,
|
|
1744
|
-
negativeCacheTtlSeconds: data.negative_cache_ttl_seconds,
|
|
1745
|
-
cacheTier: data.cache_tier,
|
|
1746
|
-
freshEnrichmentUsed: data.fresh_enrichment_used,
|
|
1747
|
-
liveProviderCalled: data.live_provider_called,
|
|
1748
|
-
openrouterCalled: data.openrouter_called,
|
|
1749
|
-
byoOpenrouterUsed: data.byo_openrouter_used,
|
|
1750
|
-
estimatedExternalCostUsd: data.estimated_external_cost_usd,
|
|
1751
1999
|
runId: data.run_id ?? verificationRunId,
|
|
1752
|
-
cachePublicationStatus: data.cache_publication_status,
|
|
1753
|
-
cachePublicationRetryEligible: data.cache_publication_retry_eligible,
|
|
1754
2000
|
suggestedAction: data.suggested_action,
|
|
1755
2001
|
raw: data
|
|
1756
2002
|
};
|
|
1757
2003
|
}
|
|
2004
|
+
function normalizeVerifyEmailStatus(value) {
|
|
2005
|
+
const status = String(value ?? "").trim().toLowerCase();
|
|
2006
|
+
if (status === "deliverable" || status === "accepted" || status === "verified") return "valid";
|
|
2007
|
+
if (status === "undeliverable" || status === "rejected") return "invalid";
|
|
2008
|
+
if ([
|
|
2009
|
+
"valid",
|
|
2010
|
+
"invalid",
|
|
2011
|
+
"catch_all",
|
|
2012
|
+
"role",
|
|
2013
|
+
"disposable",
|
|
2014
|
+
"unknown",
|
|
2015
|
+
"verifier_error",
|
|
2016
|
+
"malformed",
|
|
2017
|
+
"error"
|
|
2018
|
+
].includes(status)) return status;
|
|
2019
|
+
return "unknown";
|
|
2020
|
+
}
|
|
2021
|
+
function normalizeVerifyEmailRecommendation(value, verificationStatus, verifiedForSending) {
|
|
2022
|
+
const recommendation = String(value ?? "").trim().toLowerCase();
|
|
2023
|
+
if (recommendation === "send" || recommendation === "do_not_send" || recommendation === "manual_review") {
|
|
2024
|
+
return recommendation;
|
|
2025
|
+
}
|
|
2026
|
+
if (verifiedForSending) return "send";
|
|
2027
|
+
return verificationStatus === "unknown" || verificationStatus === "verifier_error" ? "manual_review" : "do_not_send";
|
|
2028
|
+
}
|
|
1758
2029
|
function companySignalRequestBody(params) {
|
|
1759
|
-
const online = params.online ?? true;
|
|
1760
2030
|
return compact({
|
|
1761
2031
|
signal_run_id: params.signalRunId,
|
|
1762
|
-
|
|
1763
|
-
company_name: params.companyName,
|
|
1764
|
-
research_prompt: params.researchPrompt,
|
|
1765
|
-
signal_types: params.signalTypes,
|
|
1766
|
-
target_signal_count: params.targetSignalCount,
|
|
1767
|
-
lookback_days: params.lookbackDays,
|
|
1768
|
-
online,
|
|
1769
|
-
enable_deep_search: params.enableDeepSearch ?? online,
|
|
1770
|
-
search_mode: params.searchMode ?? "balanced",
|
|
1771
|
-
include_summary: params.includeSummary,
|
|
1772
|
-
enable_outreach_intelligence: params.enableOutreachIntelligence,
|
|
1773
|
-
enable_predictive_intelligence: params.enablePredictiveIntelligence,
|
|
1774
|
-
skip_cache: params.skipCache,
|
|
1775
|
-
include_candidate_evidence: params.includeCandidateEvidence,
|
|
1776
|
-
wait_for_result: true,
|
|
1777
|
-
max_wait_ms: params.maxWaitMs,
|
|
2032
|
+
domain: params.domain ?? params.companyDomain,
|
|
1778
2033
|
dry_run: params.dryRun,
|
|
1779
2034
|
idempotency_key: params.idempotencyKey
|
|
1780
2035
|
});
|
|
1781
2036
|
}
|
|
1782
2037
|
function validateCompanySignalParams(params) {
|
|
1783
|
-
|
|
1784
|
-
|
|
1785
|
-
throw new RangeError("targetSignalCount must be an integer between 1 and 15");
|
|
2038
|
+
if (!params.signalRunId && !(params.domain ?? params.companyDomain)?.trim()) {
|
|
2039
|
+
throw new TypeError("Company Signals requires domain");
|
|
1786
2040
|
}
|
|
1787
2041
|
if (params.lookbackDays !== void 0 && (!Number.isInteger(params.lookbackDays) || params.lookbackDays < 1 || params.lookbackDays > 365)) {
|
|
1788
2042
|
throw new RangeError("lookbackDays must be an integer between 1 and 365");
|
|
@@ -1790,25 +2044,11 @@ function validateCompanySignalParams(params) {
|
|
|
1790
2044
|
}
|
|
1791
2045
|
function companySignalParamsFromRecoveredRow(row) {
|
|
1792
2046
|
return {
|
|
1793
|
-
|
|
1794
|
-
companyName: row.company?.name ?? row.company_name,
|
|
2047
|
+
domain: row.company?.domain ?? row.company_domain,
|
|
1795
2048
|
signalRunId: row.signal_run_id ?? row.run_id
|
|
1796
2049
|
};
|
|
1797
2050
|
}
|
|
1798
|
-
var COMPANY_SIGNAL_LARGE_BATCH_CONTROL_FIELDS = [
|
|
1799
|
-
"research_prompt",
|
|
1800
|
-
"signal_types",
|
|
1801
|
-
"target_signal_count",
|
|
1802
|
-
"lookback_days",
|
|
1803
|
-
"online",
|
|
1804
|
-
"enable_deep_search",
|
|
1805
|
-
"search_mode",
|
|
1806
|
-
"include_summary",
|
|
1807
|
-
"enable_outreach_intelligence",
|
|
1808
|
-
"enable_predictive_intelligence",
|
|
1809
|
-
"skip_cache",
|
|
1810
|
-
"include_candidate_evidence"
|
|
1811
|
-
];
|
|
2051
|
+
var COMPANY_SIGNAL_LARGE_BATCH_CONTROL_FIELDS = [];
|
|
1812
2052
|
function companySignalLargeBatchSubmission(requests) {
|
|
1813
2053
|
if (requests.length <= 25) return null;
|
|
1814
2054
|
if (requests.some(
|
|
@@ -1825,67 +2065,158 @@ function companySignalLargeBatchSubmission(requests) {
|
|
|
1825
2065
|
COMPANY_SIGNAL_LARGE_BATCH_CONTROL_FIELDS.filter((field) => request[field] !== void 0).map((field) => [field, request[field]])
|
|
1826
2066
|
);
|
|
1827
2067
|
if (JSON.stringify(requestControls) !== controlKey) return null;
|
|
1828
|
-
const hasIdentity = typeof request.
|
|
2068
|
+
const hasIdentity = typeof request.domain === "string" && request.domain.trim();
|
|
1829
2069
|
if (!hasIdentity) return null;
|
|
1830
2070
|
}
|
|
1831
2071
|
return {
|
|
1832
|
-
requests: requests.map((request) => compact({
|
|
1833
|
-
company_domain: request.company_domain,
|
|
1834
|
-
company_name: request.company_name
|
|
1835
|
-
})),
|
|
2072
|
+
requests: requests.map((request) => compact({ domain: request.domain })),
|
|
1836
2073
|
submissionFields
|
|
1837
2074
|
};
|
|
1838
2075
|
}
|
|
1839
2076
|
function normalizeCompanySignalResult(params, data) {
|
|
2077
|
+
data = publicProductData(data, "company_signals");
|
|
1840
2078
|
const failed = coreProductResponseFailed(data);
|
|
1841
2079
|
const rawSignals = failed ? [] : data.signals ?? data.signal_feed ?? [];
|
|
2080
|
+
const fallbackCompany = {
|
|
2081
|
+
name: data.company_name ?? data.company?.name ?? params.domain ?? params.companyDomain ?? null,
|
|
2082
|
+
domain: data.company_domain ?? data.domain ?? data.company?.domain ?? params.domain ?? params.companyDomain ?? null
|
|
2083
|
+
};
|
|
2084
|
+
const signalRows = publicCompanySignalRows(rawSignals, fallbackCompany);
|
|
2085
|
+
const company = {
|
|
2086
|
+
name: fallbackCompany.name ?? signalRows[0]?.company_name ?? null,
|
|
2087
|
+
domain: fallbackCompany.domain ?? signalRows[0]?.domain ?? null
|
|
2088
|
+
};
|
|
2089
|
+
const signals = signalRows.map(companySignalOutputRow);
|
|
1842
2090
|
return {
|
|
1843
2091
|
success: !failed,
|
|
1844
2092
|
error: failed ? coreProductErrorMessage(data) : void 0,
|
|
1845
2093
|
errorCode: failed ? coreProductErrorCode(data) : void 0,
|
|
1846
2094
|
status: data.status,
|
|
1847
2095
|
signalRunId: data.signal_run_id ?? data.run_id ?? params.signalRunId,
|
|
1848
|
-
company
|
|
1849
|
-
|
|
1850
|
-
|
|
1851
|
-
|
|
1852
|
-
|
|
1853
|
-
|
|
1854
|
-
|
|
1855
|
-
|
|
1856
|
-
|
|
1857
|
-
|
|
1858
|
-
|
|
1859
|
-
|
|
1860
|
-
|
|
1861
|
-
|
|
1862
|
-
|
|
1863
|
-
|
|
1864
|
-
|
|
1865
|
-
|
|
1866
|
-
|
|
1867
|
-
|
|
1868
|
-
|
|
1869
|
-
|
|
1870
|
-
|
|
1871
|
-
|
|
1872
|
-
|
|
1873
|
-
|
|
1874
|
-
|
|
1875
|
-
|
|
1876
|
-
|
|
1877
|
-
|
|
1878
|
-
|
|
1879
|
-
|
|
1880
|
-
|
|
1881
|
-
|
|
1882
|
-
|
|
1883
|
-
|
|
1884
|
-
|
|
1885
|
-
|
|
1886
|
-
|
|
1887
|
-
|
|
1888
|
-
|
|
2096
|
+
company,
|
|
2097
|
+
signals,
|
|
2098
|
+
signalCount: signals.length,
|
|
2099
|
+
creditsUsed: data.credits_used
|
|
2100
|
+
};
|
|
2101
|
+
}
|
|
2102
|
+
function companySignalOutputRow(row) {
|
|
2103
|
+
return {
|
|
2104
|
+
date: row.date,
|
|
2105
|
+
signal_type: row.signal_type,
|
|
2106
|
+
signal_title: row.signal_title,
|
|
2107
|
+
signal_summary: row.signal_summary,
|
|
2108
|
+
source: row.source
|
|
2109
|
+
};
|
|
2110
|
+
}
|
|
2111
|
+
function validateSignalizFlowParams(params) {
|
|
2112
|
+
const query = typeof params.signalQuery === "string" ? params.signalQuery.trim() : "";
|
|
2113
|
+
const offer = typeof params.campaignOffer === "string" ? params.campaignOffer.trim() : "";
|
|
2114
|
+
if (query.length < 2 || query.length > 2e3) throw new RangeError("signalQuery must contain between 2 and 2000 characters");
|
|
2115
|
+
if (!offer || offer.length > 4e3) throw new RangeError("campaignOffer must contain between 1 and 4000 characters");
|
|
2116
|
+
if (params.signalLimit !== void 0 && (!Number.isInteger(params.signalLimit) || params.signalLimit < 1 || params.signalLimit > 25)) {
|
|
2117
|
+
throw new RangeError("signalLimit must be an integer between 1 and 25");
|
|
2118
|
+
}
|
|
2119
|
+
if (params.peoplePerCompany !== void 0 && (!Number.isInteger(params.peoplePerCompany) || params.peoplePerCompany < 1 || params.peoplePerCompany > 5)) {
|
|
2120
|
+
throw new RangeError("peoplePerCompany must be an integer between 1 and 5");
|
|
2121
|
+
}
|
|
2122
|
+
if (params.lookbackDays !== void 0 && (!Number.isInteger(params.lookbackDays) || params.lookbackDays < 1 || params.lookbackDays > 365)) {
|
|
2123
|
+
throw new RangeError("lookbackDays must be an integer between 1 and 365");
|
|
2124
|
+
}
|
|
2125
|
+
if (params.peopleTitles !== void 0 && (!Array.isArray(params.peopleTitles) || params.peopleTitles.length > 20 || params.peopleTitles.some((title) => typeof title !== "string" || !title.trim()))) {
|
|
2126
|
+
throw new TypeError("peopleTitles must contain at most 20 non-empty titles");
|
|
2127
|
+
}
|
|
2128
|
+
}
|
|
2129
|
+
function signalizFlowRequestBody(params) {
|
|
2130
|
+
const requestedFlowId = typeof params.flowId === "string" ? params.flowId.trim() : "";
|
|
2131
|
+
const requestedIdempotencyKey = typeof params.idempotencyKey === "string" ? params.idempotencyKey.trim() : "";
|
|
2132
|
+
const flowId = requestedFlowId || requestedIdempotencyKey || `sdk-flow-${globalThis.crypto?.randomUUID?.() || `${Date.now()}-${Math.random().toString(16).slice(2)}`}`;
|
|
2133
|
+
const idempotencyKey = requestedIdempotencyKey || `signaliz-flow:${flowId}`;
|
|
2134
|
+
return compact({
|
|
2135
|
+
signal_query: params.signalQuery.trim(),
|
|
2136
|
+
campaign_offer: params.campaignOffer.trim(),
|
|
2137
|
+
signal_limit: params.signalLimit,
|
|
2138
|
+
lookback_days: params.lookbackDays,
|
|
2139
|
+
icp_context: params.icpContext?.trim(),
|
|
2140
|
+
people_titles: params.peopleTitles?.map((title) => title.trim()),
|
|
2141
|
+
people_per_company: params.peoplePerCompany,
|
|
2142
|
+
copy_research_prompt: params.copyResearchPrompt?.trim(),
|
|
2143
|
+
approval_required: params.approvalRequired,
|
|
2144
|
+
flow_id: flowId,
|
|
2145
|
+
idempotency_key: idempotencyKey,
|
|
2146
|
+
dry_run: params.dryRun
|
|
2147
|
+
});
|
|
2148
|
+
}
|
|
2149
|
+
function normalizeSignalizFlowPlan(data) {
|
|
2150
|
+
const plan = data.plan && typeof data.plan === "object" ? data.plan : {};
|
|
2151
|
+
const billing = plan.billing && typeof plan.billing === "object" ? plan.billing : {};
|
|
2152
|
+
return {
|
|
2153
|
+
plannedCompanyCount: Number(plan.planned_company_count ?? 0),
|
|
2154
|
+
plannedPeoplePerCompany: Number(plan.planned_people_per_company ?? 0),
|
|
2155
|
+
maximumReviewCandidates: Number(plan.maximum_review_candidates ?? 0),
|
|
2156
|
+
safeguards: Array.isArray(plan.safeguards) ? plan.safeguards.filter((value) => typeof value === "string") : [],
|
|
2157
|
+
billing: { additionalFlowFeeCredits: Number(billing.additional_flow_fee_credits ?? 0), chargeBasis: String(billing.charge_basis ?? "") }
|
|
2158
|
+
};
|
|
2159
|
+
}
|
|
2160
|
+
function normalizeSignalizFlowPlanResult(data) {
|
|
2161
|
+
if (data.success !== true) throw new Error(String(data.error || "Signaliz Flow plan is unavailable."));
|
|
2162
|
+
return { success: true, dryRun: true, status: "PLANNED", flowId: String(data.flow_id ?? ""), plan: normalizeSignalizFlowPlan(data), creditsCharged: 0 };
|
|
2163
|
+
}
|
|
2164
|
+
function normalizeSignalizFlowStartResult(data) {
|
|
2165
|
+
if (data.success !== true || typeof data.run_id !== "string" || !data.run_id.trim()) {
|
|
2166
|
+
throw new Error(String(data.error || "Signaliz Flow could not be started."));
|
|
2167
|
+
}
|
|
2168
|
+
return { success: true, flowId: String(data.flow_id ?? ""), runId: data.run_id, status: "TRIGGERED", statusEndpoint: "api/v1/flow", message: String(data.message ?? "") };
|
|
2169
|
+
}
|
|
2170
|
+
var FLOW_SIGNAL_LIST_KEYS = /* @__PURE__ */ new Set(["signals", "signal_feed", "company_signals", "signal_results"]);
|
|
2171
|
+
var FLOW_SINGLE_SIGNAL_KEYS = /* @__PURE__ */ new Set(["signal", "source_signal"]);
|
|
2172
|
+
function publicSignalizFlowResult(value) {
|
|
2173
|
+
if (Array.isArray(value)) return value.map(publicSignalizFlowResult);
|
|
2174
|
+
if (!value || typeof value !== "object") return value;
|
|
2175
|
+
const source = value;
|
|
2176
|
+
return Object.fromEntries(Object.entries(source).flatMap(([key, raw]) => {
|
|
2177
|
+
const normalizedKey = key.toLowerCase();
|
|
2178
|
+
if (normalizedKey === "raw" || normalizedKey === "raw_data") return [];
|
|
2179
|
+
if (FLOW_SIGNAL_LIST_KEYS.has(normalizedKey)) {
|
|
2180
|
+
return [[key, oneSignalPerCompany(publicSignalRows(raw))]];
|
|
2181
|
+
}
|
|
2182
|
+
if (FLOW_SINGLE_SIGNAL_KEYS.has(normalizedKey)) {
|
|
2183
|
+
const row = publicSignalRow(raw);
|
|
2184
|
+
return row ? [[key, row]] : [];
|
|
2185
|
+
}
|
|
2186
|
+
return [[key, publicSignalizFlowResult(raw)]];
|
|
2187
|
+
}));
|
|
2188
|
+
}
|
|
2189
|
+
function normalizeSignalizFlowBilling(value) {
|
|
2190
|
+
if (!value || typeof value !== "object") return void 0;
|
|
2191
|
+
const billing = value;
|
|
2192
|
+
return {
|
|
2193
|
+
creditsCharged: Number(billing.credits_charged ?? 0),
|
|
2194
|
+
billingStatus: billing.billing_status === "charged" ? "charged" : "included_or_waived",
|
|
2195
|
+
chargeBasis: String(billing.charge_basis ?? ""),
|
|
2196
|
+
receipt: Array.isArray(billing.receipt) ? billing.receipt.map((line) => ({
|
|
2197
|
+
capability: line.capability,
|
|
2198
|
+
successfulResults: Number(line.successful_results ?? 0),
|
|
2199
|
+
creditsCharged: Number(line.credits_charged ?? 0)
|
|
2200
|
+
})).filter((line) => ["company_signals", "find_email", "signal_to_copy"].includes(line.capability)) : []
|
|
2201
|
+
};
|
|
2202
|
+
}
|
|
2203
|
+
function normalizeSignalizFlowStatus(data) {
|
|
2204
|
+
if (data.success !== true || typeof data.run_id !== "string" || !data.run_id.trim()) {
|
|
2205
|
+
throw new Error(String(data.error || "Signaliz Flow status is unavailable."));
|
|
2206
|
+
}
|
|
2207
|
+
const publicData = publicProductData(data, "signaliz_flow");
|
|
2208
|
+
const result = publicData.result && typeof publicData.result === "object" ? publicSignalizFlowResult(publicData.result) : {};
|
|
2209
|
+
const billing = normalizeSignalizFlowBilling(result.billing);
|
|
2210
|
+
if (billing) result.billing = billing;
|
|
2211
|
+
const status = String(publicData.status || "").toLowerCase();
|
|
2212
|
+
return {
|
|
2213
|
+
success: true,
|
|
2214
|
+
runId: String(publicData.run_id),
|
|
2215
|
+
status: status === "completed" || status === "failed" ? status : "running",
|
|
2216
|
+
result,
|
|
2217
|
+
createdAt: typeof publicData.created_at === "string" ? publicData.created_at : void 0,
|
|
2218
|
+
updatedAt: typeof publicData.updated_at === "string" ? publicData.updated_at : void 0,
|
|
2219
|
+
completedAt: typeof publicData.completed_at === "string" ? publicData.completed_at : void 0
|
|
1889
2220
|
};
|
|
1890
2221
|
}
|
|
1891
2222
|
var SIGNAL_DISCOVERY_SOURCES = /* @__PURE__ */ new Set(["web", "news"]);
|
|
@@ -1918,10 +2249,32 @@ function validateSignalDiscoveryParams(params) {
|
|
|
1918
2249
|
if (params.lookbackDays !== void 0 && (!Number.isInteger(params.lookbackDays) || params.lookbackDays < 1 || params.lookbackDays > 365)) {
|
|
1919
2250
|
throw new RangeError("lookbackDays must be an integer between 1 and 365");
|
|
1920
2251
|
}
|
|
2252
|
+
validateSignalDateWindow(params);
|
|
1921
2253
|
if (params.sources !== void 0 && (!Array.isArray(params.sources) || params.sources.length < 1 || params.sources.length > 2 || params.sources.some((source) => !SIGNAL_DISCOVERY_SOURCES.has(source)))) {
|
|
1922
2254
|
throw new TypeError("sources must contain only web or news");
|
|
1923
2255
|
}
|
|
1924
2256
|
}
|
|
2257
|
+
function validateSignalDateWindow(params) {
|
|
2258
|
+
const afterDate = params.afterDate?.trim();
|
|
2259
|
+
const beforeDate = params.beforeDate?.trim();
|
|
2260
|
+
if ((afterDate || beforeDate) && params.lookbackDays !== void 0) {
|
|
2261
|
+
throw new RangeError("afterDate/beforeDate cannot be combined with lookbackDays");
|
|
2262
|
+
}
|
|
2263
|
+
const parseDate = (value, field) => {
|
|
2264
|
+
if (value === void 0) return void 0;
|
|
2265
|
+
if (!/^\d{4}-\d{2}-\d{2}$/.test(value)) throw new RangeError(`${field} must use YYYY-MM-DD format`);
|
|
2266
|
+
const timestamp = Date.parse(`${value}T00:00:00Z`);
|
|
2267
|
+
if (!Number.isFinite(timestamp) || new Date(timestamp).toISOString().slice(0, 10) !== value) {
|
|
2268
|
+
throw new RangeError(`${field} must be a valid calendar date`);
|
|
2269
|
+
}
|
|
2270
|
+
return timestamp;
|
|
2271
|
+
};
|
|
2272
|
+
const afterTimestamp = parseDate(afterDate, "afterDate");
|
|
2273
|
+
const beforeTimestamp = parseDate(beforeDate, "beforeDate");
|
|
2274
|
+
if (afterTimestamp !== void 0 && beforeTimestamp !== void 0 && beforeTimestamp < afterTimestamp) {
|
|
2275
|
+
throw new RangeError("beforeDate must be on or after afterDate");
|
|
2276
|
+
}
|
|
2277
|
+
}
|
|
1925
2278
|
function signalDiscoveryRequestBody(params) {
|
|
1926
2279
|
const runId = typeof params.signalSearchRunId === "string" ? params.signalSearchRunId.trim() : "";
|
|
1927
2280
|
if (runId) {
|
|
@@ -1930,6 +2283,8 @@ function signalDiscoveryRequestBody(params) {
|
|
|
1930
2283
|
// An explicit limit expands or narrows the retained qualified cohort;
|
|
1931
2284
|
// omitting it preserves the original preview size.
|
|
1932
2285
|
limit: params.limit,
|
|
2286
|
+
after_date: params.afterDate?.trim(),
|
|
2287
|
+
before_date: params.beforeDate?.trim(),
|
|
1933
2288
|
dry_run: params.dryRun,
|
|
1934
2289
|
idempotency_key: params.idempotencyKey
|
|
1935
2290
|
});
|
|
@@ -1940,6 +2295,8 @@ function signalDiscoveryRequestBody(params) {
|
|
|
1940
2295
|
limit: params.limit ?? 100,
|
|
1941
2296
|
sources: params.sources,
|
|
1942
2297
|
lookback_days: params.lookbackDays,
|
|
2298
|
+
after_date: params.afterDate?.trim(),
|
|
2299
|
+
before_date: params.beforeDate?.trim(),
|
|
1943
2300
|
dry_run: params.dryRun,
|
|
1944
2301
|
idempotency_key: params.idempotencyKey
|
|
1945
2302
|
});
|
|
@@ -1948,106 +2305,25 @@ function normalizeSignalDiscoveryResult(params, data) {
|
|
|
1948
2305
|
const rawSignals = Array.isArray(data.signals) ? data.signals : [];
|
|
1949
2306
|
const rawStatus = String(data.status || "").toLowerCase();
|
|
1950
2307
|
const status = SIGNAL_DISCOVERY_STATUSES.has(rawStatus) ? rawStatus : rawSignals.length > 0 ? "completed" : "failed";
|
|
1951
|
-
const
|
|
2308
|
+
const requestedCount = Number(data.requested_count ?? params.limit);
|
|
2309
|
+
const signals = oneSignalPerCompany(publicSignalRows(rawSignals)).slice(
|
|
2310
|
+
0,
|
|
2311
|
+
Number.isFinite(requestedCount) && requestedCount > 0 ? requestedCount : void 0
|
|
2312
|
+
);
|
|
1952
2313
|
return {
|
|
1953
2314
|
success: data.success !== false,
|
|
1954
2315
|
status,
|
|
1955
2316
|
capability: "signals_everything",
|
|
1956
2317
|
signalSearchRunId: String(data.signal_search_run_id ?? params.signalSearchRunId ?? ""),
|
|
1957
2318
|
query: String(data.query ?? params.query ?? ""),
|
|
1958
|
-
|
|
2319
|
+
...Number.isFinite(requestedCount) && requestedCount > 0 ? { requestedCount } : {},
|
|
1959
2320
|
nextPollAfterSeconds: typeof data.next_poll_after_seconds === "number" ? data.next_poll_after_seconds : void 0,
|
|
1960
2321
|
signals,
|
|
1961
2322
|
signalCount: signals.length,
|
|
1962
|
-
|
|
1963
|
-
|
|
1964
|
-
|
|
1965
|
-
|
|
1966
|
-
identityResolution: data.identity_resolution && typeof data.identity_resolution === "object" ? data.identity_resolution : void 0,
|
|
1967
|
-
costGuardrail: normalizeSignalDiscoveryCostGuardrail(data.cost_guardrail),
|
|
1968
|
-
warnings: Array.isArray(data.warnings) ? data.warnings.filter((warning) => typeof warning === "string") : void 0,
|
|
1969
|
-
raw: data
|
|
1970
|
-
};
|
|
1971
|
-
}
|
|
1972
|
-
function normalizeSignalDiscoveryCostGuardrail(value) {
|
|
1973
|
-
if (!value || typeof value !== "object" || Array.isArray(value)) return void 0;
|
|
1974
|
-
const guardrail = value;
|
|
1975
|
-
const maxCost = Number(guardrail.max_cost_per_qualified_signal_usd);
|
|
1976
|
-
const withinLimit = guardrail.within_limit === true;
|
|
1977
|
-
if (!Number.isFinite(maxCost)) return void 0;
|
|
1978
|
-
const numberOrNullable = (candidate) => {
|
|
1979
|
-
if (candidate === null) return null;
|
|
1980
|
-
const numeric = Number(candidate);
|
|
1981
|
-
return Number.isFinite(numeric) ? numeric : void 0;
|
|
1982
|
-
};
|
|
1983
|
-
const numberOrUndefined = (candidate) => {
|
|
1984
|
-
const numeric = Number(candidate);
|
|
1985
|
-
return Number.isFinite(numeric) ? numeric : void 0;
|
|
1986
|
-
};
|
|
1987
|
-
return {
|
|
1988
|
-
maxCostPerQualifiedSignalUsd: maxCost,
|
|
1989
|
-
projectedSourceCostUsd: numberOrNullable(guardrail.projected_source_cost_usd),
|
|
1990
|
-
maxSourceCostUsd: numberOrNullable(guardrail.max_source_cost_usd),
|
|
1991
|
-
projectedCostPerRequestedCompanySignalUsd: numberOrNullable(
|
|
1992
|
-
guardrail.projected_cost_per_requested_company_signal_usd
|
|
1993
|
-
),
|
|
1994
|
-
sourceCostUsd: numberOrNullable(guardrail.source_cost_usd),
|
|
1995
|
-
costSource: ["observed", "catalog_preflight", "catalog_bounded", "mixed", "unavailable"].includes(String(guardrail.cost_source)) ? String(guardrail.cost_source) : void 0,
|
|
1996
|
-
identityResolutionCostUsd: numberOrNullable(guardrail.identity_resolution_cost_usd),
|
|
1997
|
-
identityCostSource: [
|
|
1998
|
-
"observed_zero_credit_receipts",
|
|
1999
|
-
"contractual_zero_cost",
|
|
2000
|
-
"not_used",
|
|
2001
|
-
"unavailable"
|
|
2002
|
-
].includes(String(guardrail.identity_cost_source)) ? String(guardrail.identity_cost_source) : void 0,
|
|
2003
|
-
identityProviderRequests: numberOrUndefined(guardrail.identity_provider_requests),
|
|
2004
|
-
qualifiedCompanySignalCount: numberOrUndefined(guardrail.qualified_company_signal_count),
|
|
2005
|
-
returnedCompanySignalCount: numberOrUndefined(guardrail.returned_company_signal_count),
|
|
2006
|
-
availableCompanySignalCount: numberOrUndefined(guardrail.available_company_signal_count),
|
|
2007
|
-
acquisitionCandidateLimit: numberOrUndefined(guardrail.acquisition_candidate_limit),
|
|
2008
|
-
minimumQualifiedCompanySignals: numberOrUndefined(guardrail.minimum_qualified_company_signals),
|
|
2009
|
-
costPerQualifiedSignalUsd: numberOrNullable(guardrail.cost_per_qualified_signal_usd),
|
|
2010
|
-
withinLimit
|
|
2011
|
-
};
|
|
2012
|
-
}
|
|
2013
|
-
function normalizeSignalDiscoverySignal(value) {
|
|
2014
|
-
const signal = value && typeof value === "object" && !Array.isArray(value) ? value : {};
|
|
2015
|
-
const company = signal.company && typeof signal.company === "object" && !Array.isArray(signal.company) ? signal.company : {};
|
|
2016
|
-
const companyName = String(company.name ?? signal.company_name ?? "").trim();
|
|
2017
|
-
const companyDomain = String(company.domain ?? signal.company_domain ?? "").trim();
|
|
2018
|
-
if (!companyName || !companyDomain) {
|
|
2019
|
-
throw new Error("Signals Everything response violated the company attribution contract.");
|
|
2020
|
-
}
|
|
2021
|
-
const eventDate = String(signal.event_date ?? signal.date ?? signal.signal_date ?? "").trim();
|
|
2022
|
-
const sourceUrl = String(signal.source_url ?? signal.url ?? "").trim();
|
|
2023
|
-
const evidence = Array.isArray(signal.evidence) ? signal.evidence.map((item) => ({
|
|
2024
|
-
url: String(item?.url ?? "").trim(),
|
|
2025
|
-
publishedAt: String(item?.published_at ?? item?.publishedAt ?? "").trim(),
|
|
2026
|
-
source: String(item?.source ?? "").trim()
|
|
2027
|
-
})).filter((item) => Boolean(item.url)) : [];
|
|
2028
|
-
if (!eventDate || !sourceUrl || !evidence.some((item) => item.url === sourceUrl && item.publishedAt === eventDate)) {
|
|
2029
|
-
throw new Error("Signals Everything response violated the dated-evidence and source-URL contract.");
|
|
2030
|
-
}
|
|
2031
|
-
return {
|
|
2032
|
-
id: signal.id,
|
|
2033
|
-
company: {
|
|
2034
|
-
name: companyName,
|
|
2035
|
-
domain: companyDomain,
|
|
2036
|
-
linkedinUrl: company.linkedin_url ?? signal.company_linkedin_url ?? void 0
|
|
2037
|
-
},
|
|
2038
|
-
title: signal.title ?? "",
|
|
2039
|
-
type: signal.type ?? signal.signal_type ?? "unknown",
|
|
2040
|
-
summary: signal.summary ?? signal.content ?? signal.description ?? "",
|
|
2041
|
-
eventDate,
|
|
2042
|
-
evidence,
|
|
2043
|
-
content: signal.summary ?? signal.content ?? signal.description ?? "",
|
|
2044
|
-
date: signal.event_date ?? signal.date ?? signal.signal_date ?? null,
|
|
2045
|
-
detectedAt: signal.event_date ?? signal.detected_at ?? null,
|
|
2046
|
-
sourceUrl,
|
|
2047
|
-
sourceType: signal.source_type ?? null,
|
|
2048
|
-
confidence: signal.confidence ?? signal.confidence_score ?? null,
|
|
2049
|
-
classification: signal.signal_classification ?? signal.classification ?? null,
|
|
2050
|
-
raw: signal
|
|
2323
|
+
creditsUsed: Number.isFinite(Number(data.credits_used)) ? Number(data.credits_used) : 0,
|
|
2324
|
+
creditsCharged: Number.isFinite(Number(data.credits_charged)) ? Number(data.credits_charged) : 0,
|
|
2325
|
+
billingStatus: data.billing_status === "included" ? "included" : void 0,
|
|
2326
|
+
idempotencyReplayed: typeof data.idempotency_replayed === "boolean" ? data.idempotency_replayed : void 0
|
|
2051
2327
|
};
|
|
2052
2328
|
}
|
|
2053
2329
|
function validateBatchSize(items) {
|
|
@@ -2101,9 +2377,6 @@ function normalizedBatchDomain(value) {
|
|
|
2101
2377
|
function normalizedBatchLinkedIn(value) {
|
|
2102
2378
|
return normalizedBatchText(value).replace(/\/+$/, "");
|
|
2103
2379
|
}
|
|
2104
|
-
function normalizedBatchList(value) {
|
|
2105
|
-
return Array.isArray(value) ? value.map(normalizedBatchText).filter(Boolean).sort() : [];
|
|
2106
|
-
}
|
|
2107
2380
|
function normalizedFindEmailBatchName(request) {
|
|
2108
2381
|
const fullName = normalizedBatchText(request.full_name);
|
|
2109
2382
|
const componentName = [normalizedBatchText(request.first_name), normalizedBatchText(request.last_name)].filter(Boolean).join(" ");
|
|
@@ -2118,39 +2391,24 @@ function coreProductBatchRequestKey(path2, request) {
|
|
|
2118
2391
|
normalizedBatchDomain(request.company_domain),
|
|
2119
2392
|
normalizedBatchLinkedIn(request.linkedin_url),
|
|
2120
2393
|
normalizedBatchText(request.company_name),
|
|
2121
|
-
request.skip_cache === true || request.bypass_cache === true,
|
|
2122
2394
|
normalizedBatchIdempotencyKey(request.idempotency_key)
|
|
2123
2395
|
]);
|
|
2124
2396
|
}
|
|
2125
2397
|
if (path2 === "api/v1/verify-email") {
|
|
2126
2398
|
return JSON.stringify([
|
|
2127
2399
|
normalizedBatchText(request.email),
|
|
2128
|
-
request.skip_cache === true || request.bypass_cache === true,
|
|
2129
2400
|
request.skip_catch_all_verification === true,
|
|
2130
2401
|
request.skip_esp_check === true,
|
|
2131
2402
|
normalizedBatchIdempotencyKey(request.idempotency_key)
|
|
2132
2403
|
]);
|
|
2133
2404
|
}
|
|
2134
2405
|
if (path2 === "api/v1/company-signals") {
|
|
2135
|
-
const online = request.online !== false;
|
|
2136
|
-
const deepSearch = request.enable_deep_search === void 0 ? online : request.enable_deep_search !== false;
|
|
2137
2406
|
return JSON.stringify([
|
|
2138
2407
|
normalizedBatchText(request.signal_run_id),
|
|
2139
2408
|
normalizedBatchDomain(request.company_domain || request.domain),
|
|
2140
2409
|
normalizedBatchText(request.company_name),
|
|
2141
|
-
normalizedBatchText(request.company_id),
|
|
2142
|
-
normalizedBatchLinkedIn(request.linkedin_url),
|
|
2143
|
-
normalizedBatchText(request.industry),
|
|
2144
2410
|
typeof request.research_prompt === "string" ? request.research_prompt.trim() : "",
|
|
2145
|
-
normalizedBatchList(request.signal_types),
|
|
2146
|
-
Number(request.target_signal_count) || null,
|
|
2147
2411
|
Number(request.lookback_days) || null,
|
|
2148
|
-
online,
|
|
2149
|
-
deepSearch,
|
|
2150
|
-
normalizedBatchText(request.search_mode || "balanced"),
|
|
2151
|
-
request.enable_outreach_intelligence === true,
|
|
2152
|
-
request.enable_predictive_intelligence === true,
|
|
2153
|
-
request.skip_cache === true || request.bypass_cache === true,
|
|
2154
2412
|
normalizedBatchIdempotencyKey(request.idempotency_key)
|
|
2155
2413
|
]);
|
|
2156
2414
|
}
|
|
@@ -2160,9 +2418,12 @@ function coreProductBatchRequestKey(path2, request) {
|
|
|
2160
2418
|
typeof request.title === "string" ? request.title.trim() : "",
|
|
2161
2419
|
typeof request.campaign_offer === "string" ? request.campaign_offer.trim() : "",
|
|
2162
2420
|
typeof request.research_prompt === "string" ? request.research_prompt.trim() : "",
|
|
2421
|
+
normalizedBatchText(request.copy_evidence_mode),
|
|
2163
2422
|
Number(request.lookback_days) || null,
|
|
2164
2423
|
typeof request.signal_run_id === "string" ? request.signal_run_id.trim() : "",
|
|
2165
|
-
request.
|
|
2424
|
+
typeof request.signal_search_run_id === "string" ? request.signal_search_run_id.trim() : "",
|
|
2425
|
+
typeof request.fact_id === "string" ? request.fact_id.trim() : "",
|
|
2426
|
+
typeof request.event_id === "string" ? request.event_id.trim() : "",
|
|
2166
2427
|
request.enable_deep_search === true,
|
|
2167
2428
|
normalizedBatchIdempotencyKey(request.idempotency_key)
|
|
2168
2429
|
]);
|
|
@@ -2267,43 +2528,60 @@ function signalToCopyRequestBody(params) {
|
|
|
2267
2528
|
person_name: params.personName,
|
|
2268
2529
|
title: params.title,
|
|
2269
2530
|
campaign_offer: params.campaignOffer,
|
|
2270
|
-
|
|
2271
|
-
lookback_days:
|
|
2531
|
+
copy_evidence_mode: params.copyEvidenceMode,
|
|
2532
|
+
lookback_days: 365,
|
|
2272
2533
|
signal_run_id: params.signalRunId,
|
|
2273
|
-
|
|
2534
|
+
signal_search_run_id: params.signalSearchRunId,
|
|
2535
|
+
fact_id: params.factId,
|
|
2536
|
+
event_id: params.eventId,
|
|
2274
2537
|
enable_deep_search: params.enableDeepSearch,
|
|
2275
2538
|
max_wait_ms: params.maxWaitMs,
|
|
2276
2539
|
dry_run: params.dryRun,
|
|
2277
2540
|
idempotency_key: params.idempotencyKey
|
|
2278
2541
|
});
|
|
2279
2542
|
}
|
|
2280
|
-
function
|
|
2543
|
+
function validateLargeSignalCopyBatch(requests) {
|
|
2281
2544
|
if (requests.length <= 25) return;
|
|
2282
2545
|
const invalidIndex = requests.findIndex(
|
|
2283
|
-
(request) =>
|
|
2546
|
+
(request) => Boolean(request.idempotencyKey?.trim()) || request.maxWaitMs !== void 0 || request.pollIntervalMs !== void 0 || request.waitForResult === false || Boolean(request.signalSearchRunId?.trim()) || Boolean(request.factId?.trim()) || Boolean(request.eventId?.trim()) || !request.companyDomain?.trim() || !request.personName?.trim() || !request.title?.trim() || !request.campaignOffer?.trim()
|
|
2284
2547
|
);
|
|
2285
2548
|
if (invalidIndex >= 0) {
|
|
2286
2549
|
throw new RangeError(
|
|
2287
|
-
`Signal to Copy
|
|
2550
|
+
`Signal to Copy batch row ${invalidIndex} uses canonical references (supported only in synchronous batches of 25 or fewer), uses unsupported row-level execution controls, or lacks required recipient fields. Put wait and idempotency controls in the batch options.`
|
|
2288
2551
|
);
|
|
2289
2552
|
}
|
|
2290
2553
|
}
|
|
2291
|
-
function
|
|
2554
|
+
function durableSignalCopyRequestBody(params) {
|
|
2292
2555
|
return compact({
|
|
2293
2556
|
company_domain: params.companyDomain,
|
|
2294
2557
|
person_name: params.personName,
|
|
2295
2558
|
title: params.title,
|
|
2296
2559
|
campaign_offer: params.campaignOffer,
|
|
2297
|
-
|
|
2298
|
-
lookback_days:
|
|
2299
|
-
signal_run_id: params.signalRunId
|
|
2560
|
+
copy_evidence_mode: params.copyEvidenceMode,
|
|
2561
|
+
lookback_days: 365,
|
|
2562
|
+
signal_run_id: params.signalRunId,
|
|
2563
|
+
signal_search_run_id: params.signalSearchRunId,
|
|
2564
|
+
fact_id: params.factId,
|
|
2565
|
+
event_id: params.eventId,
|
|
2566
|
+
enable_deep_search: params.enableDeepSearch
|
|
2300
2567
|
});
|
|
2301
2568
|
}
|
|
2302
2569
|
function validateSignalToCopyParams(params) {
|
|
2303
2570
|
validateCoreProductMaxWaitMs(params.maxWaitMs);
|
|
2571
|
+
if (params.copyEvidenceMode !== void 0 && !["signal_led", "firmographic"].includes(params.copyEvidenceMode)) {
|
|
2572
|
+
throw new RangeError("copyEvidenceMode must be signal_led or firmographic");
|
|
2573
|
+
}
|
|
2304
2574
|
if (params.lookbackDays !== void 0 && (!Number.isInteger(params.lookbackDays) || params.lookbackDays < 1 || params.lookbackDays > 365)) {
|
|
2305
2575
|
throw new RangeError("lookbackDays must be an integer between 1 and 365");
|
|
2306
2576
|
}
|
|
2577
|
+
if (params.signalSearchRunId !== void 0 && !params.signalSearchRunId.trim()) {
|
|
2578
|
+
throw new TypeError("signalSearchRunId must be a non-empty string");
|
|
2579
|
+
}
|
|
2580
|
+
for (const [field, value] of [["factId", params.factId], ["eventId", params.eventId]]) {
|
|
2581
|
+
if (value !== void 0 && !/^[0-9a-f]{64}$/.test(value.trim())) {
|
|
2582
|
+
throw new TypeError(`${field} must be a lowercase 64-character SHA-256 identifier`);
|
|
2583
|
+
}
|
|
2584
|
+
}
|
|
2307
2585
|
if (typeof params.signalRunId === "string" && params.signalRunId.trim()) return;
|
|
2308
2586
|
const missing = [
|
|
2309
2587
|
["companyDomain", params.companyDomain],
|
|
@@ -2322,6 +2600,7 @@ function validateCoreProductMaxWaitMs(value) {
|
|
|
2322
2600
|
}
|
|
2323
2601
|
}
|
|
2324
2602
|
function normalizeSignalToCopyResult(data) {
|
|
2603
|
+
data = publicProductData(data, "signal_to_copy");
|
|
2325
2604
|
const failed = coreProductResponseFailed(data);
|
|
2326
2605
|
return {
|
|
2327
2606
|
success: !failed,
|
|
@@ -2330,6 +2609,11 @@ function normalizeSignalToCopyResult(data) {
|
|
|
2330
2609
|
status: data.status,
|
|
2331
2610
|
runId: data.run_id ?? data.signal_run_id,
|
|
2332
2611
|
companySignalRunId: data.company_signal_run_id,
|
|
2612
|
+
signalSearchRunId: data.signal_search_run_id,
|
|
2613
|
+
factId: data.fact_id,
|
|
2614
|
+
eventId: data.event_id,
|
|
2615
|
+
canonicalSourceUrl: data.canonical_source_url,
|
|
2616
|
+
evidenceReuse: data.evidence_reuse,
|
|
2333
2617
|
resumeContextPersisted: data.resume_context_persisted,
|
|
2334
2618
|
strongestSignal: failed ? "" : data.strongest_signal ?? "",
|
|
2335
2619
|
whyNow: failed ? "" : data.why_now ?? "",
|
|
@@ -2338,17 +2622,11 @@ function normalizeSignalToCopyResult(data) {
|
|
|
2338
2622
|
confidence: failed ? 0 : data.confidence ?? 0,
|
|
2339
2623
|
evidenceUrl: failed ? "" : data.evidence_url ?? "",
|
|
2340
2624
|
researchPrompt: data.research_prompt,
|
|
2625
|
+
copyEvidenceMode: data.copy_evidence_mode,
|
|
2341
2626
|
empty: data.empty,
|
|
2342
2627
|
emptyReason: data.empty_reason,
|
|
2343
2628
|
researchMetadata: failed ? void 0 : data.research_metadata,
|
|
2344
|
-
billingMetadata: data.billing_metadata,
|
|
2345
|
-
resultReturnedFrom: data.result_returned_from,
|
|
2346
|
-
cacheHit: data.cache_hit,
|
|
2347
|
-
freshEnrichmentUsed: data.fresh_enrichment_used,
|
|
2348
2629
|
creditsUsed: data.credits_used,
|
|
2349
|
-
liveProviderCalled: data.live_provider_called,
|
|
2350
|
-
aiProviderCalled: data.ai_provider_called,
|
|
2351
|
-
byoAiUsed: data.byo_ai_used,
|
|
2352
2630
|
unlimitedSignalToCopy: data.unlimited_signal_to_copy,
|
|
2353
2631
|
signalToCopyEntitlement: data.signal_to_copy_entitlement,
|
|
2354
2632
|
variations: (failed ? [] : data.variations ?? []).map((variation) => ({
|
|
@@ -2362,6 +2640,117 @@ function normalizeSignalToCopyResult(data) {
|
|
|
2362
2640
|
raw: data
|
|
2363
2641
|
};
|
|
2364
2642
|
}
|
|
2643
|
+
function signalAwarenessMonitorRequest(monitor) {
|
|
2644
|
+
return compact({
|
|
2645
|
+
company_name: monitor.companyName,
|
|
2646
|
+
domain: monitor.domain,
|
|
2647
|
+
template: monitor.template,
|
|
2648
|
+
signal_config: monitor.signalConfig,
|
|
2649
|
+
schedule_cron: monitor.scheduleCron,
|
|
2650
|
+
webhook_url: monitor.webhookUrl
|
|
2651
|
+
});
|
|
2652
|
+
}
|
|
2653
|
+
function signalAwarenessRequestBody(request) {
|
|
2654
|
+
return compact({
|
|
2655
|
+
action: request.action,
|
|
2656
|
+
monitor_id: request.monitorId,
|
|
2657
|
+
monitor: request.monitor ? signalAwarenessMonitorRequest(request.monitor) : void 0,
|
|
2658
|
+
monitors: request.monitors?.map(signalAwarenessMonitorRequest),
|
|
2659
|
+
defaults: request.defaults,
|
|
2660
|
+
updates: request.updates,
|
|
2661
|
+
limit: request.limit,
|
|
2662
|
+
offset: request.offset,
|
|
2663
|
+
idempotency_key: request.idempotencyKey,
|
|
2664
|
+
dry_run: request.dryRun
|
|
2665
|
+
});
|
|
2666
|
+
}
|
|
2667
|
+
function normalizeSignalAwarenessResponse(data) {
|
|
2668
|
+
const payload = data.data && typeof data.data === "object" ? data.data : data;
|
|
2669
|
+
const signals = Array.isArray(payload.signals) ? oneSignalPerCompany(payload.signals.flatMap(normalizeSignalAwarenessSignal)) : void 0;
|
|
2670
|
+
const monitors = Array.isArray(payload.monitors) ? payload.monitors.map(normalizeSignalAwarenessMonitor).filter((value) => value !== void 0) : void 0;
|
|
2671
|
+
const monitor = normalizeSignalAwarenessMonitor(payload.monitor);
|
|
2672
|
+
const run = normalizeSignalAwarenessRun(payload.run);
|
|
2673
|
+
const billing = payload.billing && typeof payload.billing === "object" ? payload.billing : {};
|
|
2674
|
+
const creditsUsed = Number(payload.credits_used ?? billing.credits_used);
|
|
2675
|
+
return {
|
|
2676
|
+
success: data.success !== false,
|
|
2677
|
+
...monitors ? { monitors } : {},
|
|
2678
|
+
...monitor ? { monitor } : {},
|
|
2679
|
+
...signals ? { signals } : {},
|
|
2680
|
+
...signals ? { signalCount: signals.length } : {},
|
|
2681
|
+
...typeof payload.monitor_id === "string" ? { monitorId: payload.monitor_id } : {},
|
|
2682
|
+
...typeof payload.run_id === "string" ? { runId: payload.run_id } : {},
|
|
2683
|
+
...run ? { run } : {},
|
|
2684
|
+
...Number.isInteger(creditsUsed) && creditsUsed >= 0 ? { creditsUsed } : {},
|
|
2685
|
+
...Number.isFinite(Number(payload.created)) ? { created: Number(payload.created) } : {},
|
|
2686
|
+
...Number.isFinite(Number(payload.skipped)) ? { skipped: Number(payload.skipped) } : {},
|
|
2687
|
+
...Number.isFinite(Number(payload.total)) ? { total: Number(payload.total) } : {},
|
|
2688
|
+
...Number.isFinite(Number(payload.limit)) ? { limit: Number(payload.limit) } : {},
|
|
2689
|
+
...Number.isFinite(Number(payload.offset)) ? { offset: Number(payload.offset) } : {},
|
|
2690
|
+
...typeof payload.has_more === "boolean" ? { hasMore: payload.has_more } : {},
|
|
2691
|
+
...payload.idempotent_replay === true ? { idempotentReplay: true } : {}
|
|
2692
|
+
};
|
|
2693
|
+
}
|
|
2694
|
+
function signalAwarenessRecord(value) {
|
|
2695
|
+
return value && typeof value === "object" && !Array.isArray(value) ? value : {};
|
|
2696
|
+
}
|
|
2697
|
+
function signalAwarenessText(value, maximum = 500) {
|
|
2698
|
+
return typeof value === "string" && value.trim() && value.trim().length <= maximum ? value.trim() : void 0;
|
|
2699
|
+
}
|
|
2700
|
+
function signalAwarenessCount(value) {
|
|
2701
|
+
const numeric = Number(value);
|
|
2702
|
+
return Number.isInteger(numeric) && numeric >= 0 ? numeric : void 0;
|
|
2703
|
+
}
|
|
2704
|
+
function normalizeSignalAwarenessMonitor(value) {
|
|
2705
|
+
const monitor = signalAwarenessRecord(value);
|
|
2706
|
+
const result = {};
|
|
2707
|
+
const id = signalAwarenessText(monitor.id, 200);
|
|
2708
|
+
const companyName = signalAwarenessText(monitor.company_name, 300);
|
|
2709
|
+
const domain = signalAwarenessText(monitor.domain, 253);
|
|
2710
|
+
const status = signalAwarenessText(monitor.status, 80);
|
|
2711
|
+
const schedule = signalAwarenessText(monitor.schedule, 120);
|
|
2712
|
+
if (id) result.id = id;
|
|
2713
|
+
if (companyName) result.company_name = companyName;
|
|
2714
|
+
if (domain) result.domain = domain;
|
|
2715
|
+
if (status) result.status = status;
|
|
2716
|
+
if (schedule) result.schedule = schedule;
|
|
2717
|
+
for (const key of ["last_run_at", "next_run_at", "created_at", "updated_at"]) {
|
|
2718
|
+
const timestamp = signalAwarenessText(monitor[key], 64);
|
|
2719
|
+
if (timestamp && Number.isFinite(Date.parse(timestamp))) result[key] = timestamp;
|
|
2720
|
+
}
|
|
2721
|
+
return Object.keys(result).length > 0 ? result : void 0;
|
|
2722
|
+
}
|
|
2723
|
+
function normalizeSignalAwarenessRun(value) {
|
|
2724
|
+
const run = signalAwarenessRecord(value);
|
|
2725
|
+
const result = {};
|
|
2726
|
+
const id = signalAwarenessText(run.id, 200);
|
|
2727
|
+
const monitorId = signalAwarenessText(run.monitor_id, 200);
|
|
2728
|
+
const status = signalAwarenessText(run.status, 80);
|
|
2729
|
+
const signalsFound = signalAwarenessCount(run.signals_found);
|
|
2730
|
+
if (id) result.id = id;
|
|
2731
|
+
if (monitorId) result.monitor_id = monitorId;
|
|
2732
|
+
if (status) result.status = status;
|
|
2733
|
+
if (signalsFound !== void 0) result.signals_found = signalsFound;
|
|
2734
|
+
for (const key of ["started_at", "completed_at", "created_at"]) {
|
|
2735
|
+
const timestamp = signalAwarenessText(run[key], 64);
|
|
2736
|
+
if (timestamp && Number.isFinite(Date.parse(timestamp))) result[key] = timestamp;
|
|
2737
|
+
}
|
|
2738
|
+
return Object.keys(result).length > 0 ? result : void 0;
|
|
2739
|
+
}
|
|
2740
|
+
function normalizeSignalAwarenessSignal(value) {
|
|
2741
|
+
const signal = value && typeof value === "object" && !Array.isArray(value) ? value : {};
|
|
2742
|
+
const rawData = signal.raw_data && typeof signal.raw_data === "object" && !Array.isArray(signal.raw_data) ? signal.raw_data : {};
|
|
2743
|
+
const row = publicSignalRow({
|
|
2744
|
+
...rawData,
|
|
2745
|
+
...signal,
|
|
2746
|
+
signal_type: signal.signal_type ?? rawData.signal_type,
|
|
2747
|
+
source_url: signal.canonical_source_url ?? rawData.canonical_source_url ?? signal.source_url ?? rawData.source_url ?? rawData.url,
|
|
2748
|
+
date: signal.date ?? signal.event_date ?? signal.detected_at ?? rawData.date ?? rawData.event_date ?? rawData.detected_at ?? rawData.observed_at,
|
|
2749
|
+
company_name: signal.company_name ?? rawData.company_name,
|
|
2750
|
+
company_domain: signal.domain ?? signal.company_domain ?? rawData.company_domain ?? rawData.domain
|
|
2751
|
+
});
|
|
2752
|
+
return row ? [row] : [];
|
|
2753
|
+
}
|
|
2365
2754
|
function isPendingSignalResponse(data) {
|
|
2366
2755
|
if (coreProductResponseFailed(data)) return false;
|
|
2367
2756
|
return ["triggered", "queued", "processing", "pending", "pending_version", "waiting_for_deploy"].includes(String(data.status || "").toLowerCase());
|