mirror of
https://github.com/priyanshujain/sanderling.git
synced 2026-10-04 20:17:09 +00:00
fix(web-runtime): lock global runtime hooks against page shadowing
AddScriptToEvaluateOnNewDocument runs first, but a page script can still
delete or replace window.__sanderling{,Extractors__,NextAction__} between
install and host invocation. Define them as non-writable, non-configurable
properties so any attempt to shadow them throws in strict mode rather than
silently breaking the run.
This commit is contained in:
1 parent
31e7ed1bd7
commit
359527569f
1 file changed
+17
-5
@@ -347,7 +347,19 @@ const runtime = {
|
|||||||
pressKeys: { __sanderlingActionGenerator: true, __sanderlingKind: "pressKey" } as ActionGeneratorHandle,
|
pressKeys: { __sanderlingActionGenerator: true, __sanderlingKind: "pressKey" } as ActionGeneratorHandle,
|
||||||
};
|
};
|
||||||
|
|
||||||
(globalThis as Record<string, unknown>).__sanderling__ = runtime;
|
// Lock the runtime globals so a misbehaving (or malicious) page script can't
|
||||||
|
// shadow or replace them between AddScriptToEvaluateOnNewDocument running and
|
||||||
|
// the host invoking the extractor/next-action callbacks.
|
||||||
|
defineLockedGlobal("__sanderling__", runtime);
|
||||||
|
|
||||||
|
function defineLockedGlobal(name: string, value: unknown): void {
|
||||||
|
Object.defineProperty(globalThis, name, {
|
||||||
|
value,
|
||||||
|
writable: false,
|
||||||
|
configurable: false,
|
||||||
|
enumerable: false,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
function evaluateExtractors(): Record<number, unknown> {
|
function evaluateExtractors(): Record<number, unknown> {
|
||||||
const state = buildState();
|
const state = buildState();
|
||||||
@@ -524,11 +536,11 @@ function pointOf(value: unknown): { x: number; y: number } | undefined {
|
|||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
(globalThis as Record<string, unknown>).__sanderlingExtractors__ = function (): Record<number, unknown> {
|
defineLockedGlobal("__sanderlingExtractors__", function (): Record<number, unknown> {
|
||||||
return evaluateExtractors();
|
return evaluateExtractors();
|
||||||
};
|
});
|
||||||
|
|
||||||
(globalThis as Record<string, unknown>).__sanderlingNextAction__ = function (): unknown {
|
defineLockedGlobal("__sanderlingNextAction__", function (): unknown {
|
||||||
if (!actionsRoot) return null;
|
if (!actionsRoot) return null;
|
||||||
// Match the goja runtime: retry up to 16 times when a weighted entry's
|
// Match the goja runtime: retry up to 16 times when a weighted entry's
|
||||||
// generator returns []. Otherwise on routes where most generators are
|
// generator returns []. Otherwise on routes where most generators are
|
||||||
@@ -538,6 +550,6 @@ function pointOf(value: unknown): { x: number; y: number } | undefined {
|
|||||||
if (action !== null) return action;
|
if (action !== null) return action;
|
||||||
}
|
}
|
||||||
return null;
|
return null;
|
||||||
};
|
});
|
||||||
|
|
||||||
export {};
|
export {};
|
||||||
Reference in new issue
Block a user