@hyperframes/producer 0.8.207 → 0.8.209
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/distributed.js +99 -52
- package/dist/hyperframe.manifest.json +1 -1
- package/dist/hyperframe.runtime.iife.js +67 -67
- package/dist/index.js +99 -52
- package/dist/public-server.js +13 -8
- package/dist/services/distributed/renderChunk.d.ts +2 -0
- package/dist/services/render/stages/captureStage.d.ts +1 -0
- package/dist/services/render/stages/extractVideosStage.d.ts +1 -1
- package/dist/services/renderOrchestrator.d.ts +1 -0
- package/package.json +7 -7
package/dist/index.js
CHANGED
|
@@ -775,7 +775,7 @@ function createFileServer(options) {
|
|
|
775
775
|
if (!streamOwnsFd) closeSync(fd);
|
|
776
776
|
}
|
|
777
777
|
});
|
|
778
|
-
return new Promise((resolve13) => {
|
|
778
|
+
return new Promise((resolve13, reject) => {
|
|
779
779
|
const connections = /* @__PURE__ */ new Set();
|
|
780
780
|
const server = serve({ fetch: app.fetch, port, hostname: "127.0.0.1" }, (info) => {
|
|
781
781
|
resolve13({
|
|
@@ -795,6 +795,7 @@ function createFileServer(options) {
|
|
|
795
795
|
connections.add(socket);
|
|
796
796
|
socket.on("close", () => connections.delete(socket));
|
|
797
797
|
});
|
|
798
|
+
server.on("error", reject);
|
|
798
799
|
});
|
|
799
800
|
}
|
|
800
801
|
|
|
@@ -5668,7 +5669,7 @@ import { gsapCdnDist, normalizeGsapBaseUrl } from "@hyperframes/core/gsap-cdn";
|
|
|
5668
5669
|
import {
|
|
5669
5670
|
assignBundledRuntimeCompositionIds,
|
|
5670
5671
|
assignMediaRenderIds,
|
|
5671
|
-
|
|
5672
|
+
emitVariablesByCompScript,
|
|
5672
5673
|
inlineSubCompositions as inlineSubCompositionsShared,
|
|
5673
5674
|
ensureExternalLinkTag,
|
|
5674
5675
|
ensureExternalScriptTag,
|
|
@@ -7240,9 +7241,9 @@ function inlineSubCompositions(html, subCompositions, projectDir, variableOverri
|
|
|
7240
7241
|
}
|
|
7241
7242
|
}
|
|
7242
7243
|
}
|
|
7243
|
-
|
|
7244
|
+
emitVariablesByCompScript(document2, result.variablesByComp);
|
|
7244
7245
|
if (body) {
|
|
7245
|
-
let pending =
|
|
7246
|
+
let pending = [];
|
|
7246
7247
|
const flushInline = () => {
|
|
7247
7248
|
if (!pending.length) return;
|
|
7248
7249
|
const joined = pending.join("\n;\n");
|
|
@@ -9256,10 +9257,11 @@ var VideoExtractionStageError = class extends Error {
|
|
|
9256
9257
|
kind: failure.kind,
|
|
9257
9258
|
affectedElementCount: failure.count
|
|
9258
9259
|
}))
|
|
9259
|
-
)) {
|
|
9260
|
+
), ffmpegReason) {
|
|
9260
9261
|
const total = failures.reduce((sum2, failure) => sum2 + failure.count, 0);
|
|
9261
9262
|
const breakdown = failures.map((failure) => `${failure.kind}=${failure.count}`).join(",");
|
|
9262
|
-
|
|
9263
|
+
const reason = ffmpegReason ? `: ffmpeg said: ${ffmpegReason}` : "";
|
|
9264
|
+
super(`Video extraction failed for ${total} source(s) [${code}; ${breakdown}]${reason}`);
|
|
9263
9265
|
this.code = code;
|
|
9264
9266
|
this.retryable = retryable;
|
|
9265
9267
|
this.failures = failures;
|
|
@@ -9306,7 +9308,8 @@ function buildVideoExtractionStageError(result) {
|
|
|
9306
9308
|
retryable ? "VIDEO_EXTRACTION_FAILED" : "VIDEO_SOURCE_UNRENDERABLE",
|
|
9307
9309
|
retryable,
|
|
9308
9310
|
failures,
|
|
9309
|
-
extractionFailureMetadataFromResult(result)
|
|
9311
|
+
extractionFailureMetadataFromResult(result),
|
|
9312
|
+
result.errors.find((failure) => failure.ffmpegReason)?.ffmpegReason
|
|
9310
9313
|
);
|
|
9311
9314
|
}
|
|
9312
9315
|
function buildHdrProbeStageError(failures) {
|
|
@@ -10303,6 +10306,7 @@ async function runCaptureStage(input) {
|
|
|
10303
10306
|
dedupPerfs,
|
|
10304
10307
|
pageErrorLines: workerPageErrors,
|
|
10305
10308
|
openAttempt: input.openAttempt,
|
|
10309
|
+
verifyFirstSession: input.verifyFirstSession,
|
|
10306
10310
|
onProgress: (progress) => {
|
|
10307
10311
|
if (progress.latestWorkerPhase) {
|
|
10308
10312
|
if (progress.capturedFrames === 0) reportWorkerStartup(job, progress, onProgress);
|
|
@@ -12362,7 +12366,8 @@ async function executeDiskCaptureWithAdaptiveRetry(options) {
|
|
|
12362
12366
|
});
|
|
12363
12367
|
} : void 0,
|
|
12364
12368
|
void 0,
|
|
12365
|
-
options.cfg
|
|
12369
|
+
options.cfg,
|
|
12370
|
+
{ verifyFirstSession: options.verifyFirstSession }
|
|
12366
12371
|
);
|
|
12367
12372
|
pushWorkerDedupPerfs(workerResults, options.dedupPerfs);
|
|
12368
12373
|
if (options.pageErrorLines) pushWorkerPageErrors(workerResults, options.pageErrorLines);
|
|
@@ -20245,16 +20250,18 @@ function observedChunkCaptureMode(perfs) {
|
|
|
20245
20250
|
}
|
|
20246
20251
|
return mode;
|
|
20247
20252
|
}
|
|
20253
|
+
var PROBE_SELECTED_SCREENSHOT = "[renderChunk] probe selected screenshot capture";
|
|
20248
20254
|
function shouldRetryChunkCaptureWithScreenshot(error) {
|
|
20249
20255
|
const failure = classifyCaptureFailure4(error);
|
|
20250
20256
|
if (failure.kind === "cancelled" || failure.kind === "memory_exhaustion") return false;
|
|
20251
|
-
return /HeadlessExperimental\.beginFrame/i.test(failure.message) || /beginFrame probe timeout/i.test(failure.message) || /Another frame is pending|Frame still pending/i.test(failure.message);
|
|
20257
|
+
return /HeadlessExperimental\.beginFrame/i.test(failure.message) || /beginFrame probe timeout/i.test(failure.message) || failure.message.includes(PROBE_SELECTED_SCREENSHOT) || /Another frame is pending|Frame still pending/i.test(failure.message);
|
|
20252
20258
|
}
|
|
20253
20259
|
async function runCaptureWithScreenshotFallback(input) {
|
|
20254
20260
|
try {
|
|
20255
20261
|
return await input.run(input.forceScreenshot);
|
|
20256
20262
|
} catch (error) {
|
|
20257
|
-
if (input.forceScreenshot ||
|
|
20263
|
+
if (input.forceScreenshot || await input.canRetry?.() === false) throw error;
|
|
20264
|
+
if (!shouldRetryChunkCaptureWithScreenshot(error)) throw error;
|
|
20258
20265
|
input.onFallback?.(error);
|
|
20259
20266
|
await input.resetForScreenshotRetry();
|
|
20260
20267
|
return await input.run(true);
|
|
@@ -20463,7 +20470,24 @@ async function renderChunk(planDir, chunkIndex, outputChunkPath, options) {
|
|
|
20463
20470
|
let extraction;
|
|
20464
20471
|
const overlap = { current: null };
|
|
20465
20472
|
try {
|
|
20466
|
-
|
|
20473
|
+
const verifyInWorker = chunkWorkerCount > 1 && !forceScreenshotForChunk;
|
|
20474
|
+
let boxesMeasured;
|
|
20475
|
+
let boxesFailed;
|
|
20476
|
+
const boxesReady = new Promise((resolve13, reject) => {
|
|
20477
|
+
boxesMeasured = resolve13;
|
|
20478
|
+
boxesFailed = reject;
|
|
20479
|
+
});
|
|
20480
|
+
boxesReady.catch(() => {
|
|
20481
|
+
});
|
|
20482
|
+
const measureBoxes = async (page) => {
|
|
20483
|
+
shownBoxes = await measureVideoShownBoxes(
|
|
20484
|
+
page,
|
|
20485
|
+
[...shownFrames.keys()],
|
|
20486
|
+
chunkFrameNumbers.map((frame) => frame * chunkFps.den / chunkFps.num)
|
|
20487
|
+
);
|
|
20488
|
+
boxesMeasured();
|
|
20489
|
+
};
|
|
20490
|
+
if (chunkWorkerCount === 1) {
|
|
20467
20491
|
const bootStarted = Date.now();
|
|
20468
20492
|
session = await createVerifiedDistributedCaptureSession(
|
|
20469
20493
|
fileServer.url,
|
|
@@ -20472,11 +20496,7 @@ async function renderChunk(planDir, chunkIndex, outputChunkPath, options) {
|
|
|
20472
20496
|
cfg
|
|
20473
20497
|
);
|
|
20474
20498
|
sessionBootMs = Date.now() - bootStarted;
|
|
20475
|
-
|
|
20476
|
-
session.page,
|
|
20477
|
-
[...shownFrames.keys()],
|
|
20478
|
-
chunkFrameNumbers.map((frame) => frame * chunkFps.den / chunkFps.num)
|
|
20479
|
-
);
|
|
20499
|
+
await measureBoxes(session.page);
|
|
20480
20500
|
const browserSelectedScreenshot = session.launchCaptureMode === "screenshot";
|
|
20481
20501
|
const beginFrameStalled = !browserSelectedScreenshot && await beginFrameSessionNeedsScreenshotFallback(session);
|
|
20482
20502
|
if (browserSelectedScreenshot) {
|
|
@@ -20485,10 +20505,6 @@ async function renderChunk(planDir, chunkIndex, outputChunkPath, options) {
|
|
|
20485
20505
|
"[renderChunk] Browser capability probe selected screenshot capture for the entire chunk",
|
|
20486
20506
|
{ chunkIndex }
|
|
20487
20507
|
);
|
|
20488
|
-
if (chunkWorkerCount > 1) {
|
|
20489
|
-
await closeCaptureSession11(session);
|
|
20490
|
-
session = null;
|
|
20491
|
-
}
|
|
20492
20508
|
} else if (beginFrameStalled) {
|
|
20493
20509
|
forceScreenshotForChunk = true;
|
|
20494
20510
|
log.warn(
|
|
@@ -20498,41 +20514,66 @@ async function renderChunk(planDir, chunkIndex, outputChunkPath, options) {
|
|
|
20498
20514
|
await closeCaptureSession11(session).catch(() => {
|
|
20499
20515
|
});
|
|
20500
20516
|
session = null;
|
|
20501
|
-
|
|
20502
|
-
|
|
20503
|
-
|
|
20504
|
-
|
|
20505
|
-
|
|
20506
|
-
|
|
20507
|
-
|
|
20508
|
-
|
|
20509
|
-
|
|
20510
|
-
|
|
20511
|
-
|
|
20512
|
-
|
|
20517
|
+
const screenshotBootStarted = Date.now();
|
|
20518
|
+
const screenshotCfg = {
|
|
20519
|
+
...cfg,
|
|
20520
|
+
forceScreenshot: true,
|
|
20521
|
+
forceScreenshotExplicitlyOptedOut: false
|
|
20522
|
+
};
|
|
20523
|
+
session = await createVerifiedDistributedCaptureSession(
|
|
20524
|
+
fileServer.url,
|
|
20525
|
+
framesDir,
|
|
20526
|
+
captureOptions,
|
|
20527
|
+
screenshotCfg
|
|
20528
|
+
);
|
|
20529
|
+
sessionBootMs += Date.now() - screenshotBootStarted;
|
|
20530
|
+
}
|
|
20531
|
+
} else if (!verifyInWorker) {
|
|
20532
|
+
boxesMeasured();
|
|
20533
|
+
}
|
|
20534
|
+
let verification;
|
|
20535
|
+
const verifyFirstWorker = (first) => verification ??= (async () => {
|
|
20536
|
+
sessionBootMs = Date.now() - verifyStarted;
|
|
20537
|
+
try {
|
|
20538
|
+
await measureBoxes(first.page);
|
|
20539
|
+
const selectedScreenshot = first.launchCaptureMode === "screenshot";
|
|
20540
|
+
if (selectedScreenshot || await beginFrameSessionNeedsScreenshotFallback(first)) {
|
|
20541
|
+
forceScreenshotForChunk = true;
|
|
20542
|
+
log.warn(
|
|
20543
|
+
selectedScreenshot ? "[renderChunk] Browser capability probe selected screenshot capture for the entire chunk" : "[renderChunk] BeginFrame liveness probe failed; using screenshot capture for the entire chunk",
|
|
20544
|
+
{ chunkIndex }
|
|
20513
20545
|
);
|
|
20514
|
-
|
|
20546
|
+
throw new Error(PROBE_SELECTED_SCREENSHOT);
|
|
20515
20547
|
}
|
|
20516
|
-
}
|
|
20517
|
-
|
|
20518
|
-
|
|
20548
|
+
} catch (error) {
|
|
20549
|
+
if (!forceScreenshotForChunk) {
|
|
20550
|
+
verifyFailure = error;
|
|
20551
|
+
boxesFailed(error);
|
|
20552
|
+
}
|
|
20553
|
+
throw error;
|
|
20519
20554
|
}
|
|
20520
|
-
}
|
|
20521
|
-
|
|
20522
|
-
|
|
20523
|
-
|
|
20524
|
-
|
|
20525
|
-
|
|
20526
|
-
|
|
20527
|
-
|
|
20528
|
-
|
|
20529
|
-
|
|
20530
|
-
|
|
20531
|
-
|
|
20532
|
-
|
|
20533
|
-
|
|
20534
|
-
|
|
20555
|
+
})();
|
|
20556
|
+
let verifyStarted = 0;
|
|
20557
|
+
let verifyFailure;
|
|
20558
|
+
const deferredVideoFrames = planVideos ? boxesReady.then(() => {
|
|
20559
|
+
const extractStarted = Date.now();
|
|
20560
|
+
return extractDeferredVideoFramesForChunk({
|
|
20561
|
+
planDir,
|
|
20562
|
+
planVideos,
|
|
20563
|
+
frames: chunkFrameNumbers,
|
|
20564
|
+
fps: chunkFps,
|
|
20565
|
+
outputRoot: videoFramesDir,
|
|
20566
|
+
cfg,
|
|
20567
|
+
remoteSources,
|
|
20568
|
+
shownBoxes
|
|
20569
|
+
}).then((frames) => {
|
|
20570
|
+
videoExtractMs = Date.now() - extractStarted;
|
|
20571
|
+
return frames;
|
|
20572
|
+
});
|
|
20573
|
+
}) : boxesReady.then(() => []);
|
|
20535
20574
|
extraction = deferredVideoFrames;
|
|
20575
|
+
deferredVideoFrames.catch(() => {
|
|
20576
|
+
});
|
|
20536
20577
|
const videoFrameLookup = planVideos && planVideos.extracted.length > 0 ? deferredVideoFrames.then(
|
|
20537
20578
|
(deferred) => createFrameLookupTable5(
|
|
20538
20579
|
planVideos.videos,
|
|
@@ -20611,6 +20652,7 @@ async function renderChunk(planDir, chunkIndex, outputChunkPath, options) {
|
|
|
20611
20652
|
const captureStarted = Date.now();
|
|
20612
20653
|
captureMode = await runCaptureWithScreenshotFallback({
|
|
20613
20654
|
forceScreenshot: forceScreenshotForChunk,
|
|
20655
|
+
canRetry: () => verifyFailure === void 0,
|
|
20614
20656
|
// fallow-ignore-next-line complexity
|
|
20615
20657
|
run: async (forceScreenshot) => {
|
|
20616
20658
|
const captureCfg = cfg.forceScreenshot === forceScreenshot ? cfg : {
|
|
@@ -20640,6 +20682,7 @@ async function renderChunk(planDir, chunkIndex, outputChunkPath, options) {
|
|
|
20640
20682
|
}
|
|
20641
20683
|
const captureSession = session;
|
|
20642
20684
|
session = null;
|
|
20685
|
+
verifyStarted = Date.now();
|
|
20643
20686
|
overlap.current = canEncodeWhileCapturing(encodeInput, chunkWorkerCount, cpus3().length) ? encodeWhileCapturing(encodeInput, framesInChunk) : null;
|
|
20644
20687
|
await observeRenderStage(
|
|
20645
20688
|
new RenderObservabilityRecorder({ pipelineStartMs: start, log }),
|
|
@@ -20667,7 +20710,8 @@ async function renderChunk(planDir, chunkIndex, outputChunkPath, options) {
|
|
|
20667
20710
|
frameRange: range,
|
|
20668
20711
|
onFrameLanded: (frame) => overlap.current?.onFrameLanded(frame),
|
|
20669
20712
|
interleaveFrames: interleavesCapture(overlap.current !== null, options),
|
|
20670
|
-
openAttempt
|
|
20713
|
+
openAttempt,
|
|
20714
|
+
verifyFirstSession: forceScreenshot || !verifyInWorker ? void 0 : verifyFirstWorker
|
|
20671
20715
|
}),
|
|
20672
20716
|
{ stall: frameStallRule(job) }
|
|
20673
20717
|
).catch(async (captureError) => {
|
|
@@ -20679,6 +20723,7 @@ async function renderChunk(planDir, chunkIndex, outputChunkPath, options) {
|
|
|
20679
20723
|
},
|
|
20680
20724
|
resetForScreenshotRetry: () => {
|
|
20681
20725
|
rmSync17(workDir, { recursive: true, force: true, maxRetries: 3, retryDelay: 100 });
|
|
20726
|
+
boxesMeasured();
|
|
20682
20727
|
mkdirSync19(framesDir, { recursive: true });
|
|
20683
20728
|
capturePerfs.length = 0;
|
|
20684
20729
|
captureAttempts.length = 0;
|
|
@@ -20694,6 +20739,8 @@ async function renderChunk(planDir, chunkIndex, outputChunkPath, options) {
|
|
|
20694
20739
|
);
|
|
20695
20740
|
}
|
|
20696
20741
|
}).catch(async (captureError) => {
|
|
20742
|
+
if (verifyFailure !== void 0) throw verifyFailure;
|
|
20743
|
+
boxesFailed(captureError);
|
|
20697
20744
|
await deferredVideoFrames;
|
|
20698
20745
|
throw captureError;
|
|
20699
20746
|
});
|
package/dist/public-server.js
CHANGED
|
@@ -796,7 +796,7 @@ function createFileServer(options) {
|
|
|
796
796
|
if (!streamOwnsFd) closeSync(fd);
|
|
797
797
|
}
|
|
798
798
|
});
|
|
799
|
-
return new Promise((resolve11) => {
|
|
799
|
+
return new Promise((resolve11, reject) => {
|
|
800
800
|
const connections = /* @__PURE__ */ new Set();
|
|
801
801
|
const server = serve({ fetch: app.fetch, port, hostname: "127.0.0.1" }, (info) => {
|
|
802
802
|
resolve11({
|
|
@@ -816,6 +816,7 @@ function createFileServer(options) {
|
|
|
816
816
|
connections.add(socket);
|
|
817
817
|
socket.on("close", () => connections.delete(socket));
|
|
818
818
|
});
|
|
819
|
+
server.on("error", reject);
|
|
819
820
|
});
|
|
820
821
|
}
|
|
821
822
|
|
|
@@ -5685,7 +5686,7 @@ import { gsapCdnDist, normalizeGsapBaseUrl } from "@hyperframes/core/gsap-cdn";
|
|
|
5685
5686
|
import {
|
|
5686
5687
|
assignBundledRuntimeCompositionIds,
|
|
5687
5688
|
assignMediaRenderIds,
|
|
5688
|
-
|
|
5689
|
+
emitVariablesByCompScript,
|
|
5689
5690
|
inlineSubCompositions as inlineSubCompositionsShared,
|
|
5690
5691
|
ensureExternalLinkTag,
|
|
5691
5692
|
ensureExternalScriptTag,
|
|
@@ -7257,9 +7258,9 @@ function inlineSubCompositions(html, subCompositions, projectDir, variableOverri
|
|
|
7257
7258
|
}
|
|
7258
7259
|
}
|
|
7259
7260
|
}
|
|
7260
|
-
|
|
7261
|
+
emitVariablesByCompScript(document2, result.variablesByComp);
|
|
7261
7262
|
if (body) {
|
|
7262
|
-
let pending =
|
|
7263
|
+
let pending = [];
|
|
7263
7264
|
const flushInline = () => {
|
|
7264
7265
|
if (!pending.length) return;
|
|
7265
7266
|
const joined = pending.join("\n;\n");
|
|
@@ -9242,10 +9243,11 @@ var VideoExtractionStageError = class extends Error {
|
|
|
9242
9243
|
kind: failure.kind,
|
|
9243
9244
|
affectedElementCount: failure.count
|
|
9244
9245
|
}))
|
|
9245
|
-
)) {
|
|
9246
|
+
), ffmpegReason) {
|
|
9246
9247
|
const total = failures.reduce((sum, failure) => sum + failure.count, 0);
|
|
9247
9248
|
const breakdown = failures.map((failure) => `${failure.kind}=${failure.count}`).join(",");
|
|
9248
|
-
|
|
9249
|
+
const reason = ffmpegReason ? `: ffmpeg said: ${ffmpegReason}` : "";
|
|
9250
|
+
super(`Video extraction failed for ${total} source(s) [${code}; ${breakdown}]${reason}`);
|
|
9249
9251
|
this.code = code;
|
|
9250
9252
|
this.retryable = retryable;
|
|
9251
9253
|
this.failures = failures;
|
|
@@ -9287,7 +9289,8 @@ function buildVideoExtractionStageError(result) {
|
|
|
9287
9289
|
retryable ? "VIDEO_EXTRACTION_FAILED" : "VIDEO_SOURCE_UNRENDERABLE",
|
|
9288
9290
|
retryable,
|
|
9289
9291
|
failures,
|
|
9290
|
-
extractionFailureMetadataFromResult(result)
|
|
9292
|
+
extractionFailureMetadataFromResult(result),
|
|
9293
|
+
result.errors.find((failure) => failure.ffmpegReason)?.ffmpegReason
|
|
9291
9294
|
);
|
|
9292
9295
|
}
|
|
9293
9296
|
function buildHdrProbeStageError(failures) {
|
|
@@ -10284,6 +10287,7 @@ async function runCaptureStage(input) {
|
|
|
10284
10287
|
dedupPerfs,
|
|
10285
10288
|
pageErrorLines: workerPageErrors,
|
|
10286
10289
|
openAttempt: input.openAttempt,
|
|
10290
|
+
verifyFirstSession: input.verifyFirstSession,
|
|
10287
10291
|
onProgress: (progress) => {
|
|
10288
10292
|
if (progress.latestWorkerPhase) {
|
|
10289
10293
|
if (progress.capturedFrames === 0) reportWorkerStartup(job, progress, onProgress);
|
|
@@ -12343,7 +12347,8 @@ async function executeDiskCaptureWithAdaptiveRetry(options) {
|
|
|
12343
12347
|
});
|
|
12344
12348
|
} : void 0,
|
|
12345
12349
|
void 0,
|
|
12346
|
-
options.cfg
|
|
12350
|
+
options.cfg,
|
|
12351
|
+
{ verifyFirstSession: options.verifyFirstSession }
|
|
12347
12352
|
);
|
|
12348
12353
|
pushWorkerDedupPerfs(workerResults, options.dedupPerfs);
|
|
12349
12354
|
if (options.pageErrorLines) pushWorkerPageErrors(workerResults, options.pageErrorLines);
|
|
@@ -156,6 +156,8 @@ export declare function shouldRetryChunkCaptureWithScreenshot(error: unknown): b
|
|
|
156
156
|
*/
|
|
157
157
|
export declare function runCaptureWithScreenshotFallback<T>(input: {
|
|
158
158
|
forceScreenshot: boolean;
|
|
159
|
+
/** A failure that is not capture's (the probe's own) is never retried. */
|
|
160
|
+
canRetry?: () => boolean | Promise<boolean>;
|
|
159
161
|
run: (forceScreenshot: boolean) => Promise<T>;
|
|
160
162
|
resetForScreenshotRetry: () => Promise<void> | void;
|
|
161
163
|
onFallback?: (error: unknown) => void;
|
|
@@ -88,6 +88,7 @@ export interface CaptureStageInput {
|
|
|
88
88
|
interleaveFrames?: boolean;
|
|
89
89
|
/** Each capture attempt opens one, so a stalled attempt is retried by the ladders below. */
|
|
90
90
|
openAttempt?: OpenStallAttempt;
|
|
91
|
+
verifyFirstSession?: (session: CaptureSession) => Promise<void>;
|
|
91
92
|
}
|
|
92
93
|
export interface CaptureStageResult {
|
|
93
94
|
/** Final worker count after any adaptive retry. */
|
|
@@ -117,7 +117,7 @@ export declare class VideoExtractionStageError extends Error {
|
|
|
117
117
|
* validating and applying policy to it.
|
|
118
118
|
*/
|
|
119
119
|
readonly publicMetadata: Readonly<Record<string, unknown>>;
|
|
120
|
-
constructor(code: VideoExtractionStageErrorCode, retryable: boolean, failures: readonly VideoExtractionStageFailureSummary[], extractionFailure?: ExtractionFailureMetadataV1);
|
|
120
|
+
constructor(code: VideoExtractionStageErrorCode, retryable: boolean, failures: readonly VideoExtractionStageFailureSummary[], extractionFailure?: ExtractionFailureMetadataV1, ffmpegReason?: string);
|
|
121
121
|
}
|
|
122
122
|
export declare function assertVideoExtractionSucceeded(result: ExtractionResult): void;
|
|
123
123
|
export declare function buildHdrProbeStageError(failures: readonly Pick<ReturnType<typeof classifyVideoExtractionError>, "kind" | "retryable">[]): VideoExtractionStageError;
|
|
@@ -610,6 +610,7 @@ export declare function executeDiskCaptureWithAdaptiveRetry(options: {
|
|
|
610
610
|
/** Mutated in place: the workers' page-error console lines, for the render's error count. */
|
|
611
611
|
pageErrorLines?: string[];
|
|
612
612
|
openAttempt?: OpenStallAttempt;
|
|
613
|
+
verifyFirstSession?: (session: CaptureSession) => Promise<void>;
|
|
613
614
|
}): Promise<CaptureAttemptSummary[]>;
|
|
614
615
|
export type RenderConfigInput = Omit<RenderConfig, "fps"> & {
|
|
615
616
|
fps: FpsInput;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@hyperframes/producer",
|
|
3
|
-
"version": "0.8.
|
|
3
|
+
"version": "0.8.209",
|
|
4
4
|
"description": "HTML-to-video rendering engine using Chrome's BeginFrame API",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
@@ -35,11 +35,11 @@
|
|
|
35
35
|
"postcss": "^8.4.0",
|
|
36
36
|
"puppeteer": "^25.2.1",
|
|
37
37
|
"puppeteer-core": "^25.2.1",
|
|
38
|
-
"@hyperframes/
|
|
39
|
-
"@hyperframes/
|
|
40
|
-
"@hyperframes/lint": "0.8.
|
|
41
|
-
"@hyperframes/parsers": "0.8.
|
|
42
|
-
"@hyperframes/studio-server": "0.8.
|
|
38
|
+
"@hyperframes/core": "0.8.209",
|
|
39
|
+
"@hyperframes/engine": "0.8.209",
|
|
40
|
+
"@hyperframes/lint": "0.8.209",
|
|
41
|
+
"@hyperframes/parsers": "0.8.209",
|
|
42
|
+
"@hyperframes/studio-server": "0.8.209"
|
|
43
43
|
},
|
|
44
44
|
"devDependencies": {
|
|
45
45
|
"@types/node": "^25.0.10",
|
|
@@ -48,7 +48,7 @@
|
|
|
48
48
|
"tsx": "^4.21.0",
|
|
49
49
|
"typescript": "^5.7.2",
|
|
50
50
|
"vitest": "^4.1.11",
|
|
51
|
-
"@hyperframes/aws-lambda": "0.8.
|
|
51
|
+
"@hyperframes/aws-lambda": "0.8.209"
|
|
52
52
|
},
|
|
53
53
|
"engines": {
|
|
54
54
|
"node": ">=22"
|