import { Uuid } from "../Uuid"; import { argumentNotEmptyString, getGlobal } from "../safe"; import { TraceSource } from "../log/TraceSource"; import m = require("module"); const sandboxId = Uuid(); define(sandboxId, ["require"], (r: any) => r); const globalRequire = getGlobal().require as Require || requirejs; const trace = TraceSource.get(m.id); trace.debug("globalRequire = {0}", globalRequire); class ModuleResolver { _base: string | undefined; _require: Require; constructor(req: Require, base?: string) { this._base = base; this._require = req; } resolve(moduleName: string) { argumentNotEmptyString(moduleName, "moduleName"); const resolvedName = moduleName[0] === "." && this._base ? [this._base, moduleName].join("/") : moduleName; trace.debug(`${moduleName} -> ${resolvedName}`); const req = this._require; return new Promise((cb, eb) => { req([resolvedName], cb, eb); }); } } export function makeResolver(moduleName: string, contextRequire: Require) { const base = moduleName && moduleName.split("/").slice(0, -1).join("/"); const req = contextRequire || globalRequire; if (!req) throw new Error("A global require isn't defined, the contextRequire parameter is mandatory"); const resolver = new ModuleResolver(req, base); return (id: string) => resolver.resolve(id); }