@sudoo/marked
Version:
JavaScript & TypeScript code runner in JavaScript, safe with marked territory, asynchronous
160 lines (159 loc) • 8.07 kB
JavaScript
"use strict";
/**
* @author WMXPY
* @namespace Util
* @description Import
*/
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.resolveImport = void 0;
const error_code_1 = require("../declare/error-code");
const evaluate_1 = require("../declare/evaluate");
const variable_1 = require("../declare/variable");
const declare_1 = require("../marked/declare");
const native_to_sand_1 = require("../parse/native-to-sand");
const flag_1 = require("../variable/flag");
const sand_map_1 = require("../variable/sand-map");
const error_1 = require("./error/error");
const resolveModuleImport = function (source, node, scope, currentTrace, nextTrace) {
return __awaiter(this, void 0, void 0, function* () {
const targetModule = this.module(source);
if (!Boolean(targetModule)) {
return false;
}
for (const specifier of node.specifiers) {
const target = yield this.execute(specifier, scope, nextTrace);
const register = scope.register(variable_1.VARIABLE_TYPE.CONSTANT);
switch (specifier.type) {
case "ImportDefaultSpecifier": {
if (!(typeof targetModule === "object" && Boolean(targetModule.default))) {
throw (0, error_1.error)(error_code_1.ERROR_CODE.IMPORT_DEFAULT_OBJECT_HAVE_NO_DEFAULT_EXPORT, target, node, currentTrace);
}
const moduleContent = targetModule.default;
const parsedContent = (0, native_to_sand_1.parseNativeToSand)(moduleContent);
register(target, parsedContent);
break;
}
case "ImportNamespaceSpecifier": {
if (!(typeof targetModule === "object")) {
throw (0, error_1.error)(error_code_1.ERROR_CODE.IMPORT_OBJECT_NOT_FOUND, target, node, currentTrace);
}
const parsedContent = (0, native_to_sand_1.parseNativeToSand)(targetModule);
register(target, parsedContent);
break;
}
case "ImportSpecifier": {
const imported = specifier.imported.type === "Literal"
? yield this.execute(specifier.imported, scope, nextTrace)
: specifier.imported.name;
if (!Boolean(targetModule[imported])) {
throw (0, error_1.error)(error_code_1.ERROR_CODE.IMPORT_OBJECT_NOT_FOUND, imported, node, currentTrace);
}
const moduleContent = targetModule[imported];
const parsedContent = (0, native_to_sand_1.parseNativeToSand)(moduleContent);
register(target, parsedContent);
break;
}
default: {
throw (0, error_1.error)(error_code_1.ERROR_CODE.UNKNOWN_ERROR, specifier.type, node, currentTrace);
}
}
}
return true;
});
};
const resolveDynamicImport = function (source, node, scope, currentTrace, nextTrace) {
return __awaiter(this, void 0, void 0, function* () {
const targetModule = yield this.resolveResource(source, currentTrace);
if (typeof targetModule !== "object"
|| !targetModule) {
return false;
}
const breakPoints = currentTrace.hasBreakPointController()
? currentTrace.ensureBreakPointController().getBreakPoints()
: undefined;
const executer = yield this.evaluateResource(targetModule, breakPoints);
if (executer.signal === declare_1.EVALUATE_RESOURCE_END_SIGNAL.CYCLED_IMPORT) {
const flag = flag_1.Flag.fromFatal(currentTrace);
const sourceScript = currentTrace.scriptLocation.hash();
const targetScript = targetModule.scriptLocation.hash();
flag.setValue((0, error_1.error)(error_code_1.ERROR_CODE.CYCLED_IMPORT, `source: [${sourceScript}], target: [${targetScript}]`, node, currentTrace));
return flag;
}
if (executer.signal === declare_1.EVALUATE_RESOURCE_END_SIGNAL.EVALUATE_FAILED) {
const result = executer.result;
if (result.signal === evaluate_1.END_SIGNAL.FAILED) {
throw result.error;
}
const flag = flag_1.Flag.fromThrow(currentTrace);
flag.setValue(executer.result);
return flag;
}
for (const specifier of node.specifiers) {
const target = yield this.execute(specifier, scope, nextTrace);
const register = scope.register(variable_1.VARIABLE_TYPE.CONSTANT);
const exposed = executer.executer.exposed;
switch (specifier.type) {
case "ImportDefaultSpecifier": {
if (!Boolean(exposed.default)) {
throw (0, error_1.error)(error_code_1.ERROR_CODE.IMPORT_DEFAULT_OBJECT_HAVE_NO_DEFAULT_EXPORT, target, node, currentTrace);
}
register(target, exposed.default);
break;
}
case "ImportNamespaceSpecifier": {
const namedKeys = Object.keys(exposed.named);
const importObject = {};
namedKeys.forEach((key) => {
importObject[key] = exposed.named[key];
});
const map = sand_map_1.SandMap.fromRawRecord(importObject);
register(target, map);
break;
}
case "ImportSpecifier": {
const namedMap = new Map();
const namedKeys = Object.keys(exposed.named);
for (const namedKey of namedKeys) {
namedMap.set(namedKey, exposed.named[namedKey]);
}
const imported = specifier.imported.type === "Literal"
? yield this.execute(specifier.imported, scope, nextTrace)
: specifier.imported.name;
if (!namedMap.has(imported)) {
throw (0, error_1.error)(error_code_1.ERROR_CODE.IMPORT_OBJECT_NOT_FOUND, imported, node, currentTrace);
}
register(target, namedMap.get(imported));
break;
}
default: {
throw (0, error_1.error)(error_code_1.ERROR_CODE.UNKNOWN_ERROR, specifier.type, node, currentTrace);
}
}
}
return true;
});
};
const resolveImport = function (source, node, scope, currentTrace, nextTrace) {
return __awaiter(this, void 0, void 0, function* () {
const bindResolveModuleImport = resolveModuleImport.bind(this);
const result = yield bindResolveModuleImport(source, node, scope, currentTrace, nextTrace);
if (result instanceof flag_1.Flag) {
return result;
}
if (result) {
return result;
}
const bindResolveDynamicImport = resolveDynamicImport.bind(this);
return yield bindResolveDynamicImport(source, node, scope, currentTrace, nextTrace);
});
};
exports.resolveImport = resolveImport;