@devkitio/faultlens 0.1.5 → 1.0.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.
@@ -1 +1,15 @@
1
1
  #!/usr/bin/env node
2
+ interface CliOptions {
3
+ endpoint: string;
4
+ token: string | undefined;
5
+ root: string;
6
+ release: string;
7
+ environment: string;
8
+ dist: string;
9
+ dryRun: boolean;
10
+ deleteAfterVerify: boolean;
11
+ }
12
+ declare function resolveCliOptions(args: string[], env: NodeJS.ProcessEnv): CliOptions;
13
+ declare function runFaultLensCli(args: string[], env?: NodeJS.ProcessEnv): Promise<void>;
14
+
15
+ export { resolveCliOptions, runFaultLensCli };
package/dist/cli/index.js CHANGED
@@ -1,6 +1,7 @@
1
1
  #!/usr/bin/env node
2
2
  import { lstat, readdir, readFile, writeFile, unlink } from 'fs/promises';
3
3
  import path from 'path';
4
+ import { fileURLToPath } from 'url';
4
5
  import { randomUUID, createHash } from 'crypto';
5
6
 
6
7
  var DEBUG_ID_PATTERN = /^[0-9a-f]{8}-[0-9a-f]{4}-[1-8][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/i;
@@ -95,30 +96,48 @@ async function removeUploadedSourceMaps(artifacts) {
95
96
  }
96
97
 
97
98
  // src/cli/index.ts
98
- function argument(name) {
99
- const index = process.argv.indexOf(name);
100
- return index >= 0 ? process.argv[index + 1] : void 0;
99
+ function argument(args, name) {
100
+ const index = args.indexOf(name);
101
+ return index >= 0 ? args[index + 1] : void 0;
101
102
  }
102
103
  function required(value, label) {
103
104
  if (!value) throw new Error(`\u7F3A\u5C11 ${label}`);
104
105
  return value;
105
106
  }
106
- function environment(name, legacyName) {
107
- return process.env[name] ?? process.env[legacyName];
107
+ function environment(env, name, legacyName) {
108
+ return env[name] ?? env[legacyName];
108
109
  }
109
- function options() {
110
+ function endpoint(value) {
111
+ const parsed = new URL(required(value, "--endpoint"));
112
+ if (parsed.protocol !== "https:" && parsed.hostname !== "localhost") {
113
+ throw new Error("\u670D\u52A1\u5730\u5740\u5FC5\u987B\u4F7F\u7528 HTTPS");
114
+ }
115
+ if (parsed.username || parsed.password || parsed.pathname !== "/" || parsed.search || parsed.hash) {
116
+ throw new Error("\u670D\u52A1\u5730\u5740\u5FC5\u987B\u662F\u65E0\u51ED\u636E\u3001\u8DEF\u5F84\u3001\u67E5\u8BE2\u53C2\u6570\u548C\u7247\u6BB5\u7684\u7AD9\u70B9\u6839\u5730\u5740");
117
+ }
118
+ return parsed.origin;
119
+ }
120
+ function resolveCliOptions(args, env) {
110
121
  return {
111
- endpoint: required(argument("--endpoint") ?? environment("FAULTLENS_SOURCEMAP_ENDPOINT", "MOQU_SOURCEMAP_ENDPOINT"), "--endpoint"),
112
- token: required(argument("--token") ?? environment("FAULTLENS_SOURCEMAP_TOKEN", "MOQU_SOURCEMAP_TOKEN"), "--token \u6216 FAULTLENS_SOURCEMAP_TOKEN"),
113
- root: path.resolve(required(argument("--root") ?? environment("FAULTLENS_SOURCEMAP_ROOT", "MOQU_SOURCEMAP_ROOT"), "--root \u6216 FAULTLENS_SOURCEMAP_ROOT")),
114
- release: required(argument("--release") ?? environment("FAULTLENS_RELEASE", "MOQU_RELEASE"), "--release \u6216 FAULTLENS_RELEASE"),
122
+ endpoint: endpoint(
123
+ argument(args, "--endpoint") ?? environment(env, "FAULTLENS_SOURCEMAP_ENDPOINT", "MOQU_SOURCEMAP_ENDPOINT")
124
+ ),
125
+ token: argument(args, "--token") ?? environment(env, "FAULTLENS_SOURCEMAP_TOKEN", "MOQU_SOURCEMAP_TOKEN"),
126
+ root: path.resolve(required(
127
+ argument(args, "--root") ?? environment(env, "FAULTLENS_SOURCEMAP_ROOT", "MOQU_SOURCEMAP_ROOT"),
128
+ "--root \u6216 FAULTLENS_SOURCEMAP_ROOT"
129
+ )),
130
+ release: required(
131
+ argument(args, "--release") ?? environment(env, "FAULTLENS_RELEASE", "MOQU_RELEASE"),
132
+ "--release \u6216 FAULTLENS_RELEASE"
133
+ ),
115
134
  environment: required(
116
- argument("--environment") ?? environment("FAULTLENS_ENVIRONMENT", "MOQU_ENVIRONMENT"),
135
+ argument(args, "--environment") ?? environment(env, "FAULTLENS_ENVIRONMENT", "MOQU_ENVIRONMENT"),
117
136
  "--environment \u6216 FAULTLENS_ENVIRONMENT"
118
137
  ),
119
- dist: argument("--dist") ?? environment("FAULTLENS_DIST", "MOQU_DIST") ?? "default",
120
- dryRun: process.argv.includes("--dry-run"),
121
- deleteAfterVerify: process.argv.includes("--delete-after-verify")
138
+ dist: argument(args, "--dist") ?? environment(env, "FAULTLENS_DIST", "MOQU_DIST") ?? "default",
139
+ dryRun: args.includes("--dry-run"),
140
+ deleteAfterVerify: args.includes("--delete-after-verify")
122
141
  };
123
142
  }
124
143
  async function upload(config, artifacts) {
@@ -126,11 +145,12 @@ async function upload(config, artifacts) {
126
145
  console.info(`\u6F14\u7EC3\u5B8C\u6210\uFF1A\u5C06\u4E0A\u4F20 ${artifacts.length} \u4E2A Source Map \u6587\u4EF6`);
127
146
  return;
128
147
  }
148
+ const token = required(config.token, "--token \u6216 FAULTLENS_SOURCEMAP_TOKEN");
129
149
  for (const current of artifacts) {
130
150
  const response = await fetch(`${config.endpoint.replace(/\/$/, "")}/v1/admin/source-maps/artifacts`, {
131
151
  method: "PUT",
132
152
  headers: {
133
- authorization: `Bearer ${config.token}`,
153
+ authorization: `Bearer ${token}`,
134
154
  "content-type": "application/octet-stream",
135
155
  "x-faultlens-release": config.release,
136
156
  "x-faultlens-environment": config.environment,
@@ -151,10 +171,11 @@ async function upload(config, artifacts) {
151
171
  console.info(`\u4E0A\u4F20\u5B8C\u6210\uFF1A${artifacts.length} \u4E2A Source Map \u6587\u4EF6`);
152
172
  }
153
173
  async function verify(config, artifacts) {
174
+ const token = required(config.token, "--token \u6216 FAULTLENS_SOURCEMAP_TOKEN");
154
175
  const response = await fetch(`${config.endpoint.replace(/\/$/, "")}/v1/admin/source-maps/verify`, {
155
176
  method: "POST",
156
177
  headers: {
157
- authorization: `Bearer ${config.token}`,
178
+ authorization: `Bearer ${token}`,
158
179
  "content-type": "application/json"
159
180
  },
160
181
  body: JSON.stringify({
@@ -175,18 +196,16 @@ async function verify(config, artifacts) {
175
196
  console.info("Source Map \u5236\u54C1\u6E05\u5355\u4E0E\u670D\u52A1\u7AEF\u4E00\u81F4");
176
197
  }
177
198
  async function doctor(config) {
178
- const url = new URL(config.endpoint);
179
- if (url.protocol !== "https:" && url.hostname !== "localhost") throw new Error("\u670D\u52A1\u5730\u5740\u5FC5\u987B\u4F7F\u7528 HTTPS");
180
199
  if (process.versions.node.split(".")[0] !== "22") {
181
200
  console.warn(`\u5F53\u524D Node.js \u4E3A ${process.version}\uFF0C\u751F\u4EA7 CI \u5E94\u4F7F\u7528 Node.js 22`);
182
201
  }
183
202
  await lstat(config.root);
184
203
  console.info("CLI \u914D\u7F6E\u68C0\u67E5\u901A\u8FC7");
185
204
  }
186
- async function main() {
187
- const command = process.argv[2];
188
- const subcommand = process.argv[3];
189
- const config = options();
205
+ async function runFaultLensCli(args, env = process.env) {
206
+ const command = args[0];
207
+ const subcommand = args[1];
208
+ const config = resolveCliOptions(args, env);
190
209
  if (command === "doctor") return doctor(config);
191
210
  if (command !== "sourcemaps" || !["upload", "verify"].includes(subcommand ?? "")) {
192
211
  throw new Error("\u7528\u6CD5\uFF1Afaultlens sourcemaps <upload|verify> [\u53C2\u6570]\uFF0C\u6216 faultlens doctor [\u53C2\u6570]");
@@ -199,7 +218,12 @@ async function main() {
199
218
  }
200
219
  return verify(config, artifacts);
201
220
  }
202
- main().catch((error) => {
203
- console.error(error instanceof Error ? error.message : "CLI \u6267\u884C\u5931\u8D25");
204
- process.exitCode = 1;
205
- });
221
+ var currentFile = fileURLToPath(import.meta.url);
222
+ if (process.argv[1] && path.resolve(process.argv[1]) === currentFile) {
223
+ runFaultLensCli(process.argv.slice(2)).catch((error) => {
224
+ console.error(error instanceof Error ? error.message : "CLI \u6267\u884C\u5931\u8D25");
225
+ process.exitCode = 1;
226
+ });
227
+ }
228
+
229
+ export { resolveCliOptions, runFaultLensCli };
@@ -1,4 +1,4 @@
1
- import { E as ErrorMonitor } from '../types-DxONWOH8.js';
1
+ import { E as ErrorMonitor } from '../types-hWS-GSV1.js';
2
2
 
3
3
  interface ExpressRequestLike {
4
4
  method?: unknown;
@@ -1,4 +1,4 @@
1
- import { E as ErrorMonitor } from '../types-DxONWOH8.js';
1
+ import { E as ErrorMonitor } from '../types-hWS-GSV1.js';
2
2
 
3
3
  interface FaultLensFastifyPluginOptions {
4
4
  monitor: ErrorMonitor;
package/dist/index.d.ts CHANGED
@@ -1,6 +1,33 @@
1
- import { M as MonitorOptions, E as ErrorMonitor } from './types-DxONWOH8.js';
2
- export { B as Breadcrumb, C as CaptureOptions, a as ContextMode, I as IngestConfig, b as MonitorStatus } from './types-DxONWOH8.js';
1
+ import { T as TelemetryTransport, I as IngestConfig, a as TelemetryEnvelope, b as TelemetryTransportOutcome, E as ErrorMonitor, M as MonitorOptions } from './types-hWS-GSV1.js';
2
+ export { B as Breadcrumb, C as CaptureOptions, c as ContextMode, d as MonitorStatus, S as Span, e as SpanOptions, f as TelemetryOptions, g as TraceContext, W as WebVitalInput, h as formatTraceParent, p as parseTraceParent, t as traceContextHeaders } from './types-hWS-GSV1.js';
3
+
4
+ declare class FetchTelemetryTransport implements TelemetryTransport {
5
+ private readonly ingest;
6
+ private readonly fetcher;
7
+ private readonly now;
8
+ constructor(ingest: IngestConfig, fetcher?: typeof fetch, now?: () => number);
9
+ send(envelope: TelemetryEnvelope): Promise<TelemetryTransportOutcome>;
10
+ }
11
+
12
+ interface FetchInstrumentationTarget {
13
+ fetch: typeof fetch;
14
+ }
15
+ interface FetchInstrumentationOptions {
16
+ target?: FetchInstrumentationTarget;
17
+ shouldTrace?: (input: RequestInfo | URL, init?: RequestInit) => boolean;
18
+ shouldPropagateTraceContext?: (url: URL) => boolean;
19
+ }
20
+ interface XhrInstrumentationTarget {
21
+ XMLHttpRequest: typeof XMLHttpRequest;
22
+ }
23
+ interface XhrInstrumentationOptions {
24
+ target?: XhrInstrumentationTarget;
25
+ shouldTrace?: (method: string, url: URL | undefined) => boolean;
26
+ shouldPropagateTraceContext?: (url: URL) => boolean;
27
+ }
28
+ declare function installFetchInstrumentation(monitor: ErrorMonitor, options?: FetchInstrumentationOptions): () => void;
29
+ declare function installXhrInstrumentation(monitor: ErrorMonitor, options?: XhrInstrumentationOptions): () => void;
3
30
 
4
31
  declare function createErrorMonitor(options: MonitorOptions): ErrorMonitor;
5
32
 
6
- export { ErrorMonitor, MonitorOptions, createErrorMonitor };
33
+ export { ErrorMonitor, type FetchInstrumentationOptions, type FetchInstrumentationTarget, FetchTelemetryTransport, IngestConfig, MonitorOptions, type XhrInstrumentationOptions, type XhrInstrumentationTarget, createErrorMonitor, installFetchInstrumentation, installXhrInstrumentation };
package/dist/index.js CHANGED
@@ -1,2 +1,2 @@
1
- export { createErrorMonitor } from './chunk-K63I3OJT.js';
2
- import './chunk-LRHXSFK2.js';
1
+ export { createErrorMonitor, installFetchInstrumentation, installXhrInstrumentation } from './chunk-6LF3JLVG.js';
2
+ export { FetchTelemetryTransport, formatTraceParent, parseTraceParent, traceContextHeaders } from './chunk-ZUVQIOFO.js';
@@ -1,4 +1,52 @@
1
- import { M as MonitorOptions, c as EventTransport, d as EventEnvelope, T as TransportOutcome, R as RuntimeDependencies, E as ErrorMonitor } from '../types-DxONWOH8.js';
1
+ import { P as PersistentEventQueue, i as PersistedQueueItem, E as ErrorMonitor, M as MonitorOptions, T as TelemetryTransport, a as TelemetryEnvelope, b as TelemetryTransportOutcome, j as EventTransport, k as EventEnvelope, l as TransportOutcome, R as RemoteSdkConfig, m as RemoteConfigLoadResult, n as RuntimeDependencies } from '../types-hWS-GSV1.js';
2
+ import { ClientRequest } from 'node:http';
3
+
4
+ interface NodeQueueEncryptionKey {
5
+ id: string;
6
+ key: Uint8Array;
7
+ }
8
+ interface NodeEncryptedFileQueueOptions {
9
+ directory: string;
10
+ encryptionKeys: NodeQueueEncryptionKey[];
11
+ maxItems?: number;
12
+ maxBytes?: number;
13
+ maxAgeMs?: number;
14
+ lockTimeoutMs?: number;
15
+ staleLockMs?: number;
16
+ }
17
+ declare class NodeEncryptedFileQueue implements PersistentEventQueue {
18
+ private readonly directory;
19
+ private readonly keys;
20
+ private readonly maxItems;
21
+ private readonly maxBytes;
22
+ private readonly maxAgeMs;
23
+ private readonly lockTimeoutMs;
24
+ private readonly staleLockMs;
25
+ private serial;
26
+ constructor(options: NodeEncryptedFileQueueOptions);
27
+ load(now: number): Promise<PersistedQueueItem[]>;
28
+ put(item: PersistedQueueItem): Promise<void>;
29
+ remove(ids: string[]): Promise<void>;
30
+ clear(): Promise<void>;
31
+ private runExclusive;
32
+ private ensureDirectory;
33
+ private withLock;
34
+ private statePath;
35
+ private readItems;
36
+ private writeItems;
37
+ }
38
+
39
+ type NodeHttpRequest = (...args: unknown[]) => ClientRequest;
40
+ interface NodeHttpInstrumentationModule {
41
+ request: NodeHttpRequest;
42
+ get: NodeHttpRequest;
43
+ }
44
+ interface NodeHttpInstrumentationOptions {
45
+ modules?: NodeHttpInstrumentationModule[];
46
+ shouldTrace?: (method: string, url: URL | undefined) => boolean;
47
+ shouldPropagateTraceContext?: (url: URL | undefined) => boolean;
48
+ }
49
+ declare function installNodeHttpInstrumentation(monitor: ErrorMonitor, options?: NodeHttpInstrumentationOptions): () => void;
2
50
 
3
51
  interface NodeRelayIngestConfig {
4
52
  mode: "relay";
@@ -10,6 +58,7 @@ interface NodeRelayIngestConfig {
10
58
  interface NodeMonitorOptions extends Omit<MonitorOptions, "ingest"> {
11
59
  ingest: NodeRelayIngestConfig;
12
60
  captureGlobalErrors?: boolean;
61
+ persistentQueue?: NodeEncryptedFileQueueOptions;
13
62
  }
14
63
  interface NodeRelayTransportOptions {
15
64
  fetcher?: typeof fetch;
@@ -26,9 +75,19 @@ declare class NodeRelayTransport implements EventTransport {
26
75
  private readonly endpoint;
27
76
  constructor(ingest: NodeRelayIngestConfig, options?: NodeRelayTransportOptions);
28
77
  send(envelope: EventEnvelope): Promise<TransportOutcome>;
78
+ loadRemoteConfig(): Promise<RemoteSdkConfig | undefined>;
79
+ loadRemoteConfigResult(): Promise<RemoteConfigLoadResult>;
80
+ }
81
+ declare class NodeRelayTelemetryTransport implements TelemetryTransport {
82
+ private readonly ingest;
83
+ private readonly fetcher;
84
+ private readonly requestTimeoutMs;
85
+ private readonly endpoint;
86
+ constructor(ingest: NodeRelayIngestConfig, options?: Pick<NodeRelayTransportOptions, "fetcher" | "requestTimeoutMs">);
87
+ send(envelope: TelemetryEnvelope): Promise<TelemetryTransportOutcome>;
29
88
  }
30
89
  declare function createNodeErrorMonitor(options: NodeMonitorOptions, overrides?: {
31
90
  transport?: EventTransport;
32
91
  } & Partial<RuntimeDependencies>): ErrorMonitor;
33
92
 
34
- export { type NodeMonitorOptions, type NodeRelayIngestConfig, NodeRelayTransport, type NodeRelayTransportOptions, createNodeErrorMonitor };
93
+ export { NodeEncryptedFileQueue, type NodeEncryptedFileQueueOptions, type NodeHttpInstrumentationModule, type NodeHttpInstrumentationOptions, type NodeMonitorOptions, type NodeQueueEncryptionKey, type NodeRelayIngestConfig, NodeRelayTelemetryTransport, NodeRelayTransport, type NodeRelayTransportOptions, createNodeErrorMonitor, installNodeHttpInstrumentation };