@telemai/sdk 0.3.2 → 0.4.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/README.md +19 -0
- package/dist/{chunk-DKTEG7EY.js → chunk-SQ3ZZA72.js} +3 -1
- package/dist/index.cjs +162 -16
- package/dist/index.d.cts +152 -9
- package/dist/index.d.ts +152 -9
- package/dist/index.js +160 -16
- package/dist/vercel/index.js +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -167,6 +167,13 @@ const page = await telem.fetch("https://example.com/article", {
|
|
|
167
167
|
const { status, content } = page.results[0]
|
|
168
168
|
```
|
|
169
169
|
|
|
170
|
+
`providers` pins the fetch providers, in order; `tier` picks the fetch tier; and
|
|
171
|
+
`noCache: true` reads the page live instead of from the shared cache. If you leave
|
|
172
|
+
one out, the client uses its environment variable: `TELEM_FETCH_PROVIDERS` (comma
|
|
173
|
+
separated), `TELEM_FETCH_TIER` (lowercased) or `TELEM_FETCH_NO_CACHE` (`1` turns it
|
|
174
|
+
on). The client reads them when you create it. An option you pass wins, so
|
|
175
|
+
`noCache: false` turns off `TELEM_FETCH_NO_CACHE=1` for that call.
|
|
176
|
+
|
|
170
177
|
A URL that failed still returns a result. Check `result.status` and `result.error`.
|
|
171
178
|
Do not expect a shorter list. The options are on the
|
|
172
179
|
[fetch parameters](https://docs.telem.ai/resources/fetch-parameters/) page.
|
|
@@ -206,10 +213,22 @@ your last poll. `poll` returns a `SearchResponse`:
|
|
|
206
213
|
```ts
|
|
207
214
|
const monitor = await telem.monitors.create("Nvidia files a new 8-K with the SEC", { frequency: "1h", ttl: "7d" })
|
|
208
215
|
const response = await telem.monitors.poll(monitor.id)
|
|
216
|
+
for await (const change of telem.monitors.iterateChanges(monitor.id)) {
|
|
217
|
+
console.log(change.seq, change.kind, change.subject.name)
|
|
218
|
+
}
|
|
209
219
|
await telem.monitors.update(monitor.id, { status: "paused" })
|
|
210
220
|
await telem.monitors.delete(monitor.id)
|
|
211
221
|
```
|
|
212
222
|
|
|
223
|
+
A monitor has an agent unless you create it with `agent: false`. The agent checks every
|
|
224
|
+
result against the query and keeps the ones that match. `iterateChanges` reads what it
|
|
225
|
+
kept, oldest first, until you are caught up, and then stops. Keep the `seq` of the last
|
|
226
|
+
change you handled and pass it as `cursor` next time: no change comes twice, and none
|
|
227
|
+
is skipped. `changes` returns one page (`nextCursor`, `watermark`) and takes
|
|
228
|
+
`cursor`, `since`, `kinds` and `limit`. `agent` returns the agent itself: its status,
|
|
229
|
+
query, frequency and plan version. `monitor.agentState` shows it on the monitor. Read
|
|
230
|
+
`iterateChanges` with `for await`.
|
|
231
|
+
|
|
213
232
|
`telem.monitors` also has `get` and `list`. See [Monitors](https://docs.telem.ai/resources/monitors/)
|
|
214
233
|
for the fields and the errors.
|
|
215
234
|
|
|
@@ -80,8 +80,10 @@ function defaultMessage(status) {
|
|
|
80
80
|
if (status === 404) return "Not found";
|
|
81
81
|
return `Unexpected status code ${status}`;
|
|
82
82
|
}
|
|
83
|
+
var BLOCKED_MESSAGE = "The request was blocked by a firewall before it reached Telem; the text may have characters that are not allowed.";
|
|
83
84
|
function statusError(status, body) {
|
|
84
|
-
|
|
85
|
+
const fallback = status === 403 && !isObject(body) ? BLOCKED_MESSAGE : defaultMessage(status);
|
|
86
|
+
return new TelemError(detailFromBody(body) ?? fallback, {
|
|
85
87
|
status,
|
|
86
88
|
code: codeFromBody(body),
|
|
87
89
|
details: body
|
package/dist/index.cjs
CHANGED
|
@@ -60,7 +60,7 @@ var TimeoutError = class extends TelemError {
|
|
|
60
60
|
};
|
|
61
61
|
|
|
62
62
|
// src/version.ts
|
|
63
|
-
var VERSION = "0.
|
|
63
|
+
var VERSION = "0.4.0";
|
|
64
64
|
|
|
65
65
|
// src/config.ts
|
|
66
66
|
var DEFAULT_BASE_URL = "https://router.telem.ai";
|
|
@@ -120,6 +120,7 @@ function resolveConfig(options) {
|
|
|
120
120
|
if (typeof send !== "function") {
|
|
121
121
|
throw invalidOption("no fetch on this runtime: pass one with the `fetch` option");
|
|
122
122
|
}
|
|
123
|
+
if (typeof opts.apiKey === "string" && !opts.apiKey.trim()) throw invalidOption("apiKey is empty");
|
|
123
124
|
let apiKey = opts.apiKey || env.TELEM_API_KEY || void 0;
|
|
124
125
|
let baseUrl = opts.baseUrl || env.TELEM_BASE_URL || void 0;
|
|
125
126
|
if (apiKey === void 0 || baseUrl === void 0) {
|
|
@@ -158,6 +159,14 @@ function resolveConfig(options) {
|
|
|
158
159
|
autoRouting: opts.autoRouting ?? (trimBlank(env.TELEM_AUTO_ROUTING ?? "") || void 0),
|
|
159
160
|
maxRoutingProviders: opts.maxRoutingProviders ?? intEnv(env.TELEM_MAX_ROUTING_PROVIDERS),
|
|
160
161
|
topic: opts.topic ?? (trimBlank(env.TELEM_TOPIC ?? "") || void 0)
|
|
162
|
+
},
|
|
163
|
+
// Fetch defaults: env var only, parsed as the shared option table parses it (CSV,
|
|
164
|
+
// a trimmed name, a "1"-only flag); the tier is lowercased, as the agent plugins
|
|
165
|
+
// send it. No constructor option, and no config file, as above.
|
|
166
|
+
fetchDefaults: {
|
|
167
|
+
providers: csvEnv(env.TELEM_FETCH_PROVIDERS),
|
|
168
|
+
tier: trimBlank(env.TELEM_FETCH_TIER ?? "").toLowerCase() || void 0,
|
|
169
|
+
noCache: env.TELEM_FETCH_NO_CACHE === "1" || void 0
|
|
161
170
|
}
|
|
162
171
|
};
|
|
163
172
|
}
|
|
@@ -224,8 +233,10 @@ function defaultMessage(status) {
|
|
|
224
233
|
if (status === 404) return "Not found";
|
|
225
234
|
return `Unexpected status code ${status}`;
|
|
226
235
|
}
|
|
236
|
+
var BLOCKED_MESSAGE = "The request was blocked by a firewall before it reached Telem; the text may have characters that are not allowed.";
|
|
227
237
|
function statusError(status, body) {
|
|
228
|
-
|
|
238
|
+
const fallback = status === 403 && !isObject(body) ? BLOCKED_MESSAGE : defaultMessage(status);
|
|
239
|
+
return new TelemError(detailFromBody(body) ?? fallback, {
|
|
229
240
|
status,
|
|
230
241
|
code: codeFromBody(body),
|
|
231
242
|
details: body
|
|
@@ -492,7 +503,7 @@ function wireMetadata(options, kind) {
|
|
|
492
503
|
}
|
|
493
504
|
|
|
494
505
|
// src/methods/fetch.ts
|
|
495
|
-
function fetchBody(url, options) {
|
|
506
|
+
function fetchBody(url, options, defaults) {
|
|
496
507
|
const urls = stringList(
|
|
497
508
|
typeof url === "string" ? [url] : url,
|
|
498
509
|
"fetch() requires at least one URL",
|
|
@@ -500,11 +511,16 @@ function fetchBody(url, options) {
|
|
|
500
511
|
);
|
|
501
512
|
const { metadata, sessionId } = wireMetadata(options, "fetch");
|
|
502
513
|
const body = { urls, metadata };
|
|
514
|
+
const providers2 = options.providers ?? defaults.providers;
|
|
515
|
+
const tier = options.tier ?? defaults.tier;
|
|
516
|
+
const noCache = options.noCache ?? defaults.noCache;
|
|
503
517
|
const block = {};
|
|
504
|
-
if (
|
|
518
|
+
if (providers2 !== void 0) block.providers = providers2;
|
|
505
519
|
if (options.inlineContent !== void 0) block.inline_content = options.inlineContent;
|
|
506
520
|
if (options.inlineMaxChars !== void 0) block.inline_max_chars = options.inlineMaxChars;
|
|
507
521
|
if (options.contentFormat !== void 0) block.content_format = options.contentFormat;
|
|
522
|
+
if (tier !== void 0) block.tier = tier;
|
|
523
|
+
if (noCache !== void 0) block.no_cache = noCache;
|
|
508
524
|
if (Object.keys(block).length) body.options = block;
|
|
509
525
|
if (sessionId !== void 0) body.session_id = sessionId;
|
|
510
526
|
return body;
|
|
@@ -545,12 +561,17 @@ function buildFetchResponse(interaction) {
|
|
|
545
561
|
};
|
|
546
562
|
}
|
|
547
563
|
async function fetchUrls(config, url, options) {
|
|
548
|
-
const body = fetchBody(url, options);
|
|
564
|
+
const body = fetchBody(url, options, config.fetchDefaults);
|
|
549
565
|
return buildFetchResponse(await request(config, "POST", "/v1/fetch", body, options.signal));
|
|
550
566
|
}
|
|
551
567
|
|
|
552
568
|
// src/methods/search.ts
|
|
553
569
|
var MIN_SCHEMA_VERSION = 2;
|
|
570
|
+
function providersRefusal(include, includeFromCall, excludeFromCall) {
|
|
571
|
+
const where = (half, env, fromCall) => fromCall ? `the ${half} search() option` : `the client's ${half} or ${env}`;
|
|
572
|
+
const names = include.join(", ");
|
|
573
|
+
return `providersExclude removes every provider in providersInclude (${names}), so no provider is left and no search was sent. Remove ${names} from providersInclude (set by ${where("providersInclude", "TELEM_PROVIDERS_INCLUDE", includeFromCall)}) or from providersExclude (set by ${where("providersExclude", "TELEM_PROVIDERS_EXCLUDE", excludeFromCall)}).`;
|
|
574
|
+
}
|
|
554
575
|
function searchBlock(defaults, options) {
|
|
555
576
|
const fromCallTier = options.tier !== void 0;
|
|
556
577
|
const fromCallFields = options.fields !== void 0;
|
|
@@ -564,7 +585,13 @@ function searchBlock(defaults, options) {
|
|
|
564
585
|
let exclude = options.providersExclude ?? defaults.providersExclude;
|
|
565
586
|
if (include !== void 0 && exclude !== void 0) {
|
|
566
587
|
const excluded = new Set(exclude);
|
|
567
|
-
|
|
588
|
+
const kept = include.filter((name) => !excluded.has(name));
|
|
589
|
+
if (include.length && !kept.length) {
|
|
590
|
+
throw invalidRequest(
|
|
591
|
+
providersRefusal(include, options.providersInclude !== void 0, options.providersExclude !== void 0)
|
|
592
|
+
);
|
|
593
|
+
}
|
|
594
|
+
include = kept;
|
|
568
595
|
exclude = void 0;
|
|
569
596
|
}
|
|
570
597
|
const includeFullContent = options.includeFullContent ?? defaults.includeFullContent;
|
|
@@ -674,7 +701,8 @@ function providerRun(run) {
|
|
|
674
701
|
related: envelope.related ?? null,
|
|
675
702
|
verticals: envelope.verticals ?? null,
|
|
676
703
|
usage: envelope.usage ?? null,
|
|
677
|
-
warnings: asArray(envelope.warnings)
|
|
704
|
+
warnings: asArray(envelope.warnings),
|
|
705
|
+
sameStory: isObject(envelope.same_story) ? envelope.same_story : null
|
|
678
706
|
};
|
|
679
707
|
}
|
|
680
708
|
function buildSearchResponse(interaction) {
|
|
@@ -698,9 +726,25 @@ async function search(config, query, options) {
|
|
|
698
726
|
}
|
|
699
727
|
|
|
700
728
|
// src/methods/monitors.ts
|
|
729
|
+
function agentStateFrom(data) {
|
|
730
|
+
return {
|
|
731
|
+
engine: String(data.engine ?? ""),
|
|
732
|
+
status: String(data.status ?? ""),
|
|
733
|
+
needsAttention: data.needs_attention === true,
|
|
734
|
+
planVersion: typeof data.plan_version === "number" ? data.plan_version : null,
|
|
735
|
+
nextRunAt: typeof data.next_run_at === "string" ? data.next_run_at : null,
|
|
736
|
+
watermark: Number(data.watermark ?? 0),
|
|
737
|
+
// No compile job yet is null, not an object of empty strings.
|
|
738
|
+
compile: isObject(data.compile) ? {
|
|
739
|
+
jobId: String(data.compile.job_id ?? ""),
|
|
740
|
+
status: String(data.compile.status ?? ""),
|
|
741
|
+
error: typeof data.compile.error === "string" ? data.compile.error : null
|
|
742
|
+
} : null
|
|
743
|
+
};
|
|
744
|
+
}
|
|
701
745
|
function monitorFrom(body) {
|
|
702
746
|
const data = asObject(body);
|
|
703
|
-
|
|
747
|
+
const monitor = {
|
|
704
748
|
id: String(data.id ?? ""),
|
|
705
749
|
query: data.query ?? "",
|
|
706
750
|
frequency: data.frequency ?? "",
|
|
@@ -713,12 +757,85 @@ function monitorFrom(body) {
|
|
|
713
757
|
webhookSecret: data.webhook_secret ?? null,
|
|
714
758
|
raw: data
|
|
715
759
|
};
|
|
760
|
+
if (data.agent_state !== void 0) {
|
|
761
|
+
monitor.agentState = isObject(data.agent_state) ? agentStateFrom(data.agent_state) : null;
|
|
762
|
+
}
|
|
763
|
+
return monitor;
|
|
764
|
+
}
|
|
765
|
+
function agentDocumentFrom(body) {
|
|
766
|
+
const data = asObject(body);
|
|
767
|
+
const document = { raw: data };
|
|
768
|
+
if (typeof data.status === "string") document.status = data.status;
|
|
769
|
+
if (typeof data.query === "string") document.query = data.query;
|
|
770
|
+
if (typeof data.frequency === "string") document.frequency = data.frequency;
|
|
771
|
+
if (typeof data.spec_version === "number") document.specVersion = data.spec_version;
|
|
772
|
+
if (data.budget !== void 0) document.budget = isObject(data.budget) ? data.budget : null;
|
|
773
|
+
if (typeof data.spend_usd === "number") document.spendUsd = data.spend_usd;
|
|
774
|
+
return document;
|
|
775
|
+
}
|
|
776
|
+
function changeRecordFrom(entry) {
|
|
777
|
+
const subject = asObject(entry.subject);
|
|
778
|
+
return {
|
|
779
|
+
seq: Number(entry.seq ?? 0),
|
|
780
|
+
type: String(entry.type ?? ""),
|
|
781
|
+
kind: String(entry.kind ?? ""),
|
|
782
|
+
monitorId: String(entry.monitor_id ?? ""),
|
|
783
|
+
subject: {
|
|
784
|
+
entityId: typeof subject.entity_id === "string" ? subject.entity_id : null,
|
|
785
|
+
name: typeof subject.name === "string" ? subject.name : null
|
|
786
|
+
},
|
|
787
|
+
// The values depend on the kind (an object, a status string, nothing): as sent.
|
|
788
|
+
before: entry.before ?? null,
|
|
789
|
+
after: entry.after ?? null,
|
|
790
|
+
factIds: asArray(entry.fact_ids).map(String),
|
|
791
|
+
at: String(entry.at ?? ""),
|
|
792
|
+
raw: entry
|
|
793
|
+
};
|
|
794
|
+
}
|
|
795
|
+
function changesPageFrom(body) {
|
|
796
|
+
const data = asObject(body);
|
|
797
|
+
return {
|
|
798
|
+
changes: asArray(data.changes).filter(isObject).map(changeRecordFrom),
|
|
799
|
+
nextCursor: Number(data.next_cursor ?? 0),
|
|
800
|
+
watermark: Number(data.watermark ?? 0)
|
|
801
|
+
};
|
|
802
|
+
}
|
|
803
|
+
function listQuery(options) {
|
|
804
|
+
const params = new URLSearchParams();
|
|
805
|
+
if (options.limit !== void 0) params.set("limit", String(options.limit));
|
|
806
|
+
if (options.cursor !== void 0) params.set("cursor", options.cursor);
|
|
807
|
+
const query = params.toString();
|
|
808
|
+
return query ? `?${query}` : "";
|
|
809
|
+
}
|
|
810
|
+
function sinceParam(since) {
|
|
811
|
+
if (typeof since === "string") return since;
|
|
812
|
+
if (Number.isNaN(since.getTime())) throw invalidRequest("since is not a valid date");
|
|
813
|
+
return since.toISOString();
|
|
814
|
+
}
|
|
815
|
+
function changesQuery(options) {
|
|
816
|
+
const params = new URLSearchParams();
|
|
817
|
+
if (options.cursor !== void 0) params.set("cursor", String(options.cursor));
|
|
818
|
+
if (options.since !== void 0) params.set("since", sinceParam(options.since));
|
|
819
|
+
if (options.kinds !== void 0) params.set("kinds", options.kinds.join(","));
|
|
820
|
+
if (options.limit !== void 0) params.set("limit", String(options.limit));
|
|
821
|
+
const query = params.toString();
|
|
822
|
+
return query ? `?${query}` : "";
|
|
716
823
|
}
|
|
717
824
|
function createMonitors(config) {
|
|
718
825
|
const path = (monitorId, suffix = "") => {
|
|
719
826
|
if (!monitorId || /^\.+$/.test(monitorId)) throw invalidRequest("a monitor id is required");
|
|
720
827
|
return `/v1/monitors/${encodeURIComponent(monitorId)}${suffix}`;
|
|
721
828
|
};
|
|
829
|
+
const listPage = async (options = {}) => {
|
|
830
|
+
const route = `/v1/monitors${listQuery(options)}`;
|
|
831
|
+
const data = asObject(await request(config, "GET", route, void 0, options.signal));
|
|
832
|
+
const nextCursor = typeof data.next_cursor === "string" ? data.next_cursor : null;
|
|
833
|
+
return { monitors: asArray(data.monitors).map(monitorFrom), nextCursor };
|
|
834
|
+
};
|
|
835
|
+
const changes = async (monitorId, options = {}) => {
|
|
836
|
+
const route = `${path(monitorId, "/agent/changes")}${changesQuery(options)}`;
|
|
837
|
+
return changesPageFrom(await request(config, "GET", route, void 0, options.signal));
|
|
838
|
+
};
|
|
722
839
|
return {
|
|
723
840
|
/** Create a monitor. Telem runs `query` on the schedule. */
|
|
724
841
|
async create(query, options = {}) {
|
|
@@ -732,15 +849,25 @@ function createMonitors(config) {
|
|
|
732
849
|
if (options.metadata !== void 0) body.metadata = options.metadata;
|
|
733
850
|
if (options.webhookUrl !== void 0) body.webhook_url = options.webhookUrl;
|
|
734
851
|
if (options.ttl !== void 0) body.ttl = options.ttl;
|
|
735
|
-
|
|
852
|
+
if (options.agent !== void 0) body.agent = options.agent;
|
|
853
|
+
const data = await request(config, "POST", "/v1/monitors", body, options.signal, "rate_limit").catch(
|
|
854
|
+
(error) => {
|
|
855
|
+
if (error instanceof TimeoutError) {
|
|
856
|
+
throw new TimeoutError(
|
|
857
|
+
`${error.message}. The monitor may exist: list monitors before you create it again.`,
|
|
858
|
+
error.cause
|
|
859
|
+
);
|
|
860
|
+
}
|
|
861
|
+
throw error;
|
|
862
|
+
}
|
|
863
|
+
);
|
|
736
864
|
return monitorFrom(data);
|
|
737
865
|
},
|
|
738
|
-
/** List your monitors, newest first
|
|
866
|
+
/** List your monitors, newest first. `listPage` also gives the next cursor. */
|
|
739
867
|
async list(options = {}) {
|
|
740
|
-
|
|
741
|
-
const body = await request(config, "GET", `/v1/monitors${query}`, void 0, options.signal);
|
|
742
|
-
return asArray(asObject(body).monitors).map(monitorFrom);
|
|
868
|
+
return (await listPage(options)).monitors;
|
|
743
869
|
},
|
|
870
|
+
listPage,
|
|
744
871
|
/** Get one monitor. */
|
|
745
872
|
async get(monitorId, options = {}) {
|
|
746
873
|
return monitorFrom(await request(config, "GET", path(monitorId), void 0, options.signal));
|
|
@@ -750,7 +877,7 @@ function createMonitors(config) {
|
|
|
750
877
|
const body = {};
|
|
751
878
|
if (options.status !== void 0) body.status = options.status;
|
|
752
879
|
if (options.frequency !== void 0) body.frequency = options.frequency;
|
|
753
|
-
if (options.webhookUrl !== void 0) body.webhook_url = options.webhookUrl;
|
|
880
|
+
if (options.webhookUrl !== void 0) body.webhook_url = options.webhookUrl || null;
|
|
754
881
|
const route = path(monitorId);
|
|
755
882
|
return monitorFrom(await request(config, "PATCH", route, body, options.signal));
|
|
756
883
|
},
|
|
@@ -766,6 +893,23 @@ function createMonitors(config) {
|
|
|
766
893
|
/** Delete a monitor. A repeat deletes what a failed delete left. */
|
|
767
894
|
async delete(monitorId, options = {}) {
|
|
768
895
|
await request(config, "DELETE", path(monitorId), void 0, options.signal);
|
|
896
|
+
},
|
|
897
|
+
/** Read the monitor agent's document. A monitor without an agent answers 404. */
|
|
898
|
+
async agent(monitorId, options = {}) {
|
|
899
|
+
const route = path(monitorId, "/agent");
|
|
900
|
+
return agentDocumentFrom(await request(config, "GET", route, void 0, options.signal));
|
|
901
|
+
},
|
|
902
|
+
/** One page of the agent's changes. Keep `nextCursor` and pass it back as `cursor`. */
|
|
903
|
+
changes,
|
|
904
|
+
/** Every change after `cursor`, page by page, until you are caught up. */
|
|
905
|
+
async *iterateChanges(monitorId, options = {}) {
|
|
906
|
+
let cursor = options.cursor ?? 0;
|
|
907
|
+
for (; ; ) {
|
|
908
|
+
const page = await changes(monitorId, { cursor, signal: options.signal });
|
|
909
|
+
for (const change of page.changes) yield change;
|
|
910
|
+
if (!page.changes.length || page.nextCursor <= cursor || page.nextCursor >= page.watermark) return;
|
|
911
|
+
cursor = page.nextCursor;
|
|
912
|
+
}
|
|
769
913
|
}
|
|
770
914
|
};
|
|
771
915
|
}
|
|
@@ -798,7 +942,8 @@ async function providers(config) {
|
|
|
798
942
|
method: entry.method ?? null,
|
|
799
943
|
url: entry.url ?? null,
|
|
800
944
|
normalized: entry.normalized ?? false,
|
|
801
|
-
tiers: asArray(entry.tiers)
|
|
945
|
+
tiers: asArray(entry.tiers),
|
|
946
|
+
autoRouted: entry.auto_routed ?? null
|
|
802
947
|
}));
|
|
803
948
|
}
|
|
804
949
|
|
|
@@ -867,7 +1012,8 @@ var Telem = class {
|
|
|
867
1012
|
maxRetries;
|
|
868
1013
|
/** The session read surface: `list` and `results(id)`. */
|
|
869
1014
|
sessions;
|
|
870
|
-
/** Monitors: `create`, `list`, `get`, `update`, `poll`, `delete
|
|
1015
|
+
/** Monitors: `create`, `list`, `listPage`, `get`, `update`, `poll`, `delete`, and the
|
|
1016
|
+
* agent reads `agent`, `changes` and `iterateChanges`. */
|
|
871
1017
|
monitors;
|
|
872
1018
|
#config;
|
|
873
1019
|
/**
|
package/dist/index.d.cts
CHANGED
|
@@ -96,10 +96,17 @@ type SearchOptions = {
|
|
|
96
96
|
* `numResults`/`includeRaw`/`rerank`/`providerOverrides` are per-call intent only. */
|
|
97
97
|
type SearchDefaults = Pick<SearchOptions, "tier" | "fields" | "providersInclude" | "providersExclude" | "includeFullContent" | "autoRouting" | "maxRoutingProviders" | "topic">;
|
|
98
98
|
type FetchOptions = {
|
|
99
|
+
/** Fetch provider chain, in order. Defaults to `TELEM_FETCH_PROVIDERS`. */
|
|
99
100
|
providers?: string[];
|
|
100
101
|
inlineContent?: boolean;
|
|
101
102
|
inlineMaxChars?: number;
|
|
102
103
|
contentFormat?: string;
|
|
104
|
+
/** Fetch tier: `minimalist`, `default`, `extended` or `max`. Sent as given; the
|
|
105
|
+
* server rejects an unknown one. Defaults to `TELEM_FETCH_TIER`, lowercased. */
|
|
106
|
+
tier?: string;
|
|
107
|
+
/** `true` reads every page live and skips the shared fetch cache. Defaults to
|
|
108
|
+
* `TELEM_FETCH_NO_CACHE` (on with exactly `"1"`); `false` overrides it. */
|
|
109
|
+
noCache?: boolean;
|
|
103
110
|
session?: string;
|
|
104
111
|
/** Abort this call: the request stops, no retry follows, and the call rejects
|
|
105
112
|
* with the signal's reason. Merged with the per-attempt timeout. */
|
|
@@ -150,6 +157,8 @@ type ProviderRun = {
|
|
|
150
157
|
verticals: Json | null;
|
|
151
158
|
usage: Json | unknown[] | null;
|
|
152
159
|
warnings: Json[];
|
|
160
|
+
/** Monitor polls: results folded as the same story, `{leadUrl: [{url, title}]}`. */
|
|
161
|
+
sameStory: Record<string, Json[]> | null;
|
|
153
162
|
raw: Json | null;
|
|
154
163
|
};
|
|
155
164
|
type SearchResponse = {
|
|
@@ -200,6 +209,8 @@ type ProviderInfo = {
|
|
|
200
209
|
url: string | null;
|
|
201
210
|
normalized: boolean;
|
|
202
211
|
tiers: string[];
|
|
212
|
+
/** Whether auto-routing can pick it; `null` from a router that does not say. */
|
|
213
|
+
autoRouted: boolean | null;
|
|
203
214
|
};
|
|
204
215
|
/** One session as `sessions.list` reports it. */
|
|
205
216
|
type SessionSummary = {
|
|
@@ -243,6 +254,10 @@ type MonitorCreateOptions = {
|
|
|
243
254
|
webhookUrl?: string;
|
|
244
255
|
/** Delete the monitor after this long, such as `"12h"` or `"7d"` (at most `"30d"`). Without it, the monitor never expires. */
|
|
245
256
|
ttl?: string;
|
|
257
|
+
/** Start the monitor agent with the monitor: it checks every result against the query
|
|
258
|
+
* and keeps the ones that match. Telem turns it on when you leave this out; `false`
|
|
259
|
+
* creates the monitor without one. Read what the agent keeps with `monitors.changes`. */
|
|
260
|
+
agent?: boolean;
|
|
246
261
|
signal?: AbortSignal;
|
|
247
262
|
};
|
|
248
263
|
/** Options for `monitors.update`. Send at least one field. */
|
|
@@ -250,7 +265,7 @@ type MonitorUpdateOptions = {
|
|
|
250
265
|
/** `"paused"` or `"active"`. */
|
|
251
266
|
status?: string;
|
|
252
267
|
frequency?: string;
|
|
253
|
-
/** A new webhook URL, with a new `webhookSecret` in the response. `null` removes it. */
|
|
268
|
+
/** A new webhook URL, with a new `webhookSecret` in the response. `null` or `""` removes it. */
|
|
254
269
|
webhookUrl?: string | null;
|
|
255
270
|
signal?: AbortSignal;
|
|
256
271
|
};
|
|
@@ -267,25 +282,144 @@ type Monitor = {
|
|
|
267
282
|
id: string;
|
|
268
283
|
query: string;
|
|
269
284
|
frequency: string;
|
|
270
|
-
/** `active
|
|
285
|
+
/** `active`, `paused` (you paused it) or `ended` (past `expiresAt`). */
|
|
271
286
|
status: string;
|
|
272
287
|
sessionId: string;
|
|
273
288
|
createdAt: string;
|
|
274
289
|
lastPolledAt: string | null;
|
|
275
|
-
/** When
|
|
290
|
+
/** When the monitor ends; `null`: never. */
|
|
276
291
|
expiresAt: string | null;
|
|
277
292
|
webhookUrl: string | null;
|
|
278
293
|
/** Signs the webhook deliveries. Only in the response that set `webhookUrl`. */
|
|
279
294
|
webhookSecret: string | null;
|
|
295
|
+
/** The monitor agent's state. `null`: the monitor has no agent. Absent when the router
|
|
296
|
+
* sends none, as a router from before the agent reads does. */
|
|
297
|
+
agentState?: AgentState | null;
|
|
298
|
+
raw: Json;
|
|
299
|
+
};
|
|
300
|
+
/** The latest compile of an agent's plan (`AgentState.compile`). */
|
|
301
|
+
type AgentCompileState = {
|
|
302
|
+
jobId: string;
|
|
303
|
+
/** The compile job's status, such as `done` or `failed`. */
|
|
304
|
+
status: string;
|
|
305
|
+
/** Why the compile failed; `null` when it did not. */
|
|
306
|
+
error: string | null;
|
|
307
|
+
};
|
|
308
|
+
/** The state of a monitor's agent: `monitor.agentState`. */
|
|
309
|
+
type AgentState = {
|
|
310
|
+
/** The agent engine, `"v4"` today. */
|
|
311
|
+
engine: string;
|
|
312
|
+
/** Such as `compiling`, `ready`, `paused` or `failed`. */
|
|
313
|
+
status: string;
|
|
314
|
+
/** `true` when `status` is `failed`. */
|
|
315
|
+
needsAttention: boolean;
|
|
316
|
+
/** The version of the agent's plan; `null` before it has one. */
|
|
317
|
+
planVersion: number | null;
|
|
318
|
+
/** When the agent runs next; `null` when no run is scheduled. */
|
|
319
|
+
nextRunAt: string | null;
|
|
320
|
+
/** The `seq` of the newest change `monitors.changes` can serve now. */
|
|
321
|
+
watermark: number;
|
|
322
|
+
/** The latest compile of the plan; `null` when there has been none. */
|
|
323
|
+
compile: AgentCompileState | null;
|
|
324
|
+
};
|
|
325
|
+
/** The monitor agent's document: `monitors.agent`. A field is there only when the
|
|
326
|
+
* router sent it. The rest of the document (the plan, the counts, the runs) is in `raw`. */
|
|
327
|
+
type AgentDocument = {
|
|
328
|
+
/** Such as `compiling`, `ready`, `paused`, `failed` or `ended`. */
|
|
329
|
+
status?: string;
|
|
330
|
+
query?: string;
|
|
331
|
+
frequency?: string;
|
|
332
|
+
/** The version of the plan; 0 while the agent compiles. */
|
|
333
|
+
specVersion?: number;
|
|
334
|
+
/** The agent's spending limits; `null` when none are set. */
|
|
335
|
+
budget?: Json | null;
|
|
336
|
+
/** What the agent has spent, in US dollars. */
|
|
337
|
+
spendUsd?: number;
|
|
280
338
|
raw: Json;
|
|
281
339
|
};
|
|
340
|
+
/** The item a change is about. `entityId` is `null` for a change to the whole monitor,
|
|
341
|
+
* such as a run or a plan change. */
|
|
342
|
+
type ChangeSubject = {
|
|
343
|
+
entityId: string | null;
|
|
344
|
+
name: string | null;
|
|
345
|
+
};
|
|
346
|
+
/** One change the monitor agent made. */
|
|
347
|
+
type ChangeRecord = {
|
|
348
|
+
/** The change's place in the stream. It grows with every change and is never reused.
|
|
349
|
+
* Pass the last one you handled as `cursor` to read on from there. */
|
|
350
|
+
seq: number;
|
|
351
|
+
/** The change's own type, such as `new_object`. */
|
|
352
|
+
type: string;
|
|
353
|
+
/** What happened: one of the six kinds `entity_added`, `value_changed`,
|
|
354
|
+
* `fact_status_changed`, `alert`, `run` or `plan_changed`. */
|
|
355
|
+
kind: string;
|
|
356
|
+
monitorId: string;
|
|
357
|
+
subject: ChangeSubject;
|
|
358
|
+
/** What it was before, as the router sent it; `null` when there is no before. Its shape
|
|
359
|
+
* depends on `kind`. */
|
|
360
|
+
before: unknown;
|
|
361
|
+
/** What it is now, as the router sent it. */
|
|
362
|
+
after: unknown;
|
|
363
|
+
/** The facts behind the change; empty when the router names none. */
|
|
364
|
+
factIds: string[];
|
|
365
|
+
/** When it happened, ISO 8601. */
|
|
366
|
+
at: string;
|
|
367
|
+
raw: Json;
|
|
368
|
+
};
|
|
369
|
+
/** One page of `monitors.changes`. */
|
|
370
|
+
type ChangesPage = {
|
|
371
|
+
changes: ChangeRecord[];
|
|
372
|
+
/** Keep this and pass it as `cursor` to read the changes after this page. On a full
|
|
373
|
+
* page (`limit` changes) it is the `seq` of the last change. On a shorter page, an
|
|
374
|
+
* empty one included, it is `watermark`: the read got that far, past the changes
|
|
375
|
+
* that `kinds` left out too. */
|
|
376
|
+
nextCursor: number;
|
|
377
|
+
/** The `seq` of the newest change that can be read now. You are caught up when
|
|
378
|
+
* `nextCursor` equals it, or when a page is empty. */
|
|
379
|
+
watermark: number;
|
|
380
|
+
};
|
|
381
|
+
/** Options for `monitors.changes`. */
|
|
382
|
+
type MonitorChangesOptions = {
|
|
383
|
+
/** Read the changes after this `seq`. If you leave it out, the page starts at the
|
|
384
|
+
* first change. Do not send it with `since`. */
|
|
385
|
+
cursor?: number;
|
|
386
|
+
/** Read from this time on: a `Date`, or an ISO 8601 time with an offset such as
|
|
387
|
+
* `"2026-11-03T12:00:00Z"`. Do not send it with `cursor`. */
|
|
388
|
+
since?: string | Date;
|
|
389
|
+
/** Only these kinds of change: `entity_added`, `value_changed`, `fact_status_changed`,
|
|
390
|
+
* `alert`, `run` or `plan_changed`, for example `["alert", "run"]`. Another name is a
|
|
391
|
+
* 400 (`kinds_invalid`). An empty list is no filter. */
|
|
392
|
+
kinds?: string[];
|
|
393
|
+
/** How many changes to return (server default 200, maximum 500). */
|
|
394
|
+
limit?: number;
|
|
395
|
+
signal?: AbortSignal;
|
|
396
|
+
};
|
|
397
|
+
/** Options for `monitors.iterateChanges`. */
|
|
398
|
+
type MonitorIterateChangesOptions = {
|
|
399
|
+
/** Read the changes after this `seq`. If you leave it out, the walk starts at the
|
|
400
|
+
* first change. */
|
|
401
|
+
cursor?: number;
|
|
402
|
+
signal?: AbortSignal;
|
|
403
|
+
};
|
|
404
|
+
/** Options for `monitors.list` and `monitors.listPage`. */
|
|
405
|
+
type MonitorListOptions = {
|
|
406
|
+
/** How many to return (server default 50, maximum 200). */
|
|
407
|
+
limit?: number;
|
|
408
|
+
/** The `nextCursor` of the page before. */
|
|
409
|
+
cursor?: string;
|
|
410
|
+
signal?: AbortSignal;
|
|
411
|
+
};
|
|
412
|
+
/** One page of `monitors.listPage`. */
|
|
413
|
+
type MonitorPage = {
|
|
414
|
+
monitors: Monitor[];
|
|
415
|
+
/** Pass as `cursor` to get the next page; `null` on the last page. */
|
|
416
|
+
nextCursor: string | null;
|
|
417
|
+
};
|
|
282
418
|
/** The `telem.monitors` namespace. */
|
|
283
419
|
type MonitorsResource = {
|
|
284
420
|
create(query: string, options?: MonitorCreateOptions): Promise<Monitor>;
|
|
285
|
-
list(options?:
|
|
286
|
-
|
|
287
|
-
signal?: AbortSignal;
|
|
288
|
-
}): Promise<Monitor[]>;
|
|
421
|
+
list(options?: MonitorListOptions): Promise<Monitor[]>;
|
|
422
|
+
listPage(options?: MonitorListOptions): Promise<MonitorPage>;
|
|
289
423
|
get(monitorId: string, options?: {
|
|
290
424
|
signal?: AbortSignal;
|
|
291
425
|
}): Promise<Monitor>;
|
|
@@ -294,6 +428,14 @@ type MonitorsResource = {
|
|
|
294
428
|
delete(monitorId: string, options?: {
|
|
295
429
|
signal?: AbortSignal;
|
|
296
430
|
}): Promise<void>;
|
|
431
|
+
/** Read the monitor agent's document. A monitor without an agent answers 404. */
|
|
432
|
+
agent(monitorId: string, options?: {
|
|
433
|
+
signal?: AbortSignal;
|
|
434
|
+
}): Promise<AgentDocument>;
|
|
435
|
+
/** One page of the agent's changes. Keep `nextCursor` and pass it back as `cursor`. */
|
|
436
|
+
changes(monitorId: string, options?: MonitorChangesOptions): Promise<ChangesPage>;
|
|
437
|
+
/** Every change after `cursor`, page by page, until you are caught up. */
|
|
438
|
+
iterateChanges(monitorId: string, options?: MonitorIterateChangesOptions): AsyncGenerator<ChangeRecord, void, undefined>;
|
|
297
439
|
};
|
|
298
440
|
|
|
299
441
|
/**
|
|
@@ -437,7 +579,8 @@ declare class Telem {
|
|
|
437
579
|
readonly maxRetries: number;
|
|
438
580
|
/** The session read surface: `list` and `results(id)`. */
|
|
439
581
|
readonly sessions: SessionsResource;
|
|
440
|
-
/** Monitors: `create`, `list`, `get`, `update`, `poll`, `delete
|
|
582
|
+
/** Monitors: `create`, `list`, `listPage`, `get`, `update`, `poll`, `delete`, and the
|
|
583
|
+
* agent reads `agent`, `changes` and `iterateChanges`. */
|
|
441
584
|
readonly monitors: MonitorsResource;
|
|
442
585
|
/**
|
|
443
586
|
* @param options - An API key string, or an options object. Anything left unset
|
|
@@ -470,4 +613,4 @@ declare class Telem {
|
|
|
470
613
|
providers(): Promise<ProviderInfo[]>;
|
|
471
614
|
}
|
|
472
615
|
|
|
473
|
-
export { type FetchOptions, type FetchResponse, type FetchResult, type Json, type Monitor, type MonitorCreateOptions, type MonitorPollOptions, type MonitorUpdateOptions, type MonitorsResource, type ProviderInfo, type ProviderRun, RESERVED_METADATA, type SearchDefaults, type SearchOptions, type SearchResponse, type SearchResult, type SessionResults, type SessionSummary, type SessionsResource, type SnapshotArgs, Telem, type TelemClientErrorCode, TelemError, type TelemErrorOptions, type TelemOptions, TimeoutError, type TrajectoryArgs, type TrajectoryEnvelope, type TrajectorySnapshot, buildMetadata, buildSnapshot, contentAnchor, Telem as default, eventNodeKey, fingerprint, sessionKey, snapshotNodeKey, toolMarker, verifyWebhook, windowAnchor, withTrajectory };
|
|
616
|
+
export { type AgentCompileState, type AgentDocument, type AgentState, type ChangeRecord, type ChangeSubject, type ChangesPage, type FetchOptions, type FetchResponse, type FetchResult, type Json, type Monitor, type MonitorChangesOptions, type MonitorCreateOptions, type MonitorIterateChangesOptions, type MonitorListOptions, type MonitorPage, type MonitorPollOptions, type MonitorUpdateOptions, type MonitorsResource, type ProviderInfo, type ProviderRun, RESERVED_METADATA, type SearchDefaults, type SearchOptions, type SearchResponse, type SearchResult, type SessionResults, type SessionSummary, type SessionsResource, type SnapshotArgs, Telem, type TelemClientErrorCode, TelemError, type TelemErrorOptions, type TelemOptions, TimeoutError, type TrajectoryArgs, type TrajectoryEnvelope, type TrajectorySnapshot, buildMetadata, buildSnapshot, contentAnchor, Telem as default, eventNodeKey, fingerprint, sessionKey, snapshotNodeKey, toolMarker, verifyWebhook, windowAnchor, withTrajectory };
|
package/dist/index.d.ts
CHANGED
|
@@ -96,10 +96,17 @@ type SearchOptions = {
|
|
|
96
96
|
* `numResults`/`includeRaw`/`rerank`/`providerOverrides` are per-call intent only. */
|
|
97
97
|
type SearchDefaults = Pick<SearchOptions, "tier" | "fields" | "providersInclude" | "providersExclude" | "includeFullContent" | "autoRouting" | "maxRoutingProviders" | "topic">;
|
|
98
98
|
type FetchOptions = {
|
|
99
|
+
/** Fetch provider chain, in order. Defaults to `TELEM_FETCH_PROVIDERS`. */
|
|
99
100
|
providers?: string[];
|
|
100
101
|
inlineContent?: boolean;
|
|
101
102
|
inlineMaxChars?: number;
|
|
102
103
|
contentFormat?: string;
|
|
104
|
+
/** Fetch tier: `minimalist`, `default`, `extended` or `max`. Sent as given; the
|
|
105
|
+
* server rejects an unknown one. Defaults to `TELEM_FETCH_TIER`, lowercased. */
|
|
106
|
+
tier?: string;
|
|
107
|
+
/** `true` reads every page live and skips the shared fetch cache. Defaults to
|
|
108
|
+
* `TELEM_FETCH_NO_CACHE` (on with exactly `"1"`); `false` overrides it. */
|
|
109
|
+
noCache?: boolean;
|
|
103
110
|
session?: string;
|
|
104
111
|
/** Abort this call: the request stops, no retry follows, and the call rejects
|
|
105
112
|
* with the signal's reason. Merged with the per-attempt timeout. */
|
|
@@ -150,6 +157,8 @@ type ProviderRun = {
|
|
|
150
157
|
verticals: Json | null;
|
|
151
158
|
usage: Json | unknown[] | null;
|
|
152
159
|
warnings: Json[];
|
|
160
|
+
/** Monitor polls: results folded as the same story, `{leadUrl: [{url, title}]}`. */
|
|
161
|
+
sameStory: Record<string, Json[]> | null;
|
|
153
162
|
raw: Json | null;
|
|
154
163
|
};
|
|
155
164
|
type SearchResponse = {
|
|
@@ -200,6 +209,8 @@ type ProviderInfo = {
|
|
|
200
209
|
url: string | null;
|
|
201
210
|
normalized: boolean;
|
|
202
211
|
tiers: string[];
|
|
212
|
+
/** Whether auto-routing can pick it; `null` from a router that does not say. */
|
|
213
|
+
autoRouted: boolean | null;
|
|
203
214
|
};
|
|
204
215
|
/** One session as `sessions.list` reports it. */
|
|
205
216
|
type SessionSummary = {
|
|
@@ -243,6 +254,10 @@ type MonitorCreateOptions = {
|
|
|
243
254
|
webhookUrl?: string;
|
|
244
255
|
/** Delete the monitor after this long, such as `"12h"` or `"7d"` (at most `"30d"`). Without it, the monitor never expires. */
|
|
245
256
|
ttl?: string;
|
|
257
|
+
/** Start the monitor agent with the monitor: it checks every result against the query
|
|
258
|
+
* and keeps the ones that match. Telem turns it on when you leave this out; `false`
|
|
259
|
+
* creates the monitor without one. Read what the agent keeps with `monitors.changes`. */
|
|
260
|
+
agent?: boolean;
|
|
246
261
|
signal?: AbortSignal;
|
|
247
262
|
};
|
|
248
263
|
/** Options for `monitors.update`. Send at least one field. */
|
|
@@ -250,7 +265,7 @@ type MonitorUpdateOptions = {
|
|
|
250
265
|
/** `"paused"` or `"active"`. */
|
|
251
266
|
status?: string;
|
|
252
267
|
frequency?: string;
|
|
253
|
-
/** A new webhook URL, with a new `webhookSecret` in the response. `null` removes it. */
|
|
268
|
+
/** A new webhook URL, with a new `webhookSecret` in the response. `null` or `""` removes it. */
|
|
254
269
|
webhookUrl?: string | null;
|
|
255
270
|
signal?: AbortSignal;
|
|
256
271
|
};
|
|
@@ -267,25 +282,144 @@ type Monitor = {
|
|
|
267
282
|
id: string;
|
|
268
283
|
query: string;
|
|
269
284
|
frequency: string;
|
|
270
|
-
/** `active
|
|
285
|
+
/** `active`, `paused` (you paused it) or `ended` (past `expiresAt`). */
|
|
271
286
|
status: string;
|
|
272
287
|
sessionId: string;
|
|
273
288
|
createdAt: string;
|
|
274
289
|
lastPolledAt: string | null;
|
|
275
|
-
/** When
|
|
290
|
+
/** When the monitor ends; `null`: never. */
|
|
276
291
|
expiresAt: string | null;
|
|
277
292
|
webhookUrl: string | null;
|
|
278
293
|
/** Signs the webhook deliveries. Only in the response that set `webhookUrl`. */
|
|
279
294
|
webhookSecret: string | null;
|
|
295
|
+
/** The monitor agent's state. `null`: the monitor has no agent. Absent when the router
|
|
296
|
+
* sends none, as a router from before the agent reads does. */
|
|
297
|
+
agentState?: AgentState | null;
|
|
298
|
+
raw: Json;
|
|
299
|
+
};
|
|
300
|
+
/** The latest compile of an agent's plan (`AgentState.compile`). */
|
|
301
|
+
type AgentCompileState = {
|
|
302
|
+
jobId: string;
|
|
303
|
+
/** The compile job's status, such as `done` or `failed`. */
|
|
304
|
+
status: string;
|
|
305
|
+
/** Why the compile failed; `null` when it did not. */
|
|
306
|
+
error: string | null;
|
|
307
|
+
};
|
|
308
|
+
/** The state of a monitor's agent: `monitor.agentState`. */
|
|
309
|
+
type AgentState = {
|
|
310
|
+
/** The agent engine, `"v4"` today. */
|
|
311
|
+
engine: string;
|
|
312
|
+
/** Such as `compiling`, `ready`, `paused` or `failed`. */
|
|
313
|
+
status: string;
|
|
314
|
+
/** `true` when `status` is `failed`. */
|
|
315
|
+
needsAttention: boolean;
|
|
316
|
+
/** The version of the agent's plan; `null` before it has one. */
|
|
317
|
+
planVersion: number | null;
|
|
318
|
+
/** When the agent runs next; `null` when no run is scheduled. */
|
|
319
|
+
nextRunAt: string | null;
|
|
320
|
+
/** The `seq` of the newest change `monitors.changes` can serve now. */
|
|
321
|
+
watermark: number;
|
|
322
|
+
/** The latest compile of the plan; `null` when there has been none. */
|
|
323
|
+
compile: AgentCompileState | null;
|
|
324
|
+
};
|
|
325
|
+
/** The monitor agent's document: `monitors.agent`. A field is there only when the
|
|
326
|
+
* router sent it. The rest of the document (the plan, the counts, the runs) is in `raw`. */
|
|
327
|
+
type AgentDocument = {
|
|
328
|
+
/** Such as `compiling`, `ready`, `paused`, `failed` or `ended`. */
|
|
329
|
+
status?: string;
|
|
330
|
+
query?: string;
|
|
331
|
+
frequency?: string;
|
|
332
|
+
/** The version of the plan; 0 while the agent compiles. */
|
|
333
|
+
specVersion?: number;
|
|
334
|
+
/** The agent's spending limits; `null` when none are set. */
|
|
335
|
+
budget?: Json | null;
|
|
336
|
+
/** What the agent has spent, in US dollars. */
|
|
337
|
+
spendUsd?: number;
|
|
280
338
|
raw: Json;
|
|
281
339
|
};
|
|
340
|
+
/** The item a change is about. `entityId` is `null` for a change to the whole monitor,
|
|
341
|
+
* such as a run or a plan change. */
|
|
342
|
+
type ChangeSubject = {
|
|
343
|
+
entityId: string | null;
|
|
344
|
+
name: string | null;
|
|
345
|
+
};
|
|
346
|
+
/** One change the monitor agent made. */
|
|
347
|
+
type ChangeRecord = {
|
|
348
|
+
/** The change's place in the stream. It grows with every change and is never reused.
|
|
349
|
+
* Pass the last one you handled as `cursor` to read on from there. */
|
|
350
|
+
seq: number;
|
|
351
|
+
/** The change's own type, such as `new_object`. */
|
|
352
|
+
type: string;
|
|
353
|
+
/** What happened: one of the six kinds `entity_added`, `value_changed`,
|
|
354
|
+
* `fact_status_changed`, `alert`, `run` or `plan_changed`. */
|
|
355
|
+
kind: string;
|
|
356
|
+
monitorId: string;
|
|
357
|
+
subject: ChangeSubject;
|
|
358
|
+
/** What it was before, as the router sent it; `null` when there is no before. Its shape
|
|
359
|
+
* depends on `kind`. */
|
|
360
|
+
before: unknown;
|
|
361
|
+
/** What it is now, as the router sent it. */
|
|
362
|
+
after: unknown;
|
|
363
|
+
/** The facts behind the change; empty when the router names none. */
|
|
364
|
+
factIds: string[];
|
|
365
|
+
/** When it happened, ISO 8601. */
|
|
366
|
+
at: string;
|
|
367
|
+
raw: Json;
|
|
368
|
+
};
|
|
369
|
+
/** One page of `monitors.changes`. */
|
|
370
|
+
type ChangesPage = {
|
|
371
|
+
changes: ChangeRecord[];
|
|
372
|
+
/** Keep this and pass it as `cursor` to read the changes after this page. On a full
|
|
373
|
+
* page (`limit` changes) it is the `seq` of the last change. On a shorter page, an
|
|
374
|
+
* empty one included, it is `watermark`: the read got that far, past the changes
|
|
375
|
+
* that `kinds` left out too. */
|
|
376
|
+
nextCursor: number;
|
|
377
|
+
/** The `seq` of the newest change that can be read now. You are caught up when
|
|
378
|
+
* `nextCursor` equals it, or when a page is empty. */
|
|
379
|
+
watermark: number;
|
|
380
|
+
};
|
|
381
|
+
/** Options for `monitors.changes`. */
|
|
382
|
+
type MonitorChangesOptions = {
|
|
383
|
+
/** Read the changes after this `seq`. If you leave it out, the page starts at the
|
|
384
|
+
* first change. Do not send it with `since`. */
|
|
385
|
+
cursor?: number;
|
|
386
|
+
/** Read from this time on: a `Date`, or an ISO 8601 time with an offset such as
|
|
387
|
+
* `"2026-11-03T12:00:00Z"`. Do not send it with `cursor`. */
|
|
388
|
+
since?: string | Date;
|
|
389
|
+
/** Only these kinds of change: `entity_added`, `value_changed`, `fact_status_changed`,
|
|
390
|
+
* `alert`, `run` or `plan_changed`, for example `["alert", "run"]`. Another name is a
|
|
391
|
+
* 400 (`kinds_invalid`). An empty list is no filter. */
|
|
392
|
+
kinds?: string[];
|
|
393
|
+
/** How many changes to return (server default 200, maximum 500). */
|
|
394
|
+
limit?: number;
|
|
395
|
+
signal?: AbortSignal;
|
|
396
|
+
};
|
|
397
|
+
/** Options for `monitors.iterateChanges`. */
|
|
398
|
+
type MonitorIterateChangesOptions = {
|
|
399
|
+
/** Read the changes after this `seq`. If you leave it out, the walk starts at the
|
|
400
|
+
* first change. */
|
|
401
|
+
cursor?: number;
|
|
402
|
+
signal?: AbortSignal;
|
|
403
|
+
};
|
|
404
|
+
/** Options for `monitors.list` and `monitors.listPage`. */
|
|
405
|
+
type MonitorListOptions = {
|
|
406
|
+
/** How many to return (server default 50, maximum 200). */
|
|
407
|
+
limit?: number;
|
|
408
|
+
/** The `nextCursor` of the page before. */
|
|
409
|
+
cursor?: string;
|
|
410
|
+
signal?: AbortSignal;
|
|
411
|
+
};
|
|
412
|
+
/** One page of `monitors.listPage`. */
|
|
413
|
+
type MonitorPage = {
|
|
414
|
+
monitors: Monitor[];
|
|
415
|
+
/** Pass as `cursor` to get the next page; `null` on the last page. */
|
|
416
|
+
nextCursor: string | null;
|
|
417
|
+
};
|
|
282
418
|
/** The `telem.monitors` namespace. */
|
|
283
419
|
type MonitorsResource = {
|
|
284
420
|
create(query: string, options?: MonitorCreateOptions): Promise<Monitor>;
|
|
285
|
-
list(options?:
|
|
286
|
-
|
|
287
|
-
signal?: AbortSignal;
|
|
288
|
-
}): Promise<Monitor[]>;
|
|
421
|
+
list(options?: MonitorListOptions): Promise<Monitor[]>;
|
|
422
|
+
listPage(options?: MonitorListOptions): Promise<MonitorPage>;
|
|
289
423
|
get(monitorId: string, options?: {
|
|
290
424
|
signal?: AbortSignal;
|
|
291
425
|
}): Promise<Monitor>;
|
|
@@ -294,6 +428,14 @@ type MonitorsResource = {
|
|
|
294
428
|
delete(monitorId: string, options?: {
|
|
295
429
|
signal?: AbortSignal;
|
|
296
430
|
}): Promise<void>;
|
|
431
|
+
/** Read the monitor agent's document. A monitor without an agent answers 404. */
|
|
432
|
+
agent(monitorId: string, options?: {
|
|
433
|
+
signal?: AbortSignal;
|
|
434
|
+
}): Promise<AgentDocument>;
|
|
435
|
+
/** One page of the agent's changes. Keep `nextCursor` and pass it back as `cursor`. */
|
|
436
|
+
changes(monitorId: string, options?: MonitorChangesOptions): Promise<ChangesPage>;
|
|
437
|
+
/** Every change after `cursor`, page by page, until you are caught up. */
|
|
438
|
+
iterateChanges(monitorId: string, options?: MonitorIterateChangesOptions): AsyncGenerator<ChangeRecord, void, undefined>;
|
|
297
439
|
};
|
|
298
440
|
|
|
299
441
|
/**
|
|
@@ -437,7 +579,8 @@ declare class Telem {
|
|
|
437
579
|
readonly maxRetries: number;
|
|
438
580
|
/** The session read surface: `list` and `results(id)`. */
|
|
439
581
|
readonly sessions: SessionsResource;
|
|
440
|
-
/** Monitors: `create`, `list`, `get`, `update`, `poll`, `delete
|
|
582
|
+
/** Monitors: `create`, `list`, `listPage`, `get`, `update`, `poll`, `delete`, and the
|
|
583
|
+
* agent reads `agent`, `changes` and `iterateChanges`. */
|
|
441
584
|
readonly monitors: MonitorsResource;
|
|
442
585
|
/**
|
|
443
586
|
* @param options - An API key string, or an options object. Anything left unset
|
|
@@ -470,4 +613,4 @@ declare class Telem {
|
|
|
470
613
|
providers(): Promise<ProviderInfo[]>;
|
|
471
614
|
}
|
|
472
615
|
|
|
473
|
-
export { type FetchOptions, type FetchResponse, type FetchResult, type Json, type Monitor, type MonitorCreateOptions, type MonitorPollOptions, type MonitorUpdateOptions, type MonitorsResource, type ProviderInfo, type ProviderRun, RESERVED_METADATA, type SearchDefaults, type SearchOptions, type SearchResponse, type SearchResult, type SessionResults, type SessionSummary, type SessionsResource, type SnapshotArgs, Telem, type TelemClientErrorCode, TelemError, type TelemErrorOptions, type TelemOptions, TimeoutError, type TrajectoryArgs, type TrajectoryEnvelope, type TrajectorySnapshot, buildMetadata, buildSnapshot, contentAnchor, Telem as default, eventNodeKey, fingerprint, sessionKey, snapshotNodeKey, toolMarker, verifyWebhook, windowAnchor, withTrajectory };
|
|
616
|
+
export { type AgentCompileState, type AgentDocument, type AgentState, type ChangeRecord, type ChangeSubject, type ChangesPage, type FetchOptions, type FetchResponse, type FetchResult, type Json, type Monitor, type MonitorChangesOptions, type MonitorCreateOptions, type MonitorIterateChangesOptions, type MonitorListOptions, type MonitorPage, type MonitorPollOptions, type MonitorUpdateOptions, type MonitorsResource, type ProviderInfo, type ProviderRun, RESERVED_METADATA, type SearchDefaults, type SearchOptions, type SearchResponse, type SearchResult, type SessionResults, type SessionSummary, type SessionsResource, type SnapshotArgs, Telem, type TelemClientErrorCode, TelemError, type TelemErrorOptions, type TelemOptions, TimeoutError, type TrajectoryArgs, type TrajectoryEnvelope, type TrajectorySnapshot, buildMetadata, buildSnapshot, contentAnchor, Telem as default, eventNodeKey, fingerprint, sessionKey, snapshotNodeKey, toolMarker, verifyWebhook, windowAnchor, withTrajectory };
|
package/dist/index.js
CHANGED
|
@@ -19,10 +19,10 @@ import {
|
|
|
19
19
|
windowAnchor,
|
|
20
20
|
wireMetadata,
|
|
21
21
|
withTrajectory
|
|
22
|
-
} from "./chunk-
|
|
22
|
+
} from "./chunk-SQ3ZZA72.js";
|
|
23
23
|
|
|
24
24
|
// src/version.ts
|
|
25
|
-
var VERSION = "0.
|
|
25
|
+
var VERSION = "0.4.0";
|
|
26
26
|
|
|
27
27
|
// src/config.ts
|
|
28
28
|
var DEFAULT_BASE_URL = "https://router.telem.ai";
|
|
@@ -82,6 +82,7 @@ function resolveConfig(options) {
|
|
|
82
82
|
if (typeof send !== "function") {
|
|
83
83
|
throw invalidOption("no fetch on this runtime: pass one with the `fetch` option");
|
|
84
84
|
}
|
|
85
|
+
if (typeof opts.apiKey === "string" && !opts.apiKey.trim()) throw invalidOption("apiKey is empty");
|
|
85
86
|
let apiKey = opts.apiKey || env.TELEM_API_KEY || void 0;
|
|
86
87
|
let baseUrl = opts.baseUrl || env.TELEM_BASE_URL || void 0;
|
|
87
88
|
if (apiKey === void 0 || baseUrl === void 0) {
|
|
@@ -120,12 +121,20 @@ function resolveConfig(options) {
|
|
|
120
121
|
autoRouting: opts.autoRouting ?? (trimBlank(env.TELEM_AUTO_ROUTING ?? "") || void 0),
|
|
121
122
|
maxRoutingProviders: opts.maxRoutingProviders ?? intEnv(env.TELEM_MAX_ROUTING_PROVIDERS),
|
|
122
123
|
topic: opts.topic ?? (trimBlank(env.TELEM_TOPIC ?? "") || void 0)
|
|
124
|
+
},
|
|
125
|
+
// Fetch defaults: env var only, parsed as the shared option table parses it (CSV,
|
|
126
|
+
// a trimmed name, a "1"-only flag); the tier is lowercased, as the agent plugins
|
|
127
|
+
// send it. No constructor option, and no config file, as above.
|
|
128
|
+
fetchDefaults: {
|
|
129
|
+
providers: csvEnv(env.TELEM_FETCH_PROVIDERS),
|
|
130
|
+
tier: trimBlank(env.TELEM_FETCH_TIER ?? "").toLowerCase() || void 0,
|
|
131
|
+
noCache: env.TELEM_FETCH_NO_CACHE === "1" || void 0
|
|
123
132
|
}
|
|
124
133
|
};
|
|
125
134
|
}
|
|
126
135
|
|
|
127
136
|
// src/methods/fetch.ts
|
|
128
|
-
function fetchBody(url, options) {
|
|
137
|
+
function fetchBody(url, options, defaults) {
|
|
129
138
|
const urls = stringList(
|
|
130
139
|
typeof url === "string" ? [url] : url,
|
|
131
140
|
"fetch() requires at least one URL",
|
|
@@ -133,11 +142,16 @@ function fetchBody(url, options) {
|
|
|
133
142
|
);
|
|
134
143
|
const { metadata, sessionId } = wireMetadata(options, "fetch");
|
|
135
144
|
const body = { urls, metadata };
|
|
145
|
+
const providers2 = options.providers ?? defaults.providers;
|
|
146
|
+
const tier = options.tier ?? defaults.tier;
|
|
147
|
+
const noCache = options.noCache ?? defaults.noCache;
|
|
136
148
|
const block = {};
|
|
137
|
-
if (
|
|
149
|
+
if (providers2 !== void 0) block.providers = providers2;
|
|
138
150
|
if (options.inlineContent !== void 0) block.inline_content = options.inlineContent;
|
|
139
151
|
if (options.inlineMaxChars !== void 0) block.inline_max_chars = options.inlineMaxChars;
|
|
140
152
|
if (options.contentFormat !== void 0) block.content_format = options.contentFormat;
|
|
153
|
+
if (tier !== void 0) block.tier = tier;
|
|
154
|
+
if (noCache !== void 0) block.no_cache = noCache;
|
|
141
155
|
if (Object.keys(block).length) body.options = block;
|
|
142
156
|
if (sessionId !== void 0) body.session_id = sessionId;
|
|
143
157
|
return body;
|
|
@@ -178,12 +192,17 @@ function buildFetchResponse(interaction) {
|
|
|
178
192
|
};
|
|
179
193
|
}
|
|
180
194
|
async function fetchUrls(config, url, options) {
|
|
181
|
-
const body = fetchBody(url, options);
|
|
195
|
+
const body = fetchBody(url, options, config.fetchDefaults);
|
|
182
196
|
return buildFetchResponse(await request(config, "POST", "/v1/fetch", body, options.signal));
|
|
183
197
|
}
|
|
184
198
|
|
|
185
199
|
// src/methods/search.ts
|
|
186
200
|
var MIN_SCHEMA_VERSION = 2;
|
|
201
|
+
function providersRefusal(include, includeFromCall, excludeFromCall) {
|
|
202
|
+
const where = (half, env, fromCall) => fromCall ? `the ${half} search() option` : `the client's ${half} or ${env}`;
|
|
203
|
+
const names = include.join(", ");
|
|
204
|
+
return `providersExclude removes every provider in providersInclude (${names}), so no provider is left and no search was sent. Remove ${names} from providersInclude (set by ${where("providersInclude", "TELEM_PROVIDERS_INCLUDE", includeFromCall)}) or from providersExclude (set by ${where("providersExclude", "TELEM_PROVIDERS_EXCLUDE", excludeFromCall)}).`;
|
|
205
|
+
}
|
|
187
206
|
function searchBlock(defaults, options) {
|
|
188
207
|
const fromCallTier = options.tier !== void 0;
|
|
189
208
|
const fromCallFields = options.fields !== void 0;
|
|
@@ -197,7 +216,13 @@ function searchBlock(defaults, options) {
|
|
|
197
216
|
let exclude = options.providersExclude ?? defaults.providersExclude;
|
|
198
217
|
if (include !== void 0 && exclude !== void 0) {
|
|
199
218
|
const excluded = new Set(exclude);
|
|
200
|
-
|
|
219
|
+
const kept = include.filter((name) => !excluded.has(name));
|
|
220
|
+
if (include.length && !kept.length) {
|
|
221
|
+
throw invalidRequest(
|
|
222
|
+
providersRefusal(include, options.providersInclude !== void 0, options.providersExclude !== void 0)
|
|
223
|
+
);
|
|
224
|
+
}
|
|
225
|
+
include = kept;
|
|
201
226
|
exclude = void 0;
|
|
202
227
|
}
|
|
203
228
|
const includeFullContent = options.includeFullContent ?? defaults.includeFullContent;
|
|
@@ -307,7 +332,8 @@ function providerRun(run) {
|
|
|
307
332
|
related: envelope.related ?? null,
|
|
308
333
|
verticals: envelope.verticals ?? null,
|
|
309
334
|
usage: envelope.usage ?? null,
|
|
310
|
-
warnings: asArray(envelope.warnings)
|
|
335
|
+
warnings: asArray(envelope.warnings),
|
|
336
|
+
sameStory: isObject(envelope.same_story) ? envelope.same_story : null
|
|
311
337
|
};
|
|
312
338
|
}
|
|
313
339
|
function buildSearchResponse(interaction) {
|
|
@@ -331,9 +357,25 @@ async function search(config, query, options) {
|
|
|
331
357
|
}
|
|
332
358
|
|
|
333
359
|
// src/methods/monitors.ts
|
|
360
|
+
function agentStateFrom(data) {
|
|
361
|
+
return {
|
|
362
|
+
engine: String(data.engine ?? ""),
|
|
363
|
+
status: String(data.status ?? ""),
|
|
364
|
+
needsAttention: data.needs_attention === true,
|
|
365
|
+
planVersion: typeof data.plan_version === "number" ? data.plan_version : null,
|
|
366
|
+
nextRunAt: typeof data.next_run_at === "string" ? data.next_run_at : null,
|
|
367
|
+
watermark: Number(data.watermark ?? 0),
|
|
368
|
+
// No compile job yet is null, not an object of empty strings.
|
|
369
|
+
compile: isObject(data.compile) ? {
|
|
370
|
+
jobId: String(data.compile.job_id ?? ""),
|
|
371
|
+
status: String(data.compile.status ?? ""),
|
|
372
|
+
error: typeof data.compile.error === "string" ? data.compile.error : null
|
|
373
|
+
} : null
|
|
374
|
+
};
|
|
375
|
+
}
|
|
334
376
|
function monitorFrom(body) {
|
|
335
377
|
const data = asObject(body);
|
|
336
|
-
|
|
378
|
+
const monitor = {
|
|
337
379
|
id: String(data.id ?? ""),
|
|
338
380
|
query: data.query ?? "",
|
|
339
381
|
frequency: data.frequency ?? "",
|
|
@@ -346,12 +388,85 @@ function monitorFrom(body) {
|
|
|
346
388
|
webhookSecret: data.webhook_secret ?? null,
|
|
347
389
|
raw: data
|
|
348
390
|
};
|
|
391
|
+
if (data.agent_state !== void 0) {
|
|
392
|
+
monitor.agentState = isObject(data.agent_state) ? agentStateFrom(data.agent_state) : null;
|
|
393
|
+
}
|
|
394
|
+
return monitor;
|
|
395
|
+
}
|
|
396
|
+
function agentDocumentFrom(body) {
|
|
397
|
+
const data = asObject(body);
|
|
398
|
+
const document = { raw: data };
|
|
399
|
+
if (typeof data.status === "string") document.status = data.status;
|
|
400
|
+
if (typeof data.query === "string") document.query = data.query;
|
|
401
|
+
if (typeof data.frequency === "string") document.frequency = data.frequency;
|
|
402
|
+
if (typeof data.spec_version === "number") document.specVersion = data.spec_version;
|
|
403
|
+
if (data.budget !== void 0) document.budget = isObject(data.budget) ? data.budget : null;
|
|
404
|
+
if (typeof data.spend_usd === "number") document.spendUsd = data.spend_usd;
|
|
405
|
+
return document;
|
|
406
|
+
}
|
|
407
|
+
function changeRecordFrom(entry) {
|
|
408
|
+
const subject = asObject(entry.subject);
|
|
409
|
+
return {
|
|
410
|
+
seq: Number(entry.seq ?? 0),
|
|
411
|
+
type: String(entry.type ?? ""),
|
|
412
|
+
kind: String(entry.kind ?? ""),
|
|
413
|
+
monitorId: String(entry.monitor_id ?? ""),
|
|
414
|
+
subject: {
|
|
415
|
+
entityId: typeof subject.entity_id === "string" ? subject.entity_id : null,
|
|
416
|
+
name: typeof subject.name === "string" ? subject.name : null
|
|
417
|
+
},
|
|
418
|
+
// The values depend on the kind (an object, a status string, nothing): as sent.
|
|
419
|
+
before: entry.before ?? null,
|
|
420
|
+
after: entry.after ?? null,
|
|
421
|
+
factIds: asArray(entry.fact_ids).map(String),
|
|
422
|
+
at: String(entry.at ?? ""),
|
|
423
|
+
raw: entry
|
|
424
|
+
};
|
|
425
|
+
}
|
|
426
|
+
function changesPageFrom(body) {
|
|
427
|
+
const data = asObject(body);
|
|
428
|
+
return {
|
|
429
|
+
changes: asArray(data.changes).filter(isObject).map(changeRecordFrom),
|
|
430
|
+
nextCursor: Number(data.next_cursor ?? 0),
|
|
431
|
+
watermark: Number(data.watermark ?? 0)
|
|
432
|
+
};
|
|
433
|
+
}
|
|
434
|
+
function listQuery(options) {
|
|
435
|
+
const params = new URLSearchParams();
|
|
436
|
+
if (options.limit !== void 0) params.set("limit", String(options.limit));
|
|
437
|
+
if (options.cursor !== void 0) params.set("cursor", options.cursor);
|
|
438
|
+
const query = params.toString();
|
|
439
|
+
return query ? `?${query}` : "";
|
|
440
|
+
}
|
|
441
|
+
function sinceParam(since) {
|
|
442
|
+
if (typeof since === "string") return since;
|
|
443
|
+
if (Number.isNaN(since.getTime())) throw invalidRequest("since is not a valid date");
|
|
444
|
+
return since.toISOString();
|
|
445
|
+
}
|
|
446
|
+
function changesQuery(options) {
|
|
447
|
+
const params = new URLSearchParams();
|
|
448
|
+
if (options.cursor !== void 0) params.set("cursor", String(options.cursor));
|
|
449
|
+
if (options.since !== void 0) params.set("since", sinceParam(options.since));
|
|
450
|
+
if (options.kinds !== void 0) params.set("kinds", options.kinds.join(","));
|
|
451
|
+
if (options.limit !== void 0) params.set("limit", String(options.limit));
|
|
452
|
+
const query = params.toString();
|
|
453
|
+
return query ? `?${query}` : "";
|
|
349
454
|
}
|
|
350
455
|
function createMonitors(config) {
|
|
351
456
|
const path = (monitorId, suffix = "") => {
|
|
352
457
|
if (!monitorId || /^\.+$/.test(monitorId)) throw invalidRequest("a monitor id is required");
|
|
353
458
|
return `/v1/monitors/${encodeURIComponent(monitorId)}${suffix}`;
|
|
354
459
|
};
|
|
460
|
+
const listPage = async (options = {}) => {
|
|
461
|
+
const route = `/v1/monitors${listQuery(options)}`;
|
|
462
|
+
const data = asObject(await request(config, "GET", route, void 0, options.signal));
|
|
463
|
+
const nextCursor = typeof data.next_cursor === "string" ? data.next_cursor : null;
|
|
464
|
+
return { monitors: asArray(data.monitors).map(monitorFrom), nextCursor };
|
|
465
|
+
};
|
|
466
|
+
const changes = async (monitorId, options = {}) => {
|
|
467
|
+
const route = `${path(monitorId, "/agent/changes")}${changesQuery(options)}`;
|
|
468
|
+
return changesPageFrom(await request(config, "GET", route, void 0, options.signal));
|
|
469
|
+
};
|
|
355
470
|
return {
|
|
356
471
|
/** Create a monitor. Telem runs `query` on the schedule. */
|
|
357
472
|
async create(query, options = {}) {
|
|
@@ -365,15 +480,25 @@ function createMonitors(config) {
|
|
|
365
480
|
if (options.metadata !== void 0) body.metadata = options.metadata;
|
|
366
481
|
if (options.webhookUrl !== void 0) body.webhook_url = options.webhookUrl;
|
|
367
482
|
if (options.ttl !== void 0) body.ttl = options.ttl;
|
|
368
|
-
|
|
483
|
+
if (options.agent !== void 0) body.agent = options.agent;
|
|
484
|
+
const data = await request(config, "POST", "/v1/monitors", body, options.signal, "rate_limit").catch(
|
|
485
|
+
(error) => {
|
|
486
|
+
if (error instanceof TimeoutError) {
|
|
487
|
+
throw new TimeoutError(
|
|
488
|
+
`${error.message}. The monitor may exist: list monitors before you create it again.`,
|
|
489
|
+
error.cause
|
|
490
|
+
);
|
|
491
|
+
}
|
|
492
|
+
throw error;
|
|
493
|
+
}
|
|
494
|
+
);
|
|
369
495
|
return monitorFrom(data);
|
|
370
496
|
},
|
|
371
|
-
/** List your monitors, newest first
|
|
497
|
+
/** List your monitors, newest first. `listPage` also gives the next cursor. */
|
|
372
498
|
async list(options = {}) {
|
|
373
|
-
|
|
374
|
-
const body = await request(config, "GET", `/v1/monitors${query}`, void 0, options.signal);
|
|
375
|
-
return asArray(asObject(body).monitors).map(monitorFrom);
|
|
499
|
+
return (await listPage(options)).monitors;
|
|
376
500
|
},
|
|
501
|
+
listPage,
|
|
377
502
|
/** Get one monitor. */
|
|
378
503
|
async get(monitorId, options = {}) {
|
|
379
504
|
return monitorFrom(await request(config, "GET", path(monitorId), void 0, options.signal));
|
|
@@ -383,7 +508,7 @@ function createMonitors(config) {
|
|
|
383
508
|
const body = {};
|
|
384
509
|
if (options.status !== void 0) body.status = options.status;
|
|
385
510
|
if (options.frequency !== void 0) body.frequency = options.frequency;
|
|
386
|
-
if (options.webhookUrl !== void 0) body.webhook_url = options.webhookUrl;
|
|
511
|
+
if (options.webhookUrl !== void 0) body.webhook_url = options.webhookUrl || null;
|
|
387
512
|
const route = path(monitorId);
|
|
388
513
|
return monitorFrom(await request(config, "PATCH", route, body, options.signal));
|
|
389
514
|
},
|
|
@@ -399,6 +524,23 @@ function createMonitors(config) {
|
|
|
399
524
|
/** Delete a monitor. A repeat deletes what a failed delete left. */
|
|
400
525
|
async delete(monitorId, options = {}) {
|
|
401
526
|
await request(config, "DELETE", path(monitorId), void 0, options.signal);
|
|
527
|
+
},
|
|
528
|
+
/** Read the monitor agent's document. A monitor without an agent answers 404. */
|
|
529
|
+
async agent(monitorId, options = {}) {
|
|
530
|
+
const route = path(monitorId, "/agent");
|
|
531
|
+
return agentDocumentFrom(await request(config, "GET", route, void 0, options.signal));
|
|
532
|
+
},
|
|
533
|
+
/** One page of the agent's changes. Keep `nextCursor` and pass it back as `cursor`. */
|
|
534
|
+
changes,
|
|
535
|
+
/** Every change after `cursor`, page by page, until you are caught up. */
|
|
536
|
+
async *iterateChanges(monitorId, options = {}) {
|
|
537
|
+
let cursor = options.cursor ?? 0;
|
|
538
|
+
for (; ; ) {
|
|
539
|
+
const page = await changes(monitorId, { cursor, signal: options.signal });
|
|
540
|
+
for (const change of page.changes) yield change;
|
|
541
|
+
if (!page.changes.length || page.nextCursor <= cursor || page.nextCursor >= page.watermark) return;
|
|
542
|
+
cursor = page.nextCursor;
|
|
543
|
+
}
|
|
402
544
|
}
|
|
403
545
|
};
|
|
404
546
|
}
|
|
@@ -431,7 +573,8 @@ async function providers(config) {
|
|
|
431
573
|
method: entry.method ?? null,
|
|
432
574
|
url: entry.url ?? null,
|
|
433
575
|
normalized: entry.normalized ?? false,
|
|
434
|
-
tiers: asArray(entry.tiers)
|
|
576
|
+
tiers: asArray(entry.tiers),
|
|
577
|
+
autoRouted: entry.auto_routed ?? null
|
|
435
578
|
}));
|
|
436
579
|
}
|
|
437
580
|
|
|
@@ -500,7 +643,8 @@ var Telem = class {
|
|
|
500
643
|
maxRetries;
|
|
501
644
|
/** The session read surface: `list` and `results(id)`. */
|
|
502
645
|
sessions;
|
|
503
|
-
/** Monitors: `create`, `list`, `get`, `update`, `poll`, `delete
|
|
646
|
+
/** Monitors: `create`, `list`, `listPage`, `get`, `update`, `poll`, `delete`, and the
|
|
647
|
+
* agent reads `agent`, `changes` and `iterateChanges`. */
|
|
504
648
|
monitors;
|
|
505
649
|
#config;
|
|
506
650
|
/**
|
package/dist/vercel/index.js
CHANGED