管理后台ui,动态性非常强,我猜这个项目会火
发布于 2 年前 作者 i5ting 2610 次浏览 来自 分享

https://github.com/cloudify-cosmo/cloudify-stage

export function importWidgetBackend(widgetId: string, isCustom = true) {
    let widgetsFolder = userWidgetsFolder;
    if (!isCustom) {
        widgetsFolder = builtInWidgetsFolder;
    }
    const backendFile = pathlib.resolve(widgetsFolder, widgetId, getConfig().app.widgets.backendFilename);

    function importWidgetBackendFromFile(extensions: string[]): Promise<any> {
        if (extensions.length === 0) {
            return Promise.resolve();
        }

        const extension = extensions.pop();

        const backendFileWithExtension = `${backendFile}.${extension}`;
        if (!fs.existsSync(backendFileWithExtension)) {
            return importWidgetBackendFromFile(extensions);
        }

        logger.info(`-- initializing file ${backendFileWithExtension}`);

        try {
            const vm = new NodeVM({
                sandbox: {
                    _,
                    widgetId,
                    BackendRegistrator
                },
                require: {
                    context: 'sandbox',
                    external: true,
                    root: [backendFileWithExtension, ...allowedModulesPaths]
                },
                compiler: source => ts.transpile(source, compilerOptions),
                sourceExtensions: getConfig().app.widgets.backendFilenameExtensions
            });

            const script = `
                    import backend from '${backendFileWithExtension.replace('\\', '\\\\')}';
                    module.exports = new Promise((resolve, reject) => {
                         try {
                             if (_.isFunction(backend)) {
                                 backend(BackendRegistrator(widgetId, resolve, reject));
                             } else {
                                 reject('Backend definition must be a function (module.exports = function(BackendRegistrator) {...})');
                             }
                         } catch (error) {
                             reject(error);
                         }
                     });`;

            return vm.run(script, { filename: pathlib.resolve(`${process.cwd()}/${widgetId}`) });
        } catch (err: any) {
            logger.error('reject', backendFileWithExtension, err);
            return Promise.reject(
                `Error during importing widget backend from file ${backendFileWithExtension} - ${err.message}`
            );
        }
    }

    return importWidgetBackendFromFile([...getConfig().app.widgets.backendFilenameExtensions]);
}

通过vm2动态执行ts,不错的思路

回到顶部