feat(App): Loads mode extensions on demand (#3312)
* feat: Dynamic plugin imports * Remove unused file * Fix basic dev mode * Fix the modes issue that Joe requested * Merge fixes * Add the ability to publish directory contents * PR review changes ---------
This commit is contained in:
1 parent
2f355fa158
commit
a688f03fdb
11 files changed
+225
-197
No files matched your search
@@ -1,11 +1,14 @@
|
||||
const pluginConfig = require('../pluginConfig.json');
|
||||
const fs = require('fs');
|
||||
const os = require('os');
|
||||
const glob = require('glob');
|
||||
|
||||
const autogenerationDisclaimer = `
|
||||
// THIS FILE IS AUTOGENERATED AS PART OF THE EXTENSION AND MODE PLUGIN PROCESS.
|
||||
// IT SHOULD NOT BE MODIFIED MANUALLY \n`;
|
||||
|
||||
const extractName = (val) => (typeof val === 'string') ? val : val.packageName;
|
||||
|
||||
function constructLines(input, categoryName) {
|
||||
let pluginCount = 0;
|
||||
|
||||
@@ -19,14 +22,10 @@ function constructLines(input, categoryName) {
|
||||
input.forEach(entry => {
|
||||
if (entry.default === false) return;
|
||||
|
||||
const packageName = entry.packageName;
|
||||
const defaultImportName = `${categoryName}${pluginCount}`;
|
||||
const packageName = extractName(entry);
|
||||
|
||||
lines.importLines.push(
|
||||
`import ${defaultImportName} from '${packageName}';\n`
|
||||
);
|
||||
lines.addToWindowLines.push(
|
||||
`${categoryName}.push(${defaultImportName});\n`
|
||||
`${categoryName}.push("${packageName}");\n`
|
||||
);
|
||||
|
||||
pluginCount++;
|
||||
@@ -49,7 +48,7 @@ function getFormattedWindowBlock(addToWindowLines) {
|
||||
let content =
|
||||
'const extensions = [];\n' +
|
||||
'const modes = [];\n' +
|
||||
'const modesFactory = [];\n' +
|
||||
'\n// Not required any longer\n' +
|
||||
'window.extensions = extensions;\n' +
|
||||
'window.modes = modes;\n\n';
|
||||
|
||||
@@ -60,47 +59,55 @@ function getFormattedWindowBlock(addToWindowLines) {
|
||||
return content;
|
||||
}
|
||||
|
||||
function getRuntimeLoadModesExtensions() {
|
||||
return (
|
||||
'\n\n// Add a dynamic runtime loader\n' +
|
||||
'export default async () => {\n' +
|
||||
' for(const modeFactory of modesFactory) {\n' +
|
||||
' const newModes = await modeFactory(modes,extensions);\n' +
|
||||
' newModes.forEach(newMode => modes.push(newMode));\n' +
|
||||
'}\n}\n\n\n' +
|
||||
'async function loadRuntimeImports(config) {\n' +
|
||||
' if (config && config.modes && config.modes.length) {\n' +
|
||||
' for (const modeName of config.modes) {\n' +
|
||||
' const existingMode = modes.find(mode => mode.id === modeName);\n' +
|
||||
' if (!existingMode) {\n' +
|
||||
' if (modeName === `@ohif/mode-test`) {\n' +
|
||||
' const mode = await import(`@ohif/mode-test`);\n' +
|
||||
' window.modes.push(mode.default);\n' +
|
||||
' const extension = await import(`@ohif/extension-test`);\n' +
|
||||
' window.extensions.push(extension.default);\n' +
|
||||
' }\n' +
|
||||
' }\n' +
|
||||
' };\n' +
|
||||
' }\n' +
|
||||
'}\n' +
|
||||
'export { loadRuntimeImports };\n\n'
|
||||
);
|
||||
function getRuntimeLoadModesExtensions(modules) {
|
||||
const dynamicLoad = [];
|
||||
dynamicLoad.push(
|
||||
'\n\n// Add a dynamic runtime loader',
|
||||
'async function loadModule(module) {',
|
||||
' if (typeof module !== \'string\') return module;');
|
||||
modules.forEach(module => {
|
||||
const packageName = extractName(module);
|
||||
dynamicLoad.push(
|
||||
` if( module==="${packageName}") {`,
|
||||
` const imported = await import("${packageName}");`,
|
||||
' return imported.default;',
|
||||
' }'
|
||||
);
|
||||
})
|
||||
dynamicLoad.push(
|
||||
' return (await import(module)).default;',
|
||||
'}\n',
|
||||
'// Import a list of items (modules or string names)',
|
||||
'// @return a Promise evaluating to a list of modules',
|
||||
'export default function importItems(modules) {',
|
||||
' return Promise.all(modules.map(loadModule));',
|
||||
'}\n',
|
||||
'export { loadModule, modes, extensions, importItems };\n\n');
|
||||
return dynamicLoad.join('\n');
|
||||
}
|
||||
|
||||
const fromDirectory = (srcDir, path) => {
|
||||
if (!path) return;
|
||||
if (path[0] === '.') return srcDir + '/../../..' + path.substring(1);
|
||||
if (path[0] === '~') return os.homedir() + path.substring(1);
|
||||
return path;
|
||||
}
|
||||
|
||||
const createCopyPluginToDistForLink = (
|
||||
SRC_DIR,
|
||||
DIST_DIR,
|
||||
srcDir,
|
||||
distDir,
|
||||
plugins,
|
||||
folderName
|
||||
) => {
|
||||
return plugins
|
||||
.map(plugin => {
|
||||
const from = `${SRC_DIR}/../node_modules/${plugin.packageName}/${folderName}/`;
|
||||
const fromDir = fromDirectory(srcDir, plugin.directory);
|
||||
const from = fromDir || `${srcDir}/../node_modules/${plugin.packageName}/${folderName}/`;
|
||||
const exists = fs.existsSync(from);
|
||||
return exists
|
||||
? {
|
||||
from,
|
||||
to: DIST_DIR,
|
||||
to: distDir,
|
||||
toType: 'dir',
|
||||
}
|
||||
: undefined;
|
||||
@@ -134,23 +141,20 @@ function writePluginImportsFile(SRC_DIR, DIST_DIR) {
|
||||
|
||||
const extensionLines = constructLines(pluginConfig.extensions, 'extensions');
|
||||
const modeLines = constructLines(pluginConfig.modes, 'modes');
|
||||
const modesFactoryLines = constructLines(
|
||||
pluginConfig.modesFactory,
|
||||
'modesFactory'
|
||||
);
|
||||
|
||||
pluginImportsJsContent += getFormattedImportBlock([
|
||||
...extensionLines.importLines,
|
||||
...modeLines.importLines,
|
||||
...modesFactoryLines.importLines,
|
||||
]);
|
||||
pluginImportsJsContent += getFormattedWindowBlock([
|
||||
...extensionLines.addToWindowLines,
|
||||
...modeLines.addToWindowLines,
|
||||
...modesFactoryLines.addToWindowLines,
|
||||
]);
|
||||
|
||||
pluginImportsJsContent += getRuntimeLoadModesExtensions();
|
||||
pluginImportsJsContent += getRuntimeLoadModesExtensions([
|
||||
...pluginConfig.extensions,
|
||||
...pluginConfig.modes,
|
||||
]);
|
||||
|
||||
fs.writeFileSync(
|
||||
`${SRC_DIR}/pluginImports.js`,
|
||||
@@ -172,10 +176,8 @@ function writePluginImportsFile(SRC_DIR, DIST_DIR) {
|
||||
SRC_DIR,
|
||||
DIST_DIR,
|
||||
[
|
||||
...pluginConfig.modesFactory,
|
||||
...pluginConfig.modes,
|
||||
...pluginConfig.extensions,
|
||||
...pluginConfig.umd,
|
||||
],
|
||||
'public'
|
||||
);
|
||||
@@ -184,10 +186,9 @@ function writePluginImportsFile(SRC_DIR, DIST_DIR) {
|
||||
SRC_DIR,
|
||||
DIST_DIR,
|
||||
[
|
||||
...pluginConfig.modesFactory,
|
||||
...pluginConfig.modes,
|
||||
...pluginConfig.extensions,
|
||||
...pluginConfig.umd,
|
||||
...pluginConfig.public,
|
||||
],
|
||||
'public'
|
||||
);
|
||||
@@ -198,10 +199,8 @@ function writePluginImportsFile(SRC_DIR, DIST_DIR) {
|
||||
SRC_DIR,
|
||||
DIST_DIR,
|
||||
[
|
||||
...pluginConfig.modesFactory,
|
||||
...pluginConfig.modes,
|
||||
...pluginConfig.extensions,
|
||||
...pluginConfig.umd,
|
||||
],
|
||||
'dist'
|
||||
);
|
||||
@@ -210,15 +209,13 @@ function writePluginImportsFile(SRC_DIR, DIST_DIR) {
|
||||
SRC_DIR,
|
||||
DIST_DIR,
|
||||
[
|
||||
...pluginConfig.modesFactory,
|
||||
...pluginConfig.modes,
|
||||
...pluginConfig.extensions,
|
||||
...pluginConfig.umd,
|
||||
],
|
||||
'dist'
|
||||
);
|
||||
|
||||
console.log('copy plugins', [
|
||||
console.warn('copy plugins', [
|
||||
...copyPluginPublicToDistBuild,
|
||||
...copyPluginPublicToDistLink,
|
||||
...copyPluginDistToDistBuild,
|
||||
|
||||
Reference in new issue
Block a user