Skip to content

Commit 3ca5f85

Browse files
committed
Fix
1 parent efe2310 commit 3ca5f85

26 files changed

Lines changed: 1104 additions & 930 deletions

‎dist/spector.bundle.js‎

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

‎dist/spector.d.ts‎

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -808,13 +808,14 @@ export declare class Spector {
808808
log(value: string): void;
809809
/**
810810
* Explicitly opt in to intercepting new Worker() calls to auto-inject Spector.
811-
* Experimental/best-effort: can change Worker behavior and fails for some
812-
* CORS/CSP policies. Module Workers are not injected. Prefer spyWorker().
811+
* Experimental/best-effort: only simple same-origin classic scripts with
812+
* string URLs and no options are candidates. Module Workers stay native.
813+
* Blob wrapping can still change behavior or fail under CSP. Prefer spyWorker().
813814
* @param workerBundleUrl URL to spector.worker.bundle.js
814815
*/
815816
spyWorkers(workerBundleUrl?: string): void;
816817
/**
817-
* Stop intercepting Worker construction.
818+
* Stop intercepting Worker construction without replacing later third-party wrappers.
818819
*/
819820
stopSpyingWorkers(): void;
820821
/**
@@ -825,8 +826,7 @@ export declare class Spector {
825826
spyWorker(worker: Worker): WorkerBridge;
826827
/**
827828
* Capture a frame from a Worker's WebGL context.
828-
* Uses direct postMessage to bypass the main-thread spy chain,
829-
* which ensures a full frame is captured.
829+
* Uses the Worker's bridge to send the request and publish its result once.
830830
*/
831831
captureWorker(worker: Worker, commandCount?: number, quickCapture?: boolean, fullCapture?: boolean): void;
832832
private captureFrames;

‎documentation/apis.md‎

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -35,12 +35,16 @@ And the following list of events:
3535
- ```onError: IEvent<string>```: triggered when an error occured and return the error message.
3636

3737
### Worker / OffscreenCanvas APIs
38-
- ```spyWorkers(workerBundleUrl?: string)``` : Explicitly opt in to experimental, best-effort interception of `new Worker()` calls. Attempts to inject Spector into classic Workers; module Workers are not injected. Recognizable dynamic imports and nested Worker constructions are also bypassed, but source checks cannot establish safety. Blob wrapping, URL/base changes, and constructor interception can alter behavior; CSP/CORS restrictions can prevent injection. Defaults to `"spector.worker.bundle.js"`. Prefer `spyWorker()` when you control the Worker source.
39-
- ```stopSpyingWorkers()``` : Stop intercepting Worker construction.
38+
- ```spyWorkers(workerBundleUrl?: string)``` : Explicitly opt in to experimental, best-effort interception of `new Worker()` calls. Only primitive string URLs for same-origin HTTP(S) classic Workers without options are candidates. URL objects, options (including module Workers), subclasses, redirects, blob/data/cross-origin URLs, strict scripts, and recognizable URL-sensitive sources (`import`, `importScripts`, nested Workers, `location`, `Request`, `fetch`, XHR) use native construction. Inputs are passed to the original constructor without extra coercion or options inspection. Source checks cannot establish safety. Defaults to `"spector.worker.bundle.js"`, resolved against the caller's base URL. Prefer `spyWorker()` when you control the Worker source.
39+
- ```stopSpyingWorkers()``` : Deactivate this interceptor, including retained references to it. Restore the previous constructor only if it is still installed; preserve wrappers installed later by other libraries.
4040
- ```spyWorker(worker: Worker): WorkerBridge``` : Manually bridge a specific Worker for capture. This is the recommended API and does not replace the Worker constructor. The Worker must load `spector.worker.bundle.js` via `importScripts` (classic Workers) or `import` (module Workers).
4141
- ```captureWorker(worker: Worker, commandCount?: number, quickCapture?: boolean, fullCapture?: boolean)``` : Capture a frame from a Worker's WebGL context. If the Worker hasn't been bridged yet, `spyWorker` is called automatically.
4242

43-
The browser extension's **Auto-inject Workers (experimental)** checkbox is separate from `spyWorkers()` and defaults **off**, even when offscreen canvas capture was previously enabled. It includes OffscreenCanvas Workers and warns that instrumentation may alter behavior. Changes are persisted in page `sessionStorage` (`SPECTOR_WORKERAUTOINJECT`) for the tab/origin session, like the offscreen capture setting, then reload the tab's loaded frames. The MAIN-world content script reads the exact value `"true"` synchronously at `document_start`; there is no asynchronous storage race. Missing/false values leave `window.Worker` untouched, with no wrapper or preflight fetch. Disabling the checkbox restores that behavior on reload. Main-thread canvas capture and manual Worker APIs remain available.
43+
The browser extension's **Auto-inject Workers (experimental)** checkbox is separate from `spyWorkers()` and defaults **off**, even when offscreen canvas capture was previously enabled. It uses the same conservative eligibility rules, includes simple classic OffscreenCanvas Workers, and warns that instrumentation may alter behavior. Changes are persisted in page `sessionStorage` (`SPECTOR_WORKERAUTOINJECT`) for the tab/origin session, like the offscreen capture setting, then reload the tab's loaded frames. The MAIN-world content script reads the exact value `"true"` synchronously at `document_start`; it does not wait for asynchronous extension storage. Missing/false values leave `window.Worker` untouched, with no wrapper or preflight fetch. Disabling the checkbox restores that behavior on reload. Main-thread canvas capture and manual Worker APIs remain available.
44+
45+
For OffscreenCanvas capture in the extension, select the instrumented **Worker** entry. A transferred DOM canvas alone does not identify its owning Worker, so selecting its canvas entry reports an error instead of guessing which Worker to capture.
46+
47+
Opt-in is not a compatibility guarantee: source and instrumentation-bundle preflights add synchronous requests, computed API names can evade checks, and blob wrapping still changes the worker global and script error locations. Application responses with CSP or report-only CSP stay native because a blob cannot carry those response policies. Native constructor and preflight failures, including unavailable or non-JavaScript instrumentation bundles, fall back synchronously without creating a blob Worker. A successful XHR preflight does not prove `importScripts` will succeed: it uses different CSP checks and a separate request. Bundle import/execution exceptions are logged in the Worker so the application can still start, but partially executed instrumentation is not rolled back. CSP blocking the blob Worker itself and other asynchronous startup failures cannot transparently replace an already-returned Worker. Module Workers are always native; explicitly import the worker bundle when module capture is needed. No startup message queue or `postMessage` override is installed.
4448

4549
As you notice you could use the capture without displying the UI (this is the orientation we chosed in the browser extension).
4650

‎extensions/background.js‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -89,7 +89,7 @@ browser.action.onClicked.addListener(function (tab) {
8989

9090
listenForMessage(function(request, sender, sendResponse) {
9191
var frameId;
92-
if (sender.frameId) {
92+
if (typeof sender.frameId === "number") {
9393
frameId = sender.frameId;
9494
}
9595
else if (request.uniqueId) {

0 commit comments

Comments
 (0)