@replayio-app-building/netlify-recorder 0.24.0 → 0.26.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 +1 -10
- package/dist/index.d.ts +4 -7
- package/dist/index.js +30 -1
- package/package.json +6 -2
package/README.md
CHANGED
|
@@ -137,15 +137,7 @@ The function is idempotent — calling it multiple times for the same request is
|
|
|
137
137
|
- **`status: "queued"` or `"processing"`** — returns `null` without re-queuing
|
|
138
138
|
- **`status: "captured"` or `"failed"`** — calls the service, updates status to `"queued"`, returns `null`
|
|
139
139
|
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
```typescript
|
|
143
|
-
const recordingId = await ensureRequestRecording(sql, requestId, {
|
|
144
|
-
recorderUrl: RECORDER_URL,
|
|
145
|
-
blobDataUrl: `https://your-app.netlify.app/api/get-blob?id=${requestId}`,
|
|
146
|
-
webhookUrl: "https://your-app.netlify.app/api/on-recording-complete", // optional
|
|
147
|
-
});
|
|
148
|
-
```
|
|
140
|
+
The function reads the `blob_data` from `backend_requests`, uploads it to UploadThing, and passes the URL to the recorder service. This requires the `uploadthing` package and `UPLOADTHING_TOKEN` environment variable.
|
|
149
141
|
|
|
150
142
|
When `webhookUrl` is provided, the service POSTs the result when the recording completes:
|
|
151
143
|
|
|
@@ -411,7 +403,6 @@ Ensures a Replay recording exists (or is being created) for a backend request. L
|
|
|
411
403
|
- `sql` — A Neon SQL tagged-template function
|
|
412
404
|
- `requestId` — The backend request UUID
|
|
413
405
|
- `options.recorderUrl` — Base URL of the Netlify Recorder service
|
|
414
|
-
- `options.blobDataUrl` — Override the URL where the recording container fetches the blob JSON (defaults to `${recorderUrl}/api/get-backend-request-blob?requestId=${requestId}`)
|
|
415
406
|
- `options.webhookUrl` — URL to POST the result to when the recording completes or fails
|
|
416
407
|
|
|
417
408
|
**Returns:** The recording ID (`string`) if the request is already recorded, or `null` if the recording was queued or is in progress.
|
package/dist/index.d.ts
CHANGED
|
@@ -277,11 +277,6 @@ declare function databaseCallbacks(sql: SqlFunction$1): FinishRequestCallbacks;
|
|
|
277
277
|
interface EnsureRequestRecordingOptions {
|
|
278
278
|
/** Base URL of the Netlify Recorder service (e.g. "https://netlify-recorder-bm4wmw.netlify.app"). */
|
|
279
279
|
recorderUrl: string;
|
|
280
|
-
/**
|
|
281
|
-
* Full URL where the recording container can fetch the blob JSON for this request.
|
|
282
|
-
* Defaults to `${recorderUrl}/api/get-backend-request-blob?requestId=${requestId}`.
|
|
283
|
-
*/
|
|
284
|
-
blobDataUrl?: string;
|
|
285
280
|
/** URL to POST the result to when the recording completes or fails. */
|
|
286
281
|
webhookUrl?: string;
|
|
287
282
|
}
|
|
@@ -291,8 +286,10 @@ interface EnsureRequestRecordingOptions {
|
|
|
291
286
|
* 1. Looks up the request in `backend_requests`.
|
|
292
287
|
* 2. If a recording already exists (`status === "recorded"`), returns the recording ID immediately.
|
|
293
288
|
* 3. If the request is already queued or processing, returns `null` without re-queuing.
|
|
294
|
-
* 4. Otherwise, calls the Netlify Recorder
|
|
295
|
-
* updates the row to `"queued"`, and returns `null`.
|
|
289
|
+
* 4. Otherwise, uploads the blob data to UploadThing, calls the Netlify Recorder
|
|
290
|
+
* service's `create-recording` endpoint, updates the row to `"queued"`, and returns `null`.
|
|
291
|
+
*
|
|
292
|
+
* Requires `UPLOADTHING_TOKEN` environment variable and the `uploadthing` package.
|
|
296
293
|
*
|
|
297
294
|
* This function is idempotent — calling it multiple times for the same request
|
|
298
295
|
* is safe. Once the recording completes, subsequent calls return the recording ID.
|
package/dist/index.js
CHANGED
|
@@ -1063,6 +1063,35 @@ function databaseCallbacks(sql) {
|
|
|
1063
1063
|
}
|
|
1064
1064
|
};
|
|
1065
1065
|
}
|
|
1066
|
+
async function uploadBlobData(blobData, requestId) {
|
|
1067
|
+
let UTApi;
|
|
1068
|
+
try {
|
|
1069
|
+
({ UTApi } = await Function('return import("uploadthing/server")')());
|
|
1070
|
+
} catch {
|
|
1071
|
+
throw new Error(
|
|
1072
|
+
"ensureRequestRecording requires the 'uploadthing' package. Install it with: npm install uploadthing"
|
|
1073
|
+
);
|
|
1074
|
+
}
|
|
1075
|
+
const token = process.env.UPLOADTHING_TOKEN;
|
|
1076
|
+
if (!token) {
|
|
1077
|
+
throw new Error(
|
|
1078
|
+
"ensureRequestRecording: UPLOADTHING_TOKEN environment variable is required to upload blob data"
|
|
1079
|
+
);
|
|
1080
|
+
}
|
|
1081
|
+
const utapi = new UTApi({ token });
|
|
1082
|
+
const file = new File(
|
|
1083
|
+
[blobData],
|
|
1084
|
+
`blob-${requestId}.json`,
|
|
1085
|
+
{ type: "application/json" }
|
|
1086
|
+
);
|
|
1087
|
+
const result = await utapi.uploadFiles(file);
|
|
1088
|
+
if (result.error || !result.data?.ufsUrl) {
|
|
1089
|
+
throw new Error(
|
|
1090
|
+
`Failed to upload blob data for request ${requestId}: ${JSON.stringify(result.error ?? "no URL returned")}`
|
|
1091
|
+
);
|
|
1092
|
+
}
|
|
1093
|
+
return result.data.ufsUrl;
|
|
1094
|
+
}
|
|
1066
1095
|
async function ensureRequestRecording(sql, requestId, options) {
|
|
1067
1096
|
const request = await backendRequestsGet(sql, requestId);
|
|
1068
1097
|
if (!request) {
|
|
@@ -1074,8 +1103,8 @@ async function ensureRequestRecording(sql, requestId, options) {
|
|
|
1074
1103
|
if (request.status === "queued" || request.status === "processing") {
|
|
1075
1104
|
return null;
|
|
1076
1105
|
}
|
|
1106
|
+
const blobDataUrl = await uploadBlobData(request.blob_data, requestId);
|
|
1077
1107
|
const recorderUrl = options.recorderUrl.replace(/\/+$/, "");
|
|
1078
|
-
const blobDataUrl = options.blobDataUrl ?? `${recorderUrl}/api/get-backend-request-blob?requestId=${requestId}`;
|
|
1079
1108
|
const res = await fetch(`${recorderUrl}/api/create-recording`, {
|
|
1080
1109
|
method: "POST",
|
|
1081
1110
|
headers: { "Content-Type": "application/json" },
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@replayio-app-building/netlify-recorder",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.26.0",
|
|
4
4
|
"description": "Capture and replay Netlify function executions as Replay recordings",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"exports": {
|
|
@@ -18,11 +18,15 @@
|
|
|
18
18
|
"prepublishOnly": "tsup"
|
|
19
19
|
},
|
|
20
20
|
"peerDependencies": {
|
|
21
|
-
"@replayio/app-building": ">=1.0.0"
|
|
21
|
+
"@replayio/app-building": ">=1.0.0",
|
|
22
|
+
"uploadthing": ">=7.0.0"
|
|
22
23
|
},
|
|
23
24
|
"peerDependenciesMeta": {
|
|
24
25
|
"@replayio/app-building": {
|
|
25
26
|
"optional": true
|
|
27
|
+
},
|
|
28
|
+
"uploadthing": {
|
|
29
|
+
"optional": true
|
|
26
30
|
}
|
|
27
31
|
},
|
|
28
32
|
"devDependencies": {
|