@iobroker/plugin-base
Advanced tools
Comparing version
@@ -5,12 +5,27 @@ export = NamespaceLogger; | ||
* @param {string} namespaceLog Logging namespace to prefix | ||
* @param {object} logger logger instance | ||
* @param {ioBroker.Logger} logger logger instance | ||
*/ | ||
constructor(namespaceLog: string, logger: object); | ||
constructor(namespaceLog: string, logger: ioBroker.Logger); | ||
namespaceLog: string; | ||
logger: object; | ||
silly(msg: any): void; | ||
debug(msg: any): void; | ||
info(msg: any): void; | ||
error(msg: any): void; | ||
warn(msg: any): void; | ||
logger: ioBroker.Logger; | ||
/** | ||
* @param {string} msg | ||
*/ | ||
silly(msg: string): void; | ||
/** | ||
* @param {string} msg | ||
*/ | ||
debug(msg: string): void; | ||
/** | ||
* @param {string} msg | ||
*/ | ||
info(msg: string): void; | ||
/** | ||
* @param {string} msg | ||
*/ | ||
error(msg: string): void; | ||
/** | ||
* @param {string} msg | ||
*/ | ||
warn(msg: string): void; | ||
} |
class NamespaceLogger { | ||
/** | ||
* @param {string} namespaceLog Logging namespace to prefix | ||
* @param {object} logger logger instance | ||
* @param {ioBroker.Logger} logger logger instance | ||
*/ | ||
@@ -20,14 +20,29 @@ constructor(namespaceLog, logger) { | ||
} | ||
/** | ||
* @param {string} msg | ||
*/ | ||
silly(msg) { | ||
this.logger.silly(this.namespaceLog + ' ' + msg); | ||
} | ||
/** | ||
* @param {string} msg | ||
*/ | ||
debug(msg) { | ||
this.logger.debug(this.namespaceLog + ' ' + msg); | ||
} | ||
/** | ||
* @param {string} msg | ||
*/ | ||
info(msg) { | ||
this.logger.info(this.namespaceLog + ' ' + msg); | ||
} | ||
/** | ||
* @param {string} msg | ||
*/ | ||
error(msg) { | ||
this.logger.error(this.namespaceLog + ' ' + msg); | ||
} | ||
/** | ||
* @param {string} msg | ||
*/ | ||
warn(msg) { | ||
@@ -34,0 +49,0 @@ this.logger.warn(this.namespaceLog + ' ' + msg); |
@@ -15,2 +15,3 @@ /// <reference path="types.d.ts" /> | ||
pluginScope: "adapter" | "controller"; | ||
parentNamespace: string; | ||
pluginNamespace: string; | ||
@@ -20,4 +21,5 @@ log: import("./NamespaceLogger"); | ||
parentPackage: Record<string, any>; | ||
objectsDb: object | null; | ||
statesDb: object | null; | ||
settings: import("@iobroker/plugin-base/types").PluginSettings; | ||
objectsDb: any; | ||
statesDb: any; | ||
isActive: boolean; | ||
@@ -49,9 +51,25 @@ SCOPES: { | ||
/** | ||
* Get a State from State DB | ||
* | ||
* @param {string} id id of the state to retrieve | ||
* @return {ReturnType<ioBroker.Adapter["getStateAsync"]>} Promise with error or result | ||
*/ | ||
getStateAsync(id: string): Promise<ioBroker.State>; | ||
/** | ||
* Set a State in State DB | ||
* | ||
* @param {string} id id of the state to set | ||
* @param {Partial<ioBroker.State>} state state value to set | ||
* @param {ioBroker.SetStateCallback} [callback] Will be called with the result | ||
*/ | ||
setState(id: string, state: any, callback?: ioBroker.SetStateCallback | undefined): void; | ||
setState(id: string, state: Partial<ioBroker.State>, callback?: ioBroker.SetStateCallback): void; | ||
/** | ||
* Set a State in State DB | ||
* | ||
* @param {string} id id of the state to set | ||
* @param {Partial<ioBroker.State>} state state value to set | ||
* @return {Promise<ioBroker.State | null | undefined>} Promise with error or result | ||
*/ | ||
setStateAsync(id: string, state: Partial<ioBroker.State>): Promise<ioBroker.State>; | ||
/** | ||
* Get an Object from Objects DB | ||
@@ -64,15 +82,44 @@ * | ||
/** | ||
* Get an Object from Objects DB | ||
* | ||
* @param {string} id id of the object to retrieve | ||
* @return {Promise<ioBroker.Object | null | undefined>} Promise with result or error | ||
*/ | ||
getObjectAsync(id: string): Promise<ioBroker.Object>; | ||
/** | ||
* Set an Object in Objects DB | ||
* | ||
* @param {string} id id of the object to set | ||
* @param {ioBroker.Object} obj object to set | ||
* @param {ioBroker.SetObjectCallback} [callback] Will be called with the result | ||
*/ | ||
setObject(id: string, obj: any, callback?: ioBroker.SetObjectCallback | undefined): void; | ||
setObject(id: string, obj: ioBroker.Object, callback?: ioBroker.SetObjectCallback): void; | ||
/** | ||
* Set an Object in Objects DB | ||
* | ||
* @param {string} id id of the object to set | ||
* @param {ioBroker.Object} obj object to set | ||
* @return {ReturnType<ioBroker.Adapter["setObjectAsync"]>} Promise with error or result | ||
*/ | ||
setObjectAsync(id: string, obj: ioBroker.Object): Promise<{ | ||
id: string; | ||
}>; | ||
/** | ||
* Set/Extend an Object in Objects DB | ||
* | ||
* @param {string} id id of the object to set/extend | ||
* @param {ioBroker.Object} obj object to set | ||
* @param {ioBroker.ExtendObjectCallback} [callback] Will be called with the result | ||
*/ | ||
extendObject(id: string, obj: any, callback?: ioBroker.ExtendObjectCallback | undefined): void; | ||
extendObject(id: string, obj: ioBroker.Object, callback?: ioBroker.ExtendObjectCallback): void; | ||
/** | ||
* Set/Extend an Object in Objects DB | ||
* | ||
* @param {string} id id of the object to set/extend | ||
* @param {object} obj object to set | ||
* @return {ReturnType<ioBroker.Adapter["extendObjectAsync"]>} Promise with result or error | ||
*/ | ||
extendObjectAsync(id: string, obj: any): Promise<{ | ||
id: string; | ||
}>; | ||
/**************************************** | ||
@@ -82,26 +129,34 @@ * Internal methods!! | ||
/** | ||
* set The Active flag for the plugin | ||
* @internal | ||
* Set the Active flag for the plugin | ||
* | ||
* @param active {boolean} true/false if active | ||
* @param {boolean} active true/false if active | ||
*/ | ||
setActive(active: boolean): void; | ||
setActive(active: boolean): Promise<void>; | ||
/** | ||
* @internal | ||
* Set the objects and states database to be used internally | ||
* This method is called by js-controller/adapter process internally when initializing the plugin. | ||
* | ||
* @private | ||
* @param objectsDb {object} objects DB instance | ||
* @param statesDb {object} states DB instance | ||
* @param {any} objectsDb objects DB instance | ||
* @param {any} statesDb states DB instance | ||
*/ | ||
private setDatabase; | ||
setDatabase(objectsDb: any, statesDb: any): void; | ||
/** | ||
* @internal | ||
* Initialize plugin, internal method | ||
* | ||
* @private | ||
* @param pluginConfig {object} plugin configuration from config files | ||
* @param parentConfig {object} io-package from parent module where plugin is used in | ||
* @param callback {function} callback when done, signature "(err, initSuccessful)". On err or initSuccessful===false the plugin instance will be discarded | ||
* @param {Record<string, any>} pluginConfig plugin configuration from config files | ||
* @param {Record<string, any>} parentConfig io-package from parent module where plugin is used in | ||
* @param {import("@iobroker/plugin-base/types").InitCallback} callback Will be called when done. On err or `initSuccessful === false` the plugin instance will be discarded. | ||
*/ | ||
private initPlugin; | ||
parentIoPackage: object | undefined; | ||
initPlugin(pluginConfig: Record<string, any>, parentConfig: Record<string, any>, callback: import("@iobroker/plugin-base/types").InitCallback): Promise<void>; | ||
parentIoPackage: Record<string, any>; | ||
/** | ||
* @internal | ||
* @param {Record<string, any>} pluginConfig | ||
* @param {string | boolean} activate | ||
* @param {import("@iobroker/plugin-base/types").InitCallback} callback | ||
*/ | ||
_initialize(pluginConfig: Record<string, any>, activate: string | boolean, callback: import("@iobroker/plugin-base/types").InitCallback): Promise<void>; | ||
} |
@@ -17,2 +17,3 @@ /// <reference path="./types.d.ts" /> | ||
this.pluginScope = settings.pluginScope; | ||
this.parentNamespace = settings.parentNamespace; | ||
this.pluginNamespace = settings.pluginNamespace; | ||
@@ -22,2 +23,3 @@ this.log = new NamespaceLogger(settings.pluginLogNamespace, settings.log); | ||
this.parentPackage = settings.parentPackage || {}; | ||
this.settings = settings; | ||
@@ -43,3 +45,3 @@ this.objectsDb = null; | ||
// Implement in your Plugin instance if needed | ||
callback('Not implemented'); | ||
callback(new Error('Not implemented')); | ||
} | ||
@@ -71,5 +73,19 @@ | ||
/** | ||
* Get a State from State DB | ||
* | ||
* @param {string} id id of the state to retrieve | ||
* @return {ReturnType<ioBroker.Adapter["getStateAsync"]>} Promise with error or result | ||
*/ | ||
getStateAsync(id) { | ||
if (!this.statesDb) { | ||
return Promise.reject(new Error('States Database not initialized.')); | ||
} | ||
return this.statesDb.getStateAsync(id); | ||
} | ||
/** | ||
* Set a State in State DB | ||
* | ||
* @param {string} id id of the state to set | ||
* @param {Partial<ioBroker.State>} state state value to set | ||
* @param {ioBroker.SetStateCallback} [callback] Will be called with the result | ||
@@ -85,2 +101,16 @@ */ | ||
/** | ||
* Set a State in State DB | ||
* | ||
* @param {string} id id of the state to set | ||
* @param {Partial<ioBroker.State>} state state value to set | ||
* @return {Promise<ioBroker.State | null | undefined>} Promise with error or result | ||
*/ | ||
setStateAsync(id, state) { | ||
if (!this.statesDb) { | ||
return Promise.reject(new Error('States Database not initialized.')); | ||
} | ||
return this.statesDb.setStateAsync(id, state); | ||
} | ||
/** | ||
* Get an Object from Objects DB | ||
@@ -99,5 +129,19 @@ * | ||
/** | ||
* Get an Object from Objects DB | ||
* | ||
* @param {string} id id of the object to retrieve | ||
* @return {Promise<ioBroker.Object | null | undefined>} Promise with result or error | ||
*/ | ||
getObjectAsync(id) { | ||
if (!this.objectsDb) { | ||
return Promise.reject(new Error('Objects Database not initialized.')); | ||
} | ||
return this.objectsDb.getObjectAsync(id); | ||
} | ||
/** | ||
* Set an Object in Objects DB | ||
* | ||
* @param {string} id id of the object to set | ||
* @param {ioBroker.Object} obj object to set | ||
* @param {ioBroker.SetObjectCallback} [callback] Will be called with the result | ||
@@ -113,5 +157,20 @@ */ | ||
/** | ||
* Set an Object in Objects DB | ||
* | ||
* @param {string} id id of the object to set | ||
* @param {ioBroker.Object} obj object to set | ||
* @return {ReturnType<ioBroker.Adapter["setObjectAsync"]>} Promise with error or result | ||
*/ | ||
setObjectAsync(id, obj) { | ||
if (!this.objectsDb) { | ||
return Promise.reject(new Error('Objects Database not initialized.')); | ||
} | ||
return this.objectsDb.setObjectAsync(id, obj); | ||
} | ||
/** | ||
* Set/Extend an Object in Objects DB | ||
* | ||
* @param {string} id id of the object to set/extend | ||
* @param {ioBroker.Object} obj object to set | ||
* @param {ioBroker.ExtendObjectCallback} [callback] Will be called with the result | ||
@@ -126,2 +185,16 @@ */ | ||
/** | ||
* Set/Extend an Object in Objects DB | ||
* | ||
* @param {string} id id of the object to set/extend | ||
* @param {object} obj object to set | ||
* @return {ReturnType<ioBroker.Adapter["extendObjectAsync"]>} Promise with result or error | ||
*/ | ||
extendObjectAsync(id, obj) { | ||
if (!this.objectsDb) { | ||
return Promise.reject(new Error('Objects Database not initialized.')); | ||
} | ||
return this.objectsDb.extendObjectAsync(id, obj); | ||
} | ||
/**************************************** | ||
@@ -132,9 +205,10 @@ * Internal methods!! | ||
/** | ||
* set The Active flag for the plugin | ||
* @internal | ||
* Set the Active flag for the plugin | ||
* | ||
* @param {boolean} active true/false if active | ||
*/ | ||
setActive(active) { | ||
async setActive(active) { | ||
this.isActive = !!active; | ||
this.setState(this.pluginNamespace + '.enabled', { | ||
await this.setStateAsync(this.pluginNamespace + '.enabled', { | ||
val: !!active, | ||
@@ -147,8 +221,8 @@ ack: true, | ||
/** | ||
* @internal | ||
* Set the objects and states database to be used internally | ||
* This method is called by js-controller/adapter process internally when initializing the plugin. | ||
* | ||
* @private | ||
* @param {obj} objectsDb objects DB instance | ||
* @param {obj} statesDb states DB instance | ||
* @param {any} objectsDb objects DB instance | ||
* @param {any} statesDb states DB instance | ||
*/ | ||
@@ -161,5 +235,5 @@ setDatabase(objectsDb, statesDb) { | ||
/** | ||
* @internal | ||
* Initialize plugin, internal method | ||
* | ||
* @private | ||
* @param {Record<string, any>} pluginConfig plugin configuration from config files | ||
@@ -169,9 +243,9 @@ * @param {Record<string, any>} parentConfig io-package from parent module where plugin is used in | ||
*/ | ||
initPlugin(pluginConfig, parentConfig, callback) { | ||
async initPlugin(pluginConfig, parentConfig, callback) { | ||
if (!pluginConfig) { | ||
return void callback('No configuration for plugin'); | ||
return void callback(new Error('No configuration for plugin')); | ||
} | ||
this.parentIoPackage = parentConfig; | ||
this.extendObject(this.pluginNamespace, { | ||
await this.extendObjectAsync(this.pluginNamespace, { | ||
type: 'folder', | ||
@@ -182,52 +256,61 @@ common: { | ||
native: {} | ||
}, () => { | ||
this.extendObject(this.pluginNamespace + '.enabled', { | ||
type: 'state', | ||
common: { | ||
name: 'Plugin - enabled', | ||
type: 'boolean', | ||
read: true, | ||
write: true, | ||
role: 'value' | ||
}, | ||
native: {} | ||
}, (_err) => { | ||
this.getState(this.pluginNamespace + '.enabled', (err, state) => { | ||
if (err || !state || typeof state.val === 'object' || state.val === undefined) { | ||
// We have first start and no enabled flag is set | ||
if (this.pluginScope === this.SCOPES.ADAPTER && parentConfig && parentConfig.common && parentConfig.common.host) { | ||
// We check if the host has a sentry enabled flag | ||
const hostNamespace = this.pluginNamespace.replace(new RegExp('system\.adapter\.' + parentConfig.common.name + '\.[0-9]+\.'), 'system.host.' + parentConfig.common.host + '.'); | ||
this.getState(hostNamespace + '.enabled', (err, hostState) => { | ||
if (err || !hostState || typeof hostState.val !== 'boolean' || hostState.val === undefined) { | ||
// No host enabled flag is set, so we use default | ||
this._initialize(pluginConfig, pluginConfig.enabled === undefined ? true : !!pluginConfig.enabled, callback); | ||
} else { | ||
// We simply use the host enabled flag state | ||
this._initialize(pluginConfig, !!hostState.val, callback); | ||
} | ||
}); | ||
}); | ||
await this.extendObjectAsync(this.pluginNamespace + '.enabled', { | ||
type: 'state', | ||
common: { | ||
name: 'Plugin - enabled', | ||
type: 'boolean', | ||
read: true, | ||
write: true, | ||
role: 'value' | ||
}, | ||
native: {} | ||
}); | ||
} else { | ||
//use default value | ||
this._initialize(pluginConfig, pluginConfig.enabled === undefined ? true : !!pluginConfig.enabled, callback); | ||
} | ||
} else { | ||
// We already have a enabled flag state, use it | ||
this._initialize(pluginConfig, !!state.val, callback); | ||
} | ||
}); | ||
}); | ||
}); | ||
let pluginEnabledState; | ||
try { | ||
pluginEnabledState = await this.getStateAsync(this.pluginNamespace + '.enabled'); | ||
} catch { | ||
// ignore | ||
} | ||
if (pluginEnabledState && typeof pluginEnabledState.val !== 'object' && pluginEnabledState.val !== undefined) { | ||
// We already have a enabled flag state, use it | ||
return this._initialize(pluginConfig, !!pluginEnabledState.val, callback); | ||
} | ||
// We have first start and no enabled flag is set | ||
if (this.pluginScope === this.SCOPES.ADAPTER && parentConfig && parentConfig.common && parentConfig.common.host) { | ||
// We check if the host has a sentry enabled flag | ||
const hostNamespace = this.pluginNamespace.replace(new RegExp('system\.adapter\.' + parentConfig.common.name + '\.[0-9]+\.'), 'system.host.' + parentConfig.common.host + '.'); | ||
let hostState; | ||
try { | ||
hostState = await this.getStateAsync(hostNamespace + '.enabled'); | ||
} catch { | ||
// ignore | ||
} | ||
if (hostState && typeof hostState.val !== 'object' && hostState.val !== undefined) { | ||
// We simply use the host enabled flag state | ||
return this._initialize(pluginConfig, !!hostState.val, callback); | ||
} | ||
} | ||
this._initialize(pluginConfig, pluginConfig.enabled === undefined ? true : !!pluginConfig.enabled, callback); | ||
} | ||
_initialize(pluginConfig, activate, callback) { | ||
/** | ||
* @internal | ||
* @param {Record<string, any>} pluginConfig | ||
* @param {string | boolean} activate | ||
* @param {import("@iobroker/plugin-base/types").InitCallback} callback | ||
*/ | ||
async _initialize(pluginConfig, activate, callback) { | ||
if (activate) { | ||
this.log.debug('Initialize Plugin (enabled=' + activate + ')'); | ||
pluginConfig.enabled = activate; | ||
this.init(pluginConfig, (err, success) => { | ||
this.init(pluginConfig, async (err, success) => { | ||
if (!err && success) { | ||
this.setActive(true); | ||
await this.setActive(true); | ||
} else { | ||
this.setActive(false); | ||
await this.setActive(false); | ||
} | ||
@@ -238,3 +321,3 @@ callback(err, success); | ||
this.log.debug('Do not initialize Plugin (enabled=' + activate + ')'); | ||
this.setActive(false); | ||
await this.setActive(false); | ||
callback(null, false); | ||
@@ -241,0 +324,0 @@ } |
@@ -0,1 +1,2 @@ | ||
/// <reference path="types.d.ts" /> | ||
export = PluginHandler; | ||
@@ -7,70 +8,66 @@ /** | ||
/** | ||
* Constructore for PluginHandler | ||
* Constructor for PluginHandler | ||
* | ||
* @param settings {object} object with configuration: | ||
* { | ||
* scope: 'adapter', // or 'controller' | ||
* namespace: 'system.adapter.myname.0.plugins.name', // or 'system.host.name.plugins.name' | ||
* logNamespace: 'myname.0', | ||
* log: {...}, // logger object | ||
* iobrokerConfig: {...}, // ioBroker configuration | ||
* parentPackage: {...} // package.json from "parent" which uses the plugin (adapter/controller) | ||
* } | ||
* @param {import("@iobroker/plugin-base/types").PluginHandlerSettings} settings | ||
*/ | ||
constructor(settings: object); | ||
settings: object; | ||
constructor(settings: import("@iobroker/plugin-base/types").PluginHandlerSettings); | ||
settings: import("@iobroker/plugin-base/types").PluginHandlerSettings; | ||
log: import("./NamespaceLogger"); | ||
plugins: {}; | ||
/** @type {Record<string, {config: Record<string, any>, instance?: import("./PluginBase") | null}>} */ | ||
plugins: Record<string, { | ||
config: Record<string, any>; | ||
instance?: import("./PluginBase") | null; | ||
}>; | ||
/** | ||
* Add plugins to the handler, resolve and require the plugin code and create instance | ||
* | ||
* @param configs {object} object with keys for plugin names and their configuration | ||
* @param resolveDirs {array|string} Resolve Directories for plugins | ||
* @param {Record<string, any>} configs object with keys for plugin names and their configuration | ||
* @param {string | string[]} resolveDirs Resolve directories for plugins | ||
*/ | ||
addPlugins(configs: object, resolveDirs: any): void; | ||
addPlugins(configs: Record<string, any>, resolveDirs: string | string[]): void; | ||
/** | ||
* Resole, Require and Instanciate Plugins | ||
* | ||
* @param name {string} name of the plugin | ||
* @param config {object} plugin configuration | ||
* @param resolveDirs {string|Array} Resolve directories | ||
* @param {string} name name of the plugin | ||
* @param {Record<string, any>} config plugin configuration | ||
* @param {string | string[]} resolveDirs Resolve directories | ||
*/ | ||
instanciatePlugin(name: string, config: object, resolveDirs: string | any[]): void; | ||
instanciatePlugin(name: string, config: Record<string, any>, resolveDirs: string | string[]): void; | ||
/** | ||
* Set Objects and States databases for all isActive plugins | ||
* | ||
* @param name {object} name of the plugin | ||
* @param objectsDb {object} Objects DB instance | ||
* @param statesDb {object} States DB instance | ||
* @param {string} name name of the plugin | ||
* @param {any} objectsDb objects DB instance | ||
* @param {any} statesDb states DB instance | ||
*/ | ||
setDatabaseForPlugin(name: object, objectsDb: object, statesDb: object): void; | ||
setDatabaseForPlugin(name: string, objectsDb: any, statesDb: any): void; | ||
/** | ||
* Set Objects and States databases for all isActive plugins | ||
* | ||
* @param objectsDb {object} Objects DB instance | ||
* @param statesDb {object} States DB instance | ||
* @param {any} objectsDb objects DB instance | ||
* @param {any} statesDb states DB instance | ||
*/ | ||
setDatabaseForPlugins(objectsDb: object, statesDb: object): void; | ||
setDatabaseForPlugins(objectsDb: any, statesDb: any): void; | ||
/** | ||
* Initialize one Plugins | ||
* | ||
* @param name {string} name of the plugin | ||
* @param parentConfig {object} io-package of the parent module that uses the plugins (adapter/controller) | ||
* @param callback {function} callback function which is called after initialization is done for all plugins | ||
* @param {string} name name of the plugin | ||
* @param {Record<string, any>} parentConfig io-package of the parent module that uses the plugins (adapter/controller) | ||
* @param {(error?: string) => void} [callback] callback function which is called after initialization is done for all plugins | ||
*/ | ||
initPlugin(name: string, parentConfig: object, callback: Function): void; | ||
initPlugin(name: string, parentConfig: Record<string, any>, callback?: (error?: string) => void): void; | ||
/** | ||
* Initialize all Plugins that are registered | ||
* | ||
* @param parentConfig {object} io-package of the parent module that uses the plugins (adapter/controller) | ||
* @param callback {function} callback function which is called after initialization is done for all plugins | ||
* @param {Record<string, any>} parentConfig io-package of the parent module that uses the plugins (adapter/controller) | ||
* @param {(error?: string) => void} callback callback function which is called after initialization is done for all plugins | ||
*/ | ||
initPlugins(parentConfig: object, callback: Function): void; | ||
initPlugins(parentConfig: Record<string, any>, callback: (error?: string) => void): void; | ||
/** | ||
* Destroy one plugin instance | ||
* | ||
* @param name {string} name of the plugin to destroy | ||
* @param force {boolean} optional true to consider plugin as destroyed also if false is returned from plugin | ||
* @param {string} name name of the plugin to destroy | ||
* @param {boolean} [force] true to consider plugin as destroyed also if false is returned from plugin | ||
*/ | ||
destroy(name: string, force: boolean): boolean; | ||
destroy(name: string, force?: boolean): boolean; | ||
/** | ||
@@ -83,17 +80,17 @@ * Destroy all plugin instances | ||
* | ||
* @param name {string} name of the plugin to return | ||
* @returns {object} plugin instance or null if not existent or not isActive | ||
* @param {string} name name of the plugin to return | ||
* @returns {import("./PluginBase") | null} plugin instance or null if not existent or not isActive | ||
*/ | ||
getPluginInstance(name: string): object; | ||
getPluginInstance(name: string): import("./PluginBase"); | ||
/** | ||
* Return plugin configuration | ||
* | ||
* @param name {string} name of the plugin to return | ||
* @returns {object} plugin configuration or null if not existent or not isActive | ||
* @param {string} name name of the plugin to return | ||
* @returns {Record<string, any> | null} plugin configuration or null if not existent or not isActive | ||
*/ | ||
getPluginConfig(name: string): object; | ||
getPluginConfig(name: string): Record<string, any>; | ||
/** | ||
* Return if plugin exists | ||
* | ||
* @param name {string} name of the plugin to check | ||
* @param {string} name name of the plugin to check | ||
* @returns {boolean} true/false if plugin was configured somewhere | ||
@@ -105,3 +102,3 @@ */ | ||
* | ||
* @param name {string} name of the plugin to check | ||
* @param {string} name name of the plugin to check | ||
* @returns {boolean} true/false if plugin is successfully isActive | ||
@@ -113,3 +110,3 @@ */ | ||
* | ||
* @param name {string} name of the plugin to check | ||
* @param {string} name name of the plugin to check | ||
* @returns {boolean} true/false if plugin is successfully isActive | ||
@@ -116,0 +113,0 @@ */ |
@@ -11,3 +11,3 @@ /// <reference path="./types.d.ts" /> | ||
* | ||
* @param {import("@iobroker/plugin-base/types").PluginSettings} settings | ||
* @param {import("@iobroker/plugin-base/types").PluginHandlerSettings} settings | ||
*/ | ||
@@ -18,2 +18,3 @@ constructor(settings) { | ||
/** @type {Record<string, {config: Record<string, any>, instance?: import("./PluginBase") | null}>} */ | ||
this.plugins = {}; | ||
@@ -60,2 +61,3 @@ } | ||
/** @type {typeof import("./PluginBase")} */ | ||
let ResolvedPlugin; | ||
@@ -69,4 +71,6 @@ try { | ||
/** @type {import("@iobroker/plugin-base/types").PluginSettings} */ | ||
const pluginSettings = { | ||
pluginScope: this.settings.scope, | ||
parentNamespace: this.settings.namespace, | ||
pluginNamespace: this.settings.namespace + '.plugins.' + name, | ||
@@ -76,3 +80,4 @@ pluginLogNamespace: this.settings.logNamespace + ' Plugin ' + name, | ||
iobrokerConfig: this.settings.iobrokerConfig, | ||
parentPackage: this.settings.parentPackage // package.json from "parent" which uses the plugin (adapter/controller) | ||
parentPackage: this.settings.parentPackage, // package.json from "parent" which uses the plugin (adapter/controller) | ||
controllerVersion: this.settings.controllerVersion | ||
}; | ||
@@ -86,3 +91,3 @@ this.plugins[name] = { | ||
} catch (err) { | ||
this.log.info('Plugin ' + name + ' could not be ininitialized: ' + err); | ||
this.log.info('Plugin ' + name + ' could not be initialized: ' + err); | ||
this.plugins[name].instance = null; | ||
@@ -96,7 +101,8 @@ } | ||
* @param {string} name name of the plugin | ||
* @param {obj} objectsDb objects DB instance | ||
* @param {obj} statesDb states DB instance | ||
* @param {any} objectsDb objects DB instance | ||
* @param {any} statesDb states DB instance | ||
*/ | ||
setDatabaseForPlugin(name, objectsDb, statesDb) { | ||
this.plugins[name] && this.plugins[name].instance && this.plugins[name].instance.setDatabase(objectsDb, statesDb); | ||
const plugin = this.plugins[name]; | ||
plugin && plugin.instance && plugin.instance.setDatabase(objectsDb, statesDb); | ||
} | ||
@@ -107,4 +113,4 @@ | ||
* | ||
* @param {obj} objectsDb objects DB instance | ||
* @param {obj} statesDb states DB instance | ||
* @param {any} objectsDb objects DB instance | ||
* @param {any} statesDb states DB instance | ||
*/ | ||
@@ -120,14 +126,15 @@ setDatabaseForPlugins(objectsDb, statesDb) { | ||
* @param {Record<string, any>} parentConfig io-package of the parent module that uses the plugins (adapter/controller) | ||
* @param {(error?: string) => void} callback callback function which is called after initialization is done for all plugins | ||
* @param {(error?: string) => void} [callback] callback function which is called after initialization is done for all plugins | ||
*/ | ||
initPlugin(name, parentConfig, callback) { | ||
if (!this.plugins[name].instance) { | ||
typeof callback === 'function' && callback('Please instanciate plugin first!'); | ||
const instance = this.plugins[name].instance; | ||
if (!instance) { | ||
typeof callback === 'function' && callback(new Error('Please instanciate plugin first!')); | ||
return; | ||
} | ||
this.plugins[name].instance.initPlugin(this.plugins[name].config, parentConfig, (err, initSuccessful) => { | ||
instance.initPlugin(this.plugins[name].config, parentConfig, (err, initSuccessful) => { | ||
if (err || !initSuccessful) { | ||
this.log.debug('Plugin ' + name + ' destroyed because not initialized correctly'); | ||
this.plugins[name].instance.destroy(); | ||
instance.destroy(); | ||
delete this.plugins[name].instance; | ||
@@ -162,6 +169,7 @@ } | ||
destroy(name, force) { | ||
if (this.plugins[name].instance) { | ||
if (this.plugins[name].instance.destroy() || force) { | ||
const instance = this.plugins[name].instance; | ||
if (instance) { | ||
if (instance.destroy() || force) { | ||
this.log.debug('Plugin ' + name + ' destroyed'); | ||
!force && this.plugins[name].instance.setActive(false); | ||
!force && instance.setActive(false); | ||
delete this.plugins[name].instance; | ||
@@ -190,9 +198,10 @@ return true; | ||
* @param {string} name name of the plugin to return | ||
* @returns {object} plugin instance or null if not existent or not isActive | ||
* @returns {import("./PluginBase") | null} plugin instance or null if not existent or not isActive | ||
*/ | ||
getPluginInstance(name) { | ||
if (!this.plugins[name] || !this.plugins[name].instance) { | ||
const plugin = this.plugins[name]; | ||
if (!plugin || !plugin.instance) { | ||
return null; | ||
} | ||
return this.plugins[name].instance; | ||
return plugin.instance; | ||
} | ||
@@ -204,9 +213,10 @@ | ||
* @param {string} name name of the plugin to return | ||
* @returns {object} plugin configuration or null if not existent or not isActive | ||
* @returns {Record<string, any> | null} plugin configuration or null if not existent or not isActive | ||
*/ | ||
getPluginConfig(name) { | ||
if (!this.plugins[name] || !this.plugins[name].config) { | ||
const plugin = this.plugins[name]; | ||
if (!plugin || !plugin.config) { | ||
return null; | ||
} | ||
return this.plugins[name].config; | ||
return plugin.config; | ||
} | ||
@@ -241,2 +251,3 @@ | ||
isPluginActive(name) { | ||
// @ts-ignore Not sure why TS doesn't like this pattern | ||
return !!(this.plugins[name] && this.plugins[name].instance && this.plugins[name].instance.isActive); | ||
@@ -243,0 +254,0 @@ } |
declare module "@iobroker/plugin-base/types" { | ||
export interface PluginHandlerSettings { | ||
/** The scope in which the plugin will be executed */ | ||
scope: "adapter" | "controller"; | ||
/** The object namespace for the plugin, e.g. `system.adapter.<adaptername>.0.plugins.name`, or `system.host.<hostname>.plugins.name` */ | ||
namespace: string; | ||
/** The namespace which will be used for logging */ | ||
logNamespace: string; | ||
/** The logger object to use for logging */ | ||
log: ioBroker.Logger; | ||
/** The complete ioBroker configuration object */ | ||
iobrokerConfig: Record<string, any>; | ||
/** The package.json contents from the "parent" (adapter/controller) which uses this plugin */ | ||
parentPackage: Record<string, any>; | ||
/** The version of the installed JS-Controller */ | ||
controllerVersion: string; | ||
} | ||
export interface PluginSettings { | ||
/** The scope in which the plugin will be executed */ | ||
pluginScope: "adapter" | "controller"; | ||
/** The object namespace for the parent of the plugin, e.g. `system.adapter.<adaptername>.0`, or `system.host.<hostname>.` */ | ||
parentNamespace: string; | ||
/** The object namespace for the plugin, e.g. `system.adapter.<adaptername>.0.plugins.name`, or `system.host.<hostname>.plugins.name` */ | ||
@@ -15,7 +35,10 @@ pluginNamespace: string; | ||
parentPackage: Record<string, any>; | ||
/** The version of the installed JS-Controller */ | ||
controllerVersion: string; | ||
} | ||
export type InitCallback = ( | ||
err: string | undefined, | ||
err: Error | null | undefined, | ||
initSuccessful?: boolean | ||
) => void; | ||
} |
{ | ||
"name": "@iobroker/plugin-base", | ||
"version": "1.1.1", | ||
"version": "1.2.0", | ||
"description": "Base module for plugins for js-controller and adapters", | ||
@@ -9,7 +9,11 @@ "author": { | ||
}, | ||
"contributors": [ | ||
"Al Calzone <d.griesel@gmx.net>" | ||
], | ||
"main": "index.js", | ||
"types": "index.d.ts", | ||
"scripts": { | ||
"prebuild": "rimraf lib/!(types).d.ts", | ||
"build": "tsc" | ||
"prebuild": "rimraf \"lib/!(types).d.ts\"", | ||
"build": "tsc -p tsconfig.build.json", | ||
"prepublishOnly": "npm run build" | ||
}, | ||
@@ -33,4 +37,4 @@ "repository": { | ||
"@types/iobroker": "^3.0.6", | ||
"@types/node": "^13.13.4", | ||
"eslint": "^6.8.0", | ||
"@types/node": "^13.13.5", | ||
"eslint": "^7.0.0", | ||
"eslint-config-prettier": "^6.11.0", | ||
@@ -37,0 +41,0 @@ "eslint-plugin-prettier": "^3.1.3", |
@@ -91,2 +91,6 @@ # plugins-base | ||
### 1.2.0 (2020-05-09) | ||
* (Apollon77) Add async methods for Objects and States | ||
* (Apollon77) rework enable detection for plugins | ||
### 1.1.1 (2020-05-01) | ||
@@ -93,0 +97,0 @@ * (Apollon77) fix for host lookup to work for all plugins |
{ | ||
// Used to type-check in the editor | ||
"compilerOptions": { | ||
@@ -9,6 +10,7 @@ /* Basic Options */ | ||
"allowJs": true, /* Allow javascript files to be compiled. */ | ||
// "checkJs": true, /* Report errors in .js files. */ | ||
"checkJs": true, /* Report errors in .js files. */ | ||
// "jsx": "preserve", /* Specify JSX code generation: 'preserve', 'react-native', or 'react'. */ | ||
"declaration": true, /* Generates corresponding '.d.ts' file. */ | ||
"emitDeclarationOnly": true, | ||
"stripInternal": true, | ||
// "declarationMap": true, /* Generates a sourcemap for each corresponding '.d.ts' file. */ | ||
@@ -15,0 +17,0 @@ // "sourceMap": true, /* Generates corresponding '.map' file. */ |
47601
17.32%14
7.69%977
25.26%108
3.85%