Last active
October 25, 2023 03:13
-
-
Save hungtcs/e79ac3069897d6e2c15f855d3253720d to your computer and use it in GitHub Desktop.
Simple JavaScript Sandbox
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
const parser = Sandbox.compile('a + b'); | |
const result = parser({ a: 1, b: 2 }); | |
// --- | |
const parser = Sandbox.compile('a + b + alert', { throwOnUndefined: true }); | |
const result = parser({ a: 1, b: 2 }); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
interface SandboxOptions { | |
throwOnUndefined?: boolean; | |
} | |
class Sandbox { | |
public static cache = new WeakMap(); | |
private constructor() { | |
} | |
public static compile(expression: string, options: SandboxOptions = {}) { | |
return (context: any) => { | |
let _context = Sandbox.cache.get(context); | |
if (!_context) { | |
_context = new Proxy( | |
context, | |
{ | |
get: (target, p) => { | |
if (p === Symbol.unscopables) { | |
return undefined; | |
} | |
const value = target[p]; | |
if (options.throwOnUndefined && value === undefined) { | |
throw new ReferenceError(`${ p.toString() } is not defined`); | |
} | |
return value; | |
}, | |
has: () => true, | |
}, | |
); | |
Sandbox.cache.set(context, _context); | |
} | |
return (new Function('context', `with(context) { return (${ expression }) }`))(_context) | |
}; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment