152 lines
4.5 KiB
TypeScript
152 lines
4.5 KiB
TypeScript
|
/**
|
||
|
* @author Martin Karkowski
|
||
|
* @email m.karkowski@zema.de
|
||
|
* @create date 2020-11-11 14:19:10
|
||
|
* @modify date 2020-11-11 16:12:18
|
||
|
* @desc [description]
|
||
|
*/
|
||
|
|
||
|
import { readFile } from "fs/promises";
|
||
|
import { join, resolve } from "path";
|
||
|
import "reflect-metadata";
|
||
|
import { createFile, listFiles } from '../helpers/fileMethods';
|
||
|
import { getNopeLogger } from "../logger/getLogger";
|
||
|
import { IInstanceCreationMsg } from "../types/nope/nopeCommunication.interface";
|
||
|
import { IPackageDescription } from "../types/nope/nopePackage.interface";
|
||
|
import { INopePackageLoader } from "../types/nope/nopePackageLoader.interface";
|
||
|
|
||
|
export interface IConfigFile {
|
||
|
nameOfPackage: string;
|
||
|
defaultInstances: {
|
||
|
options: Partial<IInstanceCreationMsg>;
|
||
|
selector: string | symbol;
|
||
|
}[];
|
||
|
autostart: {
|
||
|
[index: string]: {
|
||
|
delay?: number;
|
||
|
params: any[];
|
||
|
}[];
|
||
|
};
|
||
|
// File Path of the element.
|
||
|
path: string;
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
* List the available Packages
|
||
|
*
|
||
|
* @export
|
||
|
* @param {string} [dir='./modules']
|
||
|
* @return {*}
|
||
|
*/
|
||
|
export async function listPackages(dir: string = './modules') {
|
||
|
|
||
|
// Define the Return Array.
|
||
|
const ret = new Array<{
|
||
|
package: IPackageDescription<any>,
|
||
|
path: string,
|
||
|
}>();
|
||
|
|
||
|
// Scan for the Package-Files
|
||
|
// And iterate over them.
|
||
|
for (const fileName of await listFiles(dir, '.package.js')) {
|
||
|
// Now Try to load a Package, to test whether is is an assembly.
|
||
|
try {
|
||
|
ret.push({
|
||
|
package: (await import(resolve(fileName))).DESCRIPTION as IPackageDescription<any>,
|
||
|
path: fileName
|
||
|
});
|
||
|
} catch (e) {
|
||
|
getNopeLogger('helper-list-packages').error('Failed Loading the Assembly ' + fileName);
|
||
|
getNopeLogger('helper-list-packages').error(e);
|
||
|
}
|
||
|
|
||
|
}
|
||
|
|
||
|
return ret;
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
* Helper Function to write a default configuration.
|
||
|
*
|
||
|
* @export
|
||
|
* @param {string} [dir='./modules']
|
||
|
* @param {string} [filename=join(resolve(process.cwd()), 'config', 'assembly.json')]
|
||
|
*/
|
||
|
export async function writeDefaultConfig(
|
||
|
dir: string = './modules',
|
||
|
filename: string = join(resolve(process.cwd()), 'config', 'assembly.json')
|
||
|
) {
|
||
|
// Determine all Packages
|
||
|
const packages = await listPackages(dir);
|
||
|
const valuesToStore: IConfigFile[] = packages.map(item => {
|
||
|
return {
|
||
|
nameOfPackage: item.package.nameOfPackage,
|
||
|
defaultInstances: item.package.defaultInstances,
|
||
|
autostart: item.package.autostart,
|
||
|
path: item.path
|
||
|
}
|
||
|
});
|
||
|
|
||
|
await createFile(filename, JSON.stringify(valuesToStore, undefined, 4));
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
* Function to load the Packages.
|
||
|
*
|
||
|
* @export
|
||
|
* @param {INopePackageLoader} loader
|
||
|
* @param {string} filename
|
||
|
*/
|
||
|
export async function loadPackages(loader: INopePackageLoader,filename: string = join(resolve(process.cwd()), 'config', 'assembly.json')) {
|
||
|
let data: IConfigFile[] = [];
|
||
|
|
||
|
try {
|
||
|
/** Load the File and Parse it. */
|
||
|
data = JSON.parse(
|
||
|
await readFile(filename,{encoding: 'utf8'})
|
||
|
);
|
||
|
} catch (e) {
|
||
|
|
||
|
// Generate the Default File
|
||
|
await writeDefaultConfig(filename);
|
||
|
|
||
|
// Show an Hint
|
||
|
getNopeLogger('helper-load-packages').warn('No configuration was present. Created a new config file in ' + filename);
|
||
|
|
||
|
// Readin the newly created Data.
|
||
|
data = JSON.parse(await readFile(
|
||
|
filename, {
|
||
|
encoding:'utf8'
|
||
|
})
|
||
|
);
|
||
|
}
|
||
|
|
||
|
// Define the Return Array.
|
||
|
const packages = new Array<IPackageDescription<any>>();
|
||
|
|
||
|
// Scan for the Package-Files
|
||
|
// And iterate over them.
|
||
|
for (const item of data) {
|
||
|
// Now Try to load a Package, to test whether is is an assembly.
|
||
|
try {
|
||
|
const loadedPackage = (await import(resolve(item.path))).DESCRIPTION as IPackageDescription<any>;
|
||
|
loadedPackage.autostart = item.autostart;
|
||
|
loadedPackage.defaultInstances = item.defaultInstances;
|
||
|
packages.push(loadedPackage);
|
||
|
} catch (e) {
|
||
|
getNopeLogger('helper-load-packages').error('Failed Loading Package ' + item.nameOfPackage, e);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// Iterate over the Packages
|
||
|
for (const thePackageToLoad of packages) {
|
||
|
try {
|
||
|
await loader.addPackage(thePackageToLoad);
|
||
|
} catch (e) {
|
||
|
getNopeLogger('helper-load-packages').error('Failed Add the Package "' + thePackageToLoad.nameOfPackage + '" to the PackageLoader', e);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// Generate the instances.
|
||
|
await loader.generateInstances()
|
||
|
}
|