iobroker.js-controller 7.2.3 → 8.0.0-alpha.1-20260921-e5941ca8a

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (69) hide show
  1. package/build/cjs/compactgroupController.js +1 -1
  2. package/build/cjs/compactgroupController.js.map +2 -2
  3. package/build/cjs/lib/adapterAutoUpgradeManager.d.ts +6 -0
  4. package/build/cjs/lib/adapterAutoUpgradeManager.js +8 -1
  5. package/build/cjs/lib/adapterAutoUpgradeManager.js.map +2 -2
  6. package/build/cjs/lib/adapterUpgradeManager.d.ts +15 -9
  7. package/build/cjs/lib/adapterUpgradeManager.js +19 -12
  8. package/build/cjs/lib/adapterUpgradeManager.js.map +2 -2
  9. package/build/cjs/lib/blocklistManager.d.ts +6 -0
  10. package/build/cjs/lib/blocklistManager.js +7 -0
  11. package/build/cjs/lib/blocklistManager.js.map +2 -2
  12. package/build/cjs/lib/multihostServer.d.ts +15 -0
  13. package/build/cjs/lib/multihostServer.js +20 -1
  14. package/build/cjs/lib/multihostServer.js.map +2 -2
  15. package/build/cjs/lib/objects.d.ts +1 -0
  16. package/build/cjs/lib/objects.js +2 -0
  17. package/build/cjs/lib/objects.js.map +2 -2
  18. package/build/cjs/lib/preinstallCheck.js +8 -1
  19. package/build/cjs/lib/preinstallCheck.js.map +2 -2
  20. package/build/cjs/lib/restart.js +3 -1
  21. package/build/cjs/lib/restart.js.map +2 -2
  22. package/build/cjs/lib/upgradeManager.d.ts +1 -1
  23. package/build/cjs/lib/upgradeManager.js +28 -17
  24. package/build/cjs/lib/upgradeManager.js.map +3 -3
  25. package/build/cjs/lib/utils.js +3 -0
  26. package/build/cjs/lib/utils.js.map +1 -1
  27. package/build/cjs/lib/vis/states.js +3 -0
  28. package/build/cjs/lib/vis/states.js.map +1 -1
  29. package/build/cjs/lib/vis/visUtils.js +8 -0
  30. package/build/cjs/lib/vis/visUtils.js.map +2 -2
  31. package/build/cjs/main.js +256 -173
  32. package/build/cjs/main.js.map +3 -3
  33. package/build/esm/compactgroupController.js +1 -1
  34. package/build/esm/compactgroupController.js.map +1 -1
  35. package/build/esm/lib/adapterAutoUpgradeManager.d.ts +6 -0
  36. package/build/esm/lib/adapterAutoUpgradeManager.d.ts.map +1 -1
  37. package/build/esm/lib/adapterAutoUpgradeManager.js +6 -0
  38. package/build/esm/lib/adapterAutoUpgradeManager.js.map +1 -1
  39. package/build/esm/lib/adapterUpgradeManager.d.ts +15 -9
  40. package/build/esm/lib/adapterUpgradeManager.d.ts.map +1 -1
  41. package/build/esm/lib/adapterUpgradeManager.js +16 -10
  42. package/build/esm/lib/adapterUpgradeManager.js.map +1 -1
  43. package/build/esm/lib/blocklistManager.d.ts +6 -0
  44. package/build/esm/lib/blocklistManager.d.ts.map +1 -1
  45. package/build/esm/lib/blocklistManager.js +6 -0
  46. package/build/esm/lib/blocklistManager.js.map +1 -1
  47. package/build/esm/lib/multihostServer.d.ts +15 -0
  48. package/build/esm/lib/multihostServer.d.ts.map +1 -1
  49. package/build/esm/lib/multihostServer.js +16 -1
  50. package/build/esm/lib/multihostServer.js.map +1 -1
  51. package/build/esm/lib/objects.d.ts +1 -0
  52. package/build/esm/lib/objects.d.ts.map +1 -1
  53. package/build/esm/lib/objects.js.map +1 -1
  54. package/build/esm/lib/preinstallCheck.js +10 -9
  55. package/build/esm/lib/preinstallCheck.js.map +1 -1
  56. package/build/esm/lib/restart.js +1 -1
  57. package/build/esm/lib/restart.js.map +1 -1
  58. package/build/esm/lib/upgradeManager.d.ts +1 -1
  59. package/build/esm/lib/upgradeManager.d.ts.map +1 -1
  60. package/build/esm/lib/upgradeManager.js +24 -18
  61. package/build/esm/lib/upgradeManager.js.map +1 -1
  62. package/build/esm/lib/vis/visUtils.d.ts.map +1 -1
  63. package/build/esm/lib/vis/visUtils.js.map +1 -1
  64. package/build/esm/main.d.ts.map +1 -1
  65. package/build/esm/main.js +252 -168
  66. package/build/esm/main.js.map +1 -1
  67. package/build/tsconfig.build.tsbuildinfo +1 -1
  68. package/io-package.json +16 -2
  69. package/package.json +22 -22
@@ -5,5 +5,5 @@ if (isNaN(compactGroup) || compactGroup < 1) {
5
5
  console.log(`Invalid compact group (${compactGroup}) as first parameter. Exit.`);
6
6
  process.exit();
7
7
  }
8
- (0, import_main.init)(compactGroup);
8
+ (0, import_main.init)(compactGroup).catch((e) => console.error(`Cannot start compact group controller: ${e.message}`));
9
9
  //# sourceMappingURL=compactgroupController.js.map
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/compactgroupController.ts"],
4
- "sourcesContent": ["/**\n * Controller process for Compact Groups\n *\n * Copyright 2018-2024 bluefox <dogafox@gmail.com>,\n * MIT License\n *\n */\nimport { init } from '@/main.js';\n\nconst compactGroup = parseInt(process.argv[2], 10);\nif (isNaN(compactGroup) || compactGroup < 1) {\n console.log(`Invalid compact group (${compactGroup}) as first parameter. Exit.`);\n process.exit();\n}\n\ninit(compactGroup);\n"],
5
- "mappings": ";AAOA,kBAAqB;AAErB,MAAM,eAAe,SAAS,QAAQ,KAAK,CAAC,GAAG,EAAE;AACjD,IAAI,MAAM,YAAY,KAAK,eAAe,GAAG;AACzC,UAAQ,IAAI,0BAA0B,YAAY,6BAA6B;AAC/E,UAAQ,KAAI;AAChB;IAEA,kBAAK,YAAY;",
4
+ "sourcesContent": ["/**\n * Controller process for Compact Groups\n *\n * Copyright 2018-2024 bluefox <dogafox@gmail.com>,\n * MIT License\n *\n */\nimport { init } from '@/main.js';\n\nconst compactGroup = parseInt(process.argv[2], 10);\nif (isNaN(compactGroup) || compactGroup < 1) {\n console.log(`Invalid compact group (${compactGroup}) as first parameter. Exit.`);\n process.exit();\n}\n\ninit(compactGroup).catch(e => console.error(`Cannot start compact group controller: ${e.message}`));\n"],
5
+ "mappings": ";AAOA,kBAAqB;AAErB,MAAM,eAAe,SAAS,QAAQ,KAAK,CAAC,GAAG,EAAE;AACjD,IAAI,MAAM,YAAY,KAAK,eAAe,GAAG;AACzC,UAAQ,IAAI,0BAA0B,YAAY,6BAA6B;AAC/E,UAAQ,KAAI;AAChB;IAEA,kBAAK,YAAY,EAAE,MAAM,OAAK,QAAQ,MAAM,0CAA0C,EAAE,OAAO,EAAE,CAAC;",
6
6
  "names": []
7
7
  }
@@ -25,6 +25,9 @@ interface UpgradeAdaptersResult {
25
25
  /** Adapters which were failed to upgrade */
26
26
  failedAdapters: UpgradedAdapter[];
27
27
  }
28
+ /**
29
+ * Manages automatic upgrades of adapters based on the configured upgrade policy
30
+ */
28
31
  export declare class AdapterAutoUpgradeManager {
29
32
  private readonly objects;
30
33
  private readonly states;
@@ -34,6 +37,9 @@ export declare class AdapterAutoUpgradeManager {
34
37
  private readonly logPrefix;
35
38
  /** Logger which needs to be prefixed */
36
39
  private logger;
40
+ /**
41
+ * @param options The objects/states clients, logger and log prefix
42
+ */
37
43
  constructor(options: AdapterAutoUpgradeOptions);
38
44
  /**
39
45
  * Checks if auto upgrade is enabled for the current configured repository
@@ -5,6 +5,7 @@ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
5
  var __getOwnPropNames = Object.getOwnPropertyNames;
6
6
  var __getProtoOf = Object.getPrototypeOf;
7
7
  var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
8
9
  var __export = (target, all) => {
9
10
  for (var name in all)
10
11
  __defProp(target, name, { get: all[name], enumerable: true });
@@ -34,6 +35,9 @@ module.exports = __toCommonJS(adapterAutoUpgradeManager_exports);
34
35
  var import_js_controller_cli = require("@iobroker/js-controller-cli");
35
36
  var import_semver = __toESM(require("semver"), 1);
36
37
  class AdapterAutoUpgradeManager {
38
+ static {
39
+ __name(this, "AdapterAutoUpgradeManager");
40
+ }
37
41
  objects;
38
42
  states;
39
43
  /** Mapping from semver range to range identifier */
@@ -47,6 +51,9 @@ class AdapterAutoUpgradeManager {
47
51
  logPrefix;
48
52
  /** Logger which needs to be prefixed */
49
53
  logger;
54
+ /**
55
+ * @param options The objects/states clients, logger and log prefix
56
+ */
50
57
  constructor(options) {
51
58
  this.objects = options.objects;
52
59
  this.states = options.states;
@@ -119,7 +126,7 @@ class AdapterAutoUpgradeManager {
119
126
  objects: this.objects,
120
127
  states: this.states,
121
128
  params: {},
122
- processExit: () => void 0
129
+ processExit: /* @__PURE__ */ __name(() => void 0, "processExit")
123
130
  });
124
131
  await upgrade.upgradeAdapter(repoName, `${name}@${version}`, false, true, false);
125
132
  }
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../src/lib/adapterAutoUpgradeManager.ts"],
4
- "sourcesContent": ["import type { Client as ObjectsClient } from '@iobroker/db-objects-redis';\nimport type { Client as StatesClient } from '@iobroker/db-states-redis';\nimport type { logger } from '@iobroker/js-controller-common';\nimport { Upgrade } from '@iobroker/js-controller-cli';\nimport semver from 'semver';\n\ninterface AdapterAutoUpgradeOptions {\n /** The objects DB client */\n objects: ObjectsClient;\n /** The states DB client */\n states: StatesClient;\n /** Logger which needs to be prefixed */\n logger: ReturnType<typeof logger>;\n /** Prefix for log messages */\n logPrefix: string;\n}\n\ninterface UpgradeAdapterOptions extends ioBroker.RepositoryJsonAdapterContent {\n /** Current active repository */\n repoName: string;\n}\n\ninterface UpgradedAdapter {\n /** Name of the adapter */\n name: string;\n /** Version before upgrade */\n oldVersion: string;\n /** Newly installed version */\n newVersion: string;\n}\n\ninterface UpgradeAdaptersResult {\n /** Adapters which were successfully upgraded */\n upgradedAdapters: UpgradedAdapter[];\n /** Adapters which were failed to upgrade */\n failedAdapters: UpgradedAdapter[];\n}\n\ninterface AdapterUpgradeConfiguration {\n /** Name of the adapter */\n name: string;\n /** Current installed version */\n version: string;\n /** Configured upgrade policy */\n upgradePolicy: ioBroker.AutoUpgradePolicy;\n}\n\nexport class AdapterAutoUpgradeManager {\n private readonly objects: ObjectsClient;\n private readonly states: StatesClient;\n /** Mapping from semver range to range identifier */\n private SEMVER_RANGE_MAPPING = {\n none: '',\n patch: '~',\n minor: '^',\n major: '>',\n } as const;\n /** Prefix for log messages */\n private readonly logPrefix: string;\n /** Logger which needs to be prefixed */\n private logger: ReturnType<typeof logger>;\n\n constructor(options: AdapterAutoUpgradeOptions) {\n this.objects = options.objects;\n this.states = options.states;\n this.logger = options.logger;\n this.logPrefix = options.logPrefix;\n }\n\n /**\n * Checks if auto upgrade is enabled for the current configured repository\n */\n async isAutoUpgradeEnabled(): Promise<boolean> {\n let sysConf: ioBroker.SystemConfigObject | null | undefined;\n\n try {\n sysConf = await this.objects.getObjectAsync('system.config');\n } catch {\n // ignore\n }\n\n if (!sysConf?.common.activeRepo?.length || !sysConf.common.adapterAutoUpgrade) {\n return false;\n }\n\n const activeRepo = sysConf.common.activeRepo[0];\n\n return sysConf.common.adapterAutoUpgrade.repositories[activeRepo];\n }\n\n /**\n * Checks the current `system.repositories` object and checks if one needs to be performed according to the adapter configuration\n */\n async upgradeAdapters(): Promise<UpgradeAdaptersResult> {\n this.logger.info(`${this.logPrefix} Check for available automatic adapter upgrades`);\n const upgradedAdapters: UpgradedAdapter[] = [];\n const failedAdapters: UpgradedAdapter[] = [];\n const repoName = await this.getConfiguredRepositoryName();\n const repoInformation = await this.getRepository(repoName);\n\n const installedAdaptersConfig = await this.getAutoUpdateConfiguration();\n\n for (const adapterConfig of installedAdaptersConfig) {\n const repoAdapterInfo = repoInformation[adapterConfig.name];\n if (!repoAdapterInfo) {\n continue;\n }\n\n if (semver.gte(adapterConfig.version, repoAdapterInfo.version)) {\n continue;\n }\n\n if (\n semver.satisfies(\n repoAdapterInfo.version,\n `${this.SEMVER_RANGE_MAPPING[adapterConfig.upgradePolicy]}${adapterConfig.version}`,\n { includePrerelease: true },\n )\n ) {\n try {\n await this.upgradeAdapter({ ...repoAdapterInfo, repoName });\n upgradedAdapters.push({\n name: repoAdapterInfo.name,\n newVersion: repoAdapterInfo.version,\n oldVersion: adapterConfig.version,\n });\n this.logger.info(\n `${this.logPrefix} Successfully upgraded adapter \"${repoAdapterInfo.name}\" to ${repoAdapterInfo.version}`,\n );\n } catch (e) {\n this.logger.error(\n `${this.logPrefix} Could not upgrade adapter \"${repoAdapterInfo.name}\" to ${repoAdapterInfo.version}: ${e.message}`,\n );\n failedAdapters.push({\n name: repoAdapterInfo.name,\n newVersion: repoAdapterInfo.version,\n oldVersion: adapterConfig.version,\n });\n }\n }\n }\n\n return { upgradedAdapters, failedAdapters };\n }\n\n /**\n * Upgrade specified adapter to given version\n *\n * @param options information of the adapter to install, e.g. version and name, sa well as active repo\n */\n private async upgradeAdapter(options: UpgradeAdapterOptions): Promise<void> {\n const { repoName, name, version } = options;\n\n this.logger.info(`${this.logPrefix} Upgrade adapter \"${name}\" to ${version}`);\n\n const upgrade = new Upgrade({\n objects: this.objects,\n states: this.states,\n params: {},\n processExit: () => undefined,\n });\n\n await upgrade.upgradeAdapter(repoName, `${name}@${version}`, false, true, false);\n }\n\n /**\n * Get the current active repository name\n */\n private async getConfiguredRepositoryName(): Promise<string> {\n const obj = await this.objects.getObjectAsync('system.config');\n\n if (!obj?.common?.activeRepo?.length) {\n throw new Error('Could not find an active repository');\n }\n\n return obj.common.activeRepo[0];\n }\n\n /**\n * Get the repository information for the given repository\n *\n * @param name Name of the repository\n */\n private async getRepository(name: string): Promise<Record<string, ioBroker.RepositoryJsonAdapterContent>> {\n const obj = await this.objects.getObjectAsync('system.repositories');\n\n const jsonContent:\n | (ioBroker.RepositoryJson & {\n _repoInfo?: any;\n })\n | null\n | undefined = obj?.native?.repositories?.[name]?.json;\n\n if (!jsonContent) {\n throw new Error(`Could not get repository information for \"${name}\"`);\n }\n\n delete jsonContent._repoInfo;\n return jsonContent as Record<string, ioBroker.RepositoryJsonAdapterContent>;\n }\n\n /**\n * Get the auto upgrade configuration of all adapters\n */\n private async getAutoUpdateConfiguration(): Promise<AdapterUpgradeConfiguration[]> {\n const res = await this.objects.getObjectViewAsync('system', 'adapter', {\n startkey: 'system.adapter.',\n endkey: 'system.adapter.\\u9999',\n });\n\n if (!res) {\n throw new Error('Did not get information about installed adapters');\n }\n\n const defaultPolicy = await this.getDefaultUpgradePolicy();\n\n return res.rows\n .filter(\n row =>\n (defaultPolicy && defaultPolicy !== 'none') ||\n (row.value?.common.automaticUpgrade && row.value.common.automaticUpgrade !== 'none'),\n )\n .map(row => {\n return {\n // ts can not infer, that we filtered out falsy row.value entries\n name: row.value.common.name,\n version: row.value.common.version,\n upgradePolicy: row.value.common.automaticUpgrade! || defaultPolicy,\n };\n });\n }\n\n /**\n * Get the default upgrade policy from the system config\n */\n private async getDefaultUpgradePolicy(): Promise<ioBroker.AutoUpgradePolicy | undefined> {\n let sysConf: ioBroker.SystemConfigObject | null | undefined;\n\n try {\n sysConf = await this.objects.getObjectAsync('system.config');\n } catch {\n // ignore\n }\n\n return sysConf?.common.adapterAutoUpgrade?.defaultPolicy;\n }\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["import type { Client as ObjectsClient } from '@iobroker/db-objects-redis';\nimport type { Client as StatesClient } from '@iobroker/db-states-redis';\nimport type { logger } from '@iobroker/js-controller-common';\nimport { Upgrade } from '@iobroker/js-controller-cli';\nimport semver from 'semver';\n\ninterface AdapterAutoUpgradeOptions {\n /** The objects DB client */\n objects: ObjectsClient;\n /** The states DB client */\n states: StatesClient;\n /** Logger which needs to be prefixed */\n logger: ReturnType<typeof logger>;\n /** Prefix for log messages */\n logPrefix: string;\n}\n\ninterface UpgradeAdapterOptions extends ioBroker.RepositoryJsonAdapterContent {\n /** Current active repository */\n repoName: string;\n}\n\ninterface UpgradedAdapter {\n /** Name of the adapter */\n name: string;\n /** Version before upgrade */\n oldVersion: string;\n /** Newly installed version */\n newVersion: string;\n}\n\ninterface UpgradeAdaptersResult {\n /** Adapters which were successfully upgraded */\n upgradedAdapters: UpgradedAdapter[];\n /** Adapters which were failed to upgrade */\n failedAdapters: UpgradedAdapter[];\n}\n\ninterface AdapterUpgradeConfiguration {\n /** Name of the adapter */\n name: string;\n /** Current installed version */\n version: string;\n /** Configured upgrade policy */\n upgradePolicy: ioBroker.AutoUpgradePolicy;\n}\n\n/**\n * Manages automatic upgrades of adapters based on the configured upgrade policy\n */\nexport class AdapterAutoUpgradeManager {\n private readonly objects: ObjectsClient;\n private readonly states: StatesClient;\n /** Mapping from semver range to range identifier */\n private SEMVER_RANGE_MAPPING = {\n none: '',\n patch: '~',\n minor: '^',\n major: '>',\n } as const;\n /** Prefix for log messages */\n private readonly logPrefix: string;\n /** Logger which needs to be prefixed */\n private logger: ReturnType<typeof logger>;\n\n /**\n * @param options The objects/states clients, logger and log prefix\n */\n constructor(options: AdapterAutoUpgradeOptions) {\n this.objects = options.objects;\n this.states = options.states;\n this.logger = options.logger;\n this.logPrefix = options.logPrefix;\n }\n\n /**\n * Checks if auto upgrade is enabled for the current configured repository\n */\n async isAutoUpgradeEnabled(): Promise<boolean> {\n let sysConf: ioBroker.SystemConfigObject | null | undefined;\n\n try {\n sysConf = await this.objects.getObjectAsync('system.config');\n } catch {\n // ignore\n }\n\n if (!sysConf?.common.activeRepo?.length || !sysConf.common.adapterAutoUpgrade) {\n return false;\n }\n\n const activeRepo = sysConf.common.activeRepo[0];\n\n return sysConf.common.adapterAutoUpgrade.repositories[activeRepo];\n }\n\n /**\n * Checks the current `system.repositories` object and checks if one needs to be performed according to the adapter configuration\n */\n async upgradeAdapters(): Promise<UpgradeAdaptersResult> {\n this.logger.info(`${this.logPrefix} Check for available automatic adapter upgrades`);\n const upgradedAdapters: UpgradedAdapter[] = [];\n const failedAdapters: UpgradedAdapter[] = [];\n const repoName = await this.getConfiguredRepositoryName();\n const repoInformation = await this.getRepository(repoName);\n\n const installedAdaptersConfig = await this.getAutoUpdateConfiguration();\n\n for (const adapterConfig of installedAdaptersConfig) {\n const repoAdapterInfo = repoInformation[adapterConfig.name];\n if (!repoAdapterInfo) {\n continue;\n }\n\n if (semver.gte(adapterConfig.version, repoAdapterInfo.version)) {\n continue;\n }\n\n if (\n semver.satisfies(\n repoAdapterInfo.version,\n `${this.SEMVER_RANGE_MAPPING[adapterConfig.upgradePolicy]}${adapterConfig.version}`,\n { includePrerelease: true },\n )\n ) {\n try {\n await this.upgradeAdapter({ ...repoAdapterInfo, repoName });\n upgradedAdapters.push({\n name: repoAdapterInfo.name,\n newVersion: repoAdapterInfo.version,\n oldVersion: adapterConfig.version,\n });\n this.logger.info(\n `${this.logPrefix} Successfully upgraded adapter \"${repoAdapterInfo.name}\" to ${repoAdapterInfo.version}`,\n );\n } catch (e) {\n this.logger.error(\n `${this.logPrefix} Could not upgrade adapter \"${repoAdapterInfo.name}\" to ${repoAdapterInfo.version}: ${e.message}`,\n );\n failedAdapters.push({\n name: repoAdapterInfo.name,\n newVersion: repoAdapterInfo.version,\n oldVersion: adapterConfig.version,\n });\n }\n }\n }\n\n return { upgradedAdapters, failedAdapters };\n }\n\n /**\n * Upgrade specified adapter to given version\n *\n * @param options information of the adapter to install, e.g. version and name, sa well as active repo\n */\n private async upgradeAdapter(options: UpgradeAdapterOptions): Promise<void> {\n const { repoName, name, version } = options;\n\n this.logger.info(`${this.logPrefix} Upgrade adapter \"${name}\" to ${version}`);\n\n const upgrade = new Upgrade({\n objects: this.objects,\n states: this.states,\n params: {},\n processExit: () => undefined,\n });\n\n await upgrade.upgradeAdapter(repoName, `${name}@${version}`, false, true, false);\n }\n\n /**\n * Get the current active repository name\n */\n private async getConfiguredRepositoryName(): Promise<string> {\n const obj = await this.objects.getObjectAsync('system.config');\n\n if (!obj?.common?.activeRepo?.length) {\n throw new Error('Could not find an active repository');\n }\n\n return obj.common.activeRepo[0];\n }\n\n /**\n * Get the repository information for the given repository\n *\n * @param name Name of the repository\n */\n private async getRepository(name: string): Promise<Record<string, ioBroker.RepositoryJsonAdapterContent>> {\n const obj = await this.objects.getObjectAsync('system.repositories');\n\n const jsonContent:\n | (Omit<ioBroker.RepositoryJson, '_repoInfo'> & {\n /** Additional internal repository metadata */\n _repoInfo?: ioBroker.RepoInfo;\n })\n | null\n | undefined = obj?.native?.repositories?.[name]?.json;\n\n if (!jsonContent) {\n throw new Error(`Could not get repository information for \"${name}\"`);\n }\n\n delete jsonContent._repoInfo;\n return jsonContent as Record<string, ioBroker.RepositoryJsonAdapterContent>;\n }\n\n /**\n * Get the auto upgrade configuration of all adapters\n */\n private async getAutoUpdateConfiguration(): Promise<AdapterUpgradeConfiguration[]> {\n const res = await this.objects.getObjectViewAsync('system', 'adapter', {\n startkey: 'system.adapter.',\n endkey: 'system.adapter.\\u9999',\n });\n\n if (!res) {\n throw new Error('Did not get information about installed adapters');\n }\n\n const defaultPolicy = await this.getDefaultUpgradePolicy();\n\n return res.rows\n .filter(\n row =>\n (defaultPolicy && defaultPolicy !== 'none') ||\n (row.value?.common.automaticUpgrade && row.value.common.automaticUpgrade !== 'none'),\n )\n .map(row => {\n return {\n // ts can not infer, that we filtered out falsy row.value entries\n name: row.value.common.name,\n version: row.value.common.version,\n upgradePolicy: row.value.common.automaticUpgrade! || defaultPolicy,\n };\n });\n }\n\n /**\n * Get the default upgrade policy from the system config\n */\n private async getDefaultUpgradePolicy(): Promise<ioBroker.AutoUpgradePolicy | undefined> {\n let sysConf: ioBroker.SystemConfigObject | null | undefined;\n\n try {\n sysConf = await this.objects.getObjectAsync('system.config');\n } catch {\n // ignore\n }\n\n return sysConf?.common.adapterAutoUpgrade?.defaultPolicy;\n }\n}\n"],
5
+ "mappings": "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",
6
6
  "names": ["semver"]
7
7
  }
@@ -1,8 +1,8 @@
1
1
  import http from 'node:http';
2
2
  import https from 'node:https';
3
+ import type { Logger } from 'winston';
3
4
  import type { Client as ObjectsClient } from '@iobroker/db-objects-redis';
4
5
  import type { Client as StatesClient } from '@iobroker/db-states-redis';
5
- import type { Logger } from 'winston';
6
6
  interface Certificates {
7
7
  /** Public certificate */
8
8
  certPublic: string;
@@ -39,6 +39,9 @@ interface GetCertificatesParams {
39
39
  /** Name of the private certificate */
40
40
  certPrivateName: string;
41
41
  }
42
+ /**
43
+ * Manages the upgrade of a single adapter, including stopping it and serving a web UI for the upgrade progress
44
+ */
42
45
  export declare class AdapterUpgradeManager {
43
46
  /** Wait ms until adapter is stopped */
44
47
  private readonly STOP_TIMEOUT_MS;
@@ -52,7 +55,7 @@ export declare class AdapterUpgradeManager {
52
55
  private readonly response;
53
56
  /** Used to stop the stop shutdown timeout */
54
57
  private shutdownAbortController?;
55
- /** Logger to log to file and other transports */
58
+ /** Logger to log to a file and other transports */
56
59
  private readonly logger;
57
60
  /** The server used for communicating upgrade status */
58
61
  private server?;
@@ -64,9 +67,9 @@ export declare class AdapterUpgradeManager {
64
67
  private readonly objects;
65
68
  /** The states DB client */
66
69
  private readonly states;
67
- /** List of instances which have been stopped */
70
+ /** List of instances that have been stopped */
68
71
  private stoppedInstances;
69
- /** If webserver should be started with https */
72
+ /** If a webserver should be started with https */
70
73
  private readonly useHttps;
71
74
  /** Public certificate name if https is desired */
72
75
  private readonly certPublicName?;
@@ -74,13 +77,16 @@ export declare class AdapterUpgradeManager {
74
77
  private readonly certPrivateName?;
75
78
  /** Port where the webserver should be running */
76
79
  private readonly port;
80
+ /**
81
+ * @param options Adapter name, target version, logger and webserver options
82
+ */
77
83
  constructor(options: AdapterUpgradeManagerOptions);
78
84
  /**
79
85
  * Stops the adapter and returns ids of stopped instances
80
86
  */
81
87
  stopAdapter(): Promise<void>;
82
88
  /**
83
- * Start all instances which were enabled before the upgrade
89
+ * Start all instances that were enabled before the upgrade
84
90
  */
85
91
  startAdapter(): Promise<void>;
86
92
  /**
@@ -91,7 +97,7 @@ export declare class AdapterUpgradeManager {
91
97
  */
92
98
  enableInstances(instances: string[], enabled: boolean): Promise<void>;
93
99
  /**
94
- * Install given version of adapter
100
+ * Install a given version of the adapter
95
101
  */
96
102
  performUpgrade(): Promise<void>;
97
103
  /**
@@ -103,7 +109,7 @@ export declare class AdapterUpgradeManager {
103
109
  */
104
110
  shutdownServer(): void;
105
111
  /**
106
- * Destroy all sockets, to prevent requests from keeping server alive
112
+ * Destroy all sockets to prevent requests from keeping the server alive
107
113
  */
108
114
  destroySockets(): void;
109
115
  /**
@@ -149,11 +155,11 @@ export declare class AdapterUpgradeManager {
149
155
  */
150
156
  getCertificates(params: GetCertificatesParams): Promise<Certificates>;
151
157
  /**
152
- * Tells the upgrade manager, that server can be shut down on next response or on timeout
158
+ * Tells the upgrade manager that the server can be shut down on the next response or on timeout
153
159
  */
154
160
  private setFinished;
155
161
  /**
156
- * Start a timeout which starts adapter and shuts down the server if expired
162
+ * Start a timeout which starts the adapter and shuts down the server if expired
157
163
  */
158
164
  startShutdownTimeout(): Promise<void>;
159
165
  }
@@ -5,6 +5,7 @@ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
5
  var __getOwnPropNames = Object.getOwnPropertyNames;
6
6
  var __getProtoOf = Object.getPrototypeOf;
7
7
  var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
8
9
  var __export = (target, all) => {
9
10
  for (var name in all)
10
11
  __defProp(target, name, { get: all[name], enumerable: true });
@@ -31,12 +32,15 @@ __export(adapterUpgradeManager_exports, {
31
32
  AdapterUpgradeManager: () => AdapterUpgradeManager
32
33
  });
33
34
  module.exports = __toCommonJS(adapterUpgradeManager_exports);
34
- var import_js_controller_common = require("@iobroker/js-controller-common");
35
35
  var import_node_http = __toESM(require("node:http"), 1);
36
36
  var import_node_https = __toESM(require("node:https"), 1);
37
37
  var import_promises = require("node:timers/promises");
38
+ var import_js_controller_common = require("@iobroker/js-controller-common");
38
39
  var import_js_controller_cli = require("@iobroker/js-controller-cli");
39
40
  class AdapterUpgradeManager {
41
+ static {
42
+ __name(this, "AdapterUpgradeManager");
43
+ }
40
44
  /** Wait ms until adapter is stopped */
41
45
  STOP_TIMEOUT_MS = 3e3;
42
46
  /** Wait ms for delivery of final response */
@@ -53,7 +57,7 @@ class AdapterUpgradeManager {
53
57
  };
54
58
  /** Used to stop the stop shutdown timeout */
55
59
  shutdownAbortController;
56
- /** Logger to log to file and other transports */
60
+ /** Logger to log to a file and other transports */
57
61
  logger;
58
62
  /** The server used for communicating upgrade status */
59
63
  server;
@@ -65,9 +69,9 @@ class AdapterUpgradeManager {
65
69
  objects;
66
70
  /** The states DB client */
67
71
  states;
68
- /** List of instances which have been stopped */
72
+ /** List of instances that have been stopped */
69
73
  stoppedInstances = [];
70
- /** If webserver should be started with https */
74
+ /** If a webserver should be started with https */
71
75
  useHttps;
72
76
  /** Public certificate name if https is desired */
73
77
  certPublicName;
@@ -75,6 +79,9 @@ class AdapterUpgradeManager {
75
79
  certPrivateName;
76
80
  /** Port where the webserver should be running */
77
81
  port;
82
+ /**
83
+ * @param options Adapter name, target version, logger and webserver options
84
+ */
78
85
  constructor(options) {
79
86
  this.adapterName = options.adapterName;
80
87
  this.version = options.version;
@@ -97,7 +104,7 @@ class AdapterUpgradeManager {
97
104
  await (0, import_promises.setTimeout)(this.STOP_TIMEOUT_MS);
98
105
  }
99
106
  /**
100
- * Start all instances which were enabled before the upgrade
107
+ * Start all instances that were enabled before the upgrade
101
108
  */
102
109
  async startAdapter() {
103
110
  await this.enableInstances(this.stoppedInstances, true);
@@ -118,16 +125,16 @@ class AdapterUpgradeManager {
118
125
  from: `system.host.${this.hostname}`,
119
126
  ts
120
127
  };
121
- await this.objects.extendObjectAsync(instance, updatedObj);
128
+ await this.objects.extendObject(instance, updatedObj);
122
129
  }
123
130
  }
124
131
  /**
125
- * Install given version of adapter
132
+ * Install a given version of the adapter
126
133
  */
127
134
  async performUpgrade() {
128
- const processExitHandler = (exitCode) => {
135
+ const processExitHandler = /* @__PURE__ */ __name((exitCode) => {
129
136
  this.log(`Upgrade process exited with code: ${exitCode}`, true);
130
- };
137
+ }, "processExitHandler");
131
138
  const upgrade = new import_js_controller_cli.Upgrade({
132
139
  objects: this.objects,
133
140
  processExit: processExitHandler,
@@ -176,7 +183,7 @@ class AdapterUpgradeManager {
176
183
  });
177
184
  }
178
185
  /**
179
- * Destroy all sockets, to prevent requests from keeping server alive
186
+ * Destroy all sockets to prevent requests from keeping the server alive
180
187
  */
181
188
  destroySockets() {
182
189
  for (const socket of this.sockets) {
@@ -284,14 +291,14 @@ class AdapterUpgradeManager {
284
291
  return { certPrivate: certs[certPrivateName], certPublic: certs[certPublicName] };
285
292
  }
286
293
  /**
287
- * Tells the upgrade manager, that server can be shut down on next response or on timeout
294
+ * Tells the upgrade manager that the server can be shut down on the next response or on timeout
288
295
  */
289
296
  async setFinished() {
290
297
  this.response.running = false;
291
298
  await this.startShutdownTimeout();
292
299
  }
293
300
  /**
294
- * Start a timeout which starts adapter and shuts down the server if expired
301
+ * Start a timeout which starts the adapter and shuts down the server if expired
295
302
  */
296
303
  async startShutdownTimeout() {
297
304
  this.shutdownAbortController = new AbortController();
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../src/lib/adapterUpgradeManager.ts"],
4
- "sourcesContent": ["import { tools } from '@iobroker/js-controller-common';\nimport http from 'node:http';\nimport https from 'node:https';\nimport type { Client as ObjectsClient } from '@iobroker/db-objects-redis';\nimport type { Client as StatesClient } from '@iobroker/db-states-redis';\nimport { setTimeout as wait } from 'node:timers/promises';\nimport type { Logger } from 'winston';\nimport { Upgrade, type ProcessExitCallback } from '@iobroker/js-controller-cli';\nimport type { Socket } from 'node:net';\nimport type { Duplex } from 'node:stream';\n\ninterface Certificates {\n /** Public certificate */\n certPublic: string;\n /** Private certificate */\n certPrivate: string;\n}\n\ninterface InsecureWebServerParameters {\n /** if https should be used for the webserver */\n useHttps: false;\n /** port of the web server */\n port: number;\n}\n\ntype SecureWebServerParameters = Omit<InsecureWebServerParameters, 'useHttps'> & {\n useHttps: true;\n certPrivateName: string;\n certPublicName: string;\n};\ntype WebServerParameters = InsecureWebServerParameters | SecureWebServerParameters;\n\nexport type AdapterUpgradeManagerOptions = {\n /** Version of adapter to upgrade too */\n version: string;\n /** Name of the adapter to upgrade */\n adapterName: string;\n /** The objects DB client */\n objects: ObjectsClient;\n /** The states DB client */\n states: StatesClient;\n /** A logger instance */\n logger: Logger;\n} & WebServerParameters;\n\ninterface GetCertificatesParams {\n /** Name of the public certificate */\n certPublicName: string;\n /** Name of the private certificate */\n certPrivateName: string;\n}\n\ninterface ServerResponse {\n /** If the update is still running */\n running: boolean;\n stderr: string[];\n stdout: string[];\n /** if installation process succeeded */\n success?: boolean;\n}\n\nexport class AdapterUpgradeManager {\n /** Wait ms until adapter is stopped */\n private readonly STOP_TIMEOUT_MS = 3_000;\n /** Wait ms for delivery of final response */\n private readonly SHUTDOWN_TIMEOUT = 10_000;\n /** Name of the adapter to upgrade */\n private readonly adapterName: string;\n /** Desired adapter version */\n private readonly version: string;\n /** Response send by webserver */\n private readonly response: ServerResponse = {\n running: true,\n stderr: [],\n stdout: [],\n };\n /** Used to stop the stop shutdown timeout */\n private shutdownAbortController?: AbortController;\n /** Logger to log to file and other transports */\n private readonly logger: Logger;\n\n /** The server used for communicating upgrade status */\n private server?: https.Server | http.Server;\n /** All socket connections of the webserver */\n private sockets = new Set<Socket | Duplex>();\n /** Name of the host for logging purposes */\n private readonly hostname = tools.getHostName();\n /** The objects DB client */\n private readonly objects: ObjectsClient;\n /** The states DB client */\n private readonly states: StatesClient;\n /** List of instances which have been stopped */\n private stoppedInstances: string[] = [];\n /** If webserver should be started with https */\n private readonly useHttps: boolean;\n /** Public certificate name if https is desired */\n private readonly certPublicName?: string;\n /** Private certificate name if https is desired */\n private readonly certPrivateName?: string;\n /** Port where the webserver should be running */\n private readonly port: number;\n\n constructor(options: AdapterUpgradeManagerOptions) {\n this.adapterName = options.adapterName;\n this.version = options.version;\n this.logger = options.logger;\n this.objects = options.objects;\n this.states = options.states;\n this.useHttps = options.useHttps;\n this.port = options.port;\n\n if (options.useHttps) {\n this.certPublicName = options.certPublicName;\n this.certPrivateName = options.certPrivateName;\n }\n }\n\n /**\n * Stops the adapter and returns ids of stopped instances\n */\n async stopAdapter(): Promise<void> {\n this.stoppedInstances = await this.getAllEnabledInstances();\n await this.enableInstances(this.stoppedInstances, false);\n await wait(this.STOP_TIMEOUT_MS);\n }\n\n /**\n * Start all instances which were enabled before the upgrade\n */\n async startAdapter(): Promise<void> {\n await this.enableInstances(this.stoppedInstances, true);\n }\n\n /**\n * Start or stop given instances\n *\n * @param instances id of instances which will be stopped\n * @param enabled if enable or disable instances\n */\n async enableInstances(instances: string[], enabled: boolean): Promise<void> {\n const ts = Date.now();\n for (const instance of instances) {\n const updatedObj = {\n common: {\n enabled,\n },\n from: `system.host.${this.hostname}`,\n ts,\n } as Partial<ioBroker.InstanceObject>;\n\n await this.objects.extendObjectAsync(instance, updatedObj);\n }\n }\n\n /**\n * Install given version of adapter\n */\n async performUpgrade(): Promise<void> {\n const processExitHandler: ProcessExitCallback = exitCode => {\n this.log(`Upgrade process exited with code: ${exitCode}`, true);\n };\n\n const upgrade = new Upgrade({\n objects: this.objects,\n processExit: processExitHandler,\n states: this.states,\n params: {},\n });\n\n try {\n await upgrade.upgradeAdapter(undefined, `${this.adapterName}@${this.version}`, true, true, false);\n this.response.success = true;\n this.log(`Successfully upgraded ${this.adapterName} to version ${this.version}`);\n } catch (e) {\n this.log(e.message, true);\n this.response.success = false;\n }\n\n await this.setFinished();\n }\n\n /**\n * Starts the web server for admin communication either secure or insecure\n */\n async startWebServer(): Promise<void> {\n if (this.useHttps && this.certPublicName && this.certPrivateName) {\n await this.startSecureWebServer({\n certPublicName: this.certPublicName,\n certPrivateName: this.certPrivateName,\n port: this.port,\n useHttps: true,\n });\n } else {\n this.startInsecureWebServer({ port: this.port, useHttps: false });\n }\n }\n\n /**\n * Shuts down the server, restarts the adapter\n */\n shutdownServer(): void {\n if (this.shutdownAbortController) {\n this.shutdownAbortController.abort();\n }\n\n if (!this.server) {\n return;\n }\n\n this.destroySockets();\n\n this.server.close(async () => {\n await this.startAdapter();\n this.log('Successfully started adapter');\n });\n }\n\n /**\n * Destroy all sockets, to prevent requests from keeping server alive\n */\n destroySockets(): void {\n for (const socket of this.sockets) {\n socket.destroy();\n this.sockets.delete(socket);\n }\n }\n\n /**\n * This function is called when the webserver receives a message\n *\n * @param req received message\n * @param res server response\n */\n webServerCallback(req: http.IncomingMessage, res: http.ServerResponse): void {\n res.writeHead(200);\n res.end(JSON.stringify(this.response));\n\n if (!this.response.running) {\n this.log('Final information delivered');\n this.shutdownServer();\n }\n }\n\n /**\n * Get all instances of the adapter\n */\n async getAllEnabledInstances(): Promise<string[]> {\n const res = await this.objects.getObjectListAsync({\n startkey: `system.adapter.${this.adapterName}.`,\n endkey: `system.adapter.${this.adapterName}.\\u9999`,\n });\n\n let enabledInstances: string[] = [];\n\n enabledInstances = res.rows\n .filter(row => row.value.common.enabled && this.hostname === row.value.common.host)\n .map(row => row.value._id);\n\n return enabledInstances;\n }\n\n /**\n * Log via logger and provide the logs for the server too\n *\n * @param message the message which will be logged\n * @param error if it is an error\n */\n log(message: string, error = false): void {\n if (error) {\n this.logger.error(`host.${this.hostname} ${message}`);\n this.response.stderr.push(message);\n return;\n }\n\n this.logger.info(`host.${this.hostname} [WEBSERVER_UPGRADE] (${this.adapterName}) ${message}`);\n this.response.stdout.push(message);\n }\n\n /**\n * Start an insecure web server for admin communication\n *\n * @param params Web server configuration\n */\n startInsecureWebServer(params: InsecureWebServerParameters): void {\n const { port } = params;\n\n this.server = http.createServer((req, res) => {\n this.webServerCallback(req, res);\n });\n\n this.monitorSockets(this.server);\n\n this.server.listen(port, () => {\n this.log(`Server is running on http://localhost:${port}`);\n });\n }\n\n /**\n * Start a secure web server for admin communication\n *\n * @param params Web server configuration\n */\n async startSecureWebServer(params: SecureWebServerParameters): Promise<void> {\n const { port, certPublicName, certPrivateName } = params;\n\n const { certPublic, certPrivate } = await this.getCertificates({ certPublicName, certPrivateName });\n\n this.server = https.createServer({ key: certPrivate, cert: certPublic }, (req, res) => {\n this.webServerCallback(req, res);\n });\n\n this.monitorSockets(this.server);\n\n this.server.listen(port, () => {\n this.log(`Server is running on http://localhost:${port}`);\n });\n }\n\n /**\n * Keep track of all existing sockets\n *\n * @param server the webserver\n */\n monitorSockets(server: http.Server | https.Server): void {\n server.on('connection', socket => {\n this.sockets.add(socket);\n\n server.once('close', () => {\n this.sockets.delete(socket);\n });\n });\n }\n\n /**\n * Get certificates from the DB\n *\n * @param params certificate information\n */\n async getCertificates(params: GetCertificatesParams): Promise<Certificates> {\n const { certPublicName, certPrivateName } = params;\n\n const obj = await this.objects.getObjectAsync('system.certificates');\n\n if (!obj) {\n throw new Error('No certificates found');\n }\n\n const certs = obj.native.certificates;\n\n return { certPrivate: certs[certPrivateName], certPublic: certs[certPublicName] };\n }\n\n /**\n * Tells the upgrade manager, that server can be shut down on next response or on timeout\n */\n private async setFinished(): Promise<void> {\n this.response.running = false;\n\n await this.startShutdownTimeout();\n }\n\n /**\n * Start a timeout which starts adapter and shuts down the server if expired\n */\n async startShutdownTimeout(): Promise<void> {\n this.shutdownAbortController = new AbortController();\n try {\n await wait(this.SHUTDOWN_TIMEOUT, null, { signal: this.shutdownAbortController.signal });\n\n this.log('Timeout expired, initializing shutdown');\n this.shutdownServer();\n } catch (e) {\n if (e.code !== 'ABORT_ERR') {\n this.log(e.message, true);\n }\n }\n }\n}\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["import http from 'node:http';\nimport https from 'node:https';\nimport { setTimeout as wait } from 'node:timers/promises';\nimport type { Socket } from 'node:net';\nimport type { Duplex } from 'node:stream';\nimport type { Logger } from 'winston';\n\nimport { tools } from '@iobroker/js-controller-common';\nimport type { Client as ObjectsClient } from '@iobroker/db-objects-redis';\nimport type { Client as StatesClient } from '@iobroker/db-states-redis';\nimport { Upgrade, type ProcessExitCallback } from '@iobroker/js-controller-cli';\n\ninterface Certificates {\n /** Public certificate */\n certPublic: string;\n /** Private certificate */\n certPrivate: string;\n}\n\ninterface InsecureWebServerParameters {\n /** if https should be used for the webserver */\n useHttps: false;\n /** port of the web server */\n port: number;\n}\n\ntype SecureWebServerParameters = Omit<InsecureWebServerParameters, 'useHttps'> & {\n useHttps: true;\n certPrivateName: string;\n certPublicName: string;\n};\ntype WebServerParameters = InsecureWebServerParameters | SecureWebServerParameters;\n\nexport type AdapterUpgradeManagerOptions = {\n /** Version of adapter to upgrade too */\n version: string;\n /** Name of the adapter to upgrade */\n adapterName: string;\n /** The objects DB client */\n objects: ObjectsClient;\n /** The states DB client */\n states: StatesClient;\n /** A logger instance */\n logger: Logger;\n} & WebServerParameters;\n\ninterface GetCertificatesParams {\n /** Name of the public certificate */\n certPublicName: string;\n /** Name of the private certificate */\n certPrivateName: string;\n}\n\ninterface ServerResponse {\n /** If the update is still running */\n running: boolean;\n stderr: string[];\n stdout: string[];\n /** if the installation process succeeded */\n success?: boolean;\n}\n\n/**\n * Manages the upgrade of a single adapter, including stopping it and serving a web UI for the upgrade progress\n */\nexport class AdapterUpgradeManager {\n /** Wait ms until adapter is stopped */\n private readonly STOP_TIMEOUT_MS = 3_000;\n /** Wait ms for delivery of final response */\n private readonly SHUTDOWN_TIMEOUT = 10_000;\n /** Name of the adapter to upgrade */\n private readonly adapterName: string;\n /** Desired adapter version */\n private readonly version: string;\n /** Response send by webserver */\n private readonly response: ServerResponse = {\n running: true,\n stderr: [],\n stdout: [],\n };\n /** Used to stop the stop shutdown timeout */\n private shutdownAbortController?: AbortController;\n /** Logger to log to a file and other transports */\n private readonly logger: Logger;\n\n /** The server used for communicating upgrade status */\n private server?: https.Server | http.Server;\n /** All socket connections of the webserver */\n private sockets = new Set<Socket | Duplex>();\n /** Name of the host for logging purposes */\n private readonly hostname = tools.getHostName();\n /** The objects DB client */\n private readonly objects: ObjectsClient;\n /** The states DB client */\n private readonly states: StatesClient;\n /** List of instances that have been stopped */\n private stoppedInstances: string[] = [];\n /** If a webserver should be started with https */\n private readonly useHttps: boolean;\n /** Public certificate name if https is desired */\n private readonly certPublicName?: string;\n /** Private certificate name if https is desired */\n private readonly certPrivateName?: string;\n /** Port where the webserver should be running */\n private readonly port: number;\n\n /**\n * @param options Adapter name, target version, logger and webserver options\n */\n constructor(options: AdapterUpgradeManagerOptions) {\n this.adapterName = options.adapterName;\n this.version = options.version;\n this.logger = options.logger;\n this.objects = options.objects;\n this.states = options.states;\n this.useHttps = options.useHttps;\n this.port = options.port;\n\n if (options.useHttps) {\n this.certPublicName = options.certPublicName;\n this.certPrivateName = options.certPrivateName;\n }\n }\n\n /**\n * Stops the adapter and returns ids of stopped instances\n */\n async stopAdapter(): Promise<void> {\n this.stoppedInstances = await this.getAllEnabledInstances();\n await this.enableInstances(this.stoppedInstances, false);\n await wait(this.STOP_TIMEOUT_MS);\n }\n\n /**\n * Start all instances that were enabled before the upgrade\n */\n async startAdapter(): Promise<void> {\n await this.enableInstances(this.stoppedInstances, true);\n }\n\n /**\n * Start or stop given instances\n *\n * @param instances id of instances which will be stopped\n * @param enabled if enable or disable instances\n */\n async enableInstances(instances: string[], enabled: boolean): Promise<void> {\n const ts = Date.now();\n for (const instance of instances) {\n const updatedObj = {\n common: {\n enabled,\n },\n from: `system.host.${this.hostname}`,\n ts,\n } as Partial<ioBroker.InstanceObject>;\n\n await this.objects.extendObject(instance, updatedObj);\n }\n }\n\n /**\n * Install a given version of the adapter\n */\n async performUpgrade(): Promise<void> {\n const processExitHandler: ProcessExitCallback = exitCode => {\n this.log(`Upgrade process exited with code: ${exitCode}`, true);\n };\n\n const upgrade = new Upgrade({\n objects: this.objects,\n processExit: processExitHandler,\n states: this.states,\n params: {},\n });\n\n try {\n await upgrade.upgradeAdapter(undefined, `${this.adapterName}@${this.version}`, true, true, false);\n this.response.success = true;\n this.log(`Successfully upgraded ${this.adapterName} to version ${this.version}`);\n } catch (e) {\n this.log(e.message, true);\n this.response.success = false;\n }\n\n await this.setFinished();\n }\n\n /**\n * Starts the web server for admin communication either secure or insecure\n */\n async startWebServer(): Promise<void> {\n if (this.useHttps && this.certPublicName && this.certPrivateName) {\n await this.startSecureWebServer({\n certPublicName: this.certPublicName,\n certPrivateName: this.certPrivateName,\n port: this.port,\n useHttps: true,\n });\n } else {\n this.startInsecureWebServer({ port: this.port, useHttps: false });\n }\n }\n\n /**\n * Shuts down the server, restarts the adapter\n */\n shutdownServer(): void {\n if (this.shutdownAbortController) {\n this.shutdownAbortController.abort();\n }\n\n if (!this.server) {\n return;\n }\n\n this.destroySockets();\n\n this.server.close(async () => {\n await this.startAdapter();\n this.log('Successfully started adapter');\n });\n }\n\n /**\n * Destroy all sockets to prevent requests from keeping the server alive\n */\n destroySockets(): void {\n for (const socket of this.sockets) {\n socket.destroy();\n this.sockets.delete(socket);\n }\n }\n\n /**\n * This function is called when the webserver receives a message\n *\n * @param req received message\n * @param res server response\n */\n webServerCallback(req: http.IncomingMessage, res: http.ServerResponse): void {\n res.writeHead(200);\n res.end(JSON.stringify(this.response));\n\n if (!this.response.running) {\n this.log('Final information delivered');\n this.shutdownServer();\n }\n }\n\n /**\n * Get all instances of the adapter\n */\n async getAllEnabledInstances(): Promise<string[]> {\n const res = await this.objects.getObjectListAsync({\n startkey: `system.adapter.${this.adapterName}.`,\n endkey: `system.adapter.${this.adapterName}.\\u9999`,\n });\n\n let enabledInstances: string[] = [];\n\n enabledInstances = res.rows\n .filter(row => row.value.common.enabled && this.hostname === row.value.common.host)\n .map(row => row.value._id);\n\n return enabledInstances;\n }\n\n /**\n * Log via logger and provide the logs for the server too\n *\n * @param message the message which will be logged\n * @param error if it is an error\n */\n log(message: string, error = false): void {\n if (error) {\n this.logger.error(`host.${this.hostname} ${message}`);\n this.response.stderr.push(message);\n return;\n }\n\n this.logger.info(`host.${this.hostname} [WEBSERVER_UPGRADE] (${this.adapterName}) ${message}`);\n this.response.stdout.push(message);\n }\n\n /**\n * Start an insecure web server for admin communication\n *\n * @param params Web server configuration\n */\n startInsecureWebServer(params: InsecureWebServerParameters): void {\n const { port } = params;\n\n this.server = http.createServer((req, res) => {\n this.webServerCallback(req, res);\n });\n\n this.monitorSockets(this.server);\n\n this.server.listen(port, () => {\n this.log(`Server is running on http://localhost:${port}`);\n });\n }\n\n /**\n * Start a secure web server for admin communication\n *\n * @param params Web server configuration\n */\n async startSecureWebServer(params: SecureWebServerParameters): Promise<void> {\n const { port, certPublicName, certPrivateName } = params;\n\n const { certPublic, certPrivate } = await this.getCertificates({ certPublicName, certPrivateName });\n\n this.server = https.createServer({ key: certPrivate, cert: certPublic }, (req, res) => {\n this.webServerCallback(req, res);\n });\n\n this.monitorSockets(this.server);\n\n this.server.listen(port, () => {\n this.log(`Server is running on http://localhost:${port}`);\n });\n }\n\n /**\n * Keep track of all existing sockets\n *\n * @param server the webserver\n */\n monitorSockets(server: http.Server | https.Server): void {\n server.on('connection', socket => {\n this.sockets.add(socket);\n\n server.once('close', () => {\n this.sockets.delete(socket);\n });\n });\n }\n\n /**\n * Get certificates from the DB\n *\n * @param params certificate information\n */\n async getCertificates(params: GetCertificatesParams): Promise<Certificates> {\n const { certPublicName, certPrivateName } = params;\n\n const obj = await this.objects.getObjectAsync('system.certificates');\n\n if (!obj) {\n throw new Error('No certificates found');\n }\n\n const certs = obj.native.certificates;\n\n return { certPrivate: certs[certPrivateName], certPublic: certs[certPublicName] };\n }\n\n /**\n * Tells the upgrade manager that the server can be shut down on the next response or on timeout\n */\n private async setFinished(): Promise<void> {\n this.response.running = false;\n\n await this.startShutdownTimeout();\n }\n\n /**\n * Start a timeout which starts the adapter and shuts down the server if expired\n */\n async startShutdownTimeout(): Promise<void> {\n this.shutdownAbortController = new AbortController();\n try {\n await wait(this.SHUTDOWN_TIMEOUT, null, { signal: this.shutdownAbortController.signal });\n\n this.log('Timeout expired, initializing shutdown');\n this.shutdownServer();\n } catch (e) {\n if (e.code !== 'ABORT_ERR') {\n this.log(e.message, true);\n }\n }\n }\n}\n"],
5
+ "mappings": "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",
6
6
  "names": ["wait", "http", "https"]
7
7
  }
@@ -9,9 +9,15 @@ interface AdapterVersionBlockedOptions {
9
9
  /** Name of the adapter */
10
10
  adapterName: string;
11
11
  }
12
+ /**
13
+ * Checks adapters and their versions against the configured block list
14
+ */
12
15
  export declare class BlocklistManager {
13
16
  /** The objects client */
14
17
  private readonly objects;
18
+ /**
19
+ * @param options The objects client used to read the block list
20
+ */
15
21
  constructor(options: BlocklistManagerOptions);
16
22
  /**
17
23
  * Iterates over all instances, disables blocklisted once if enabled
@@ -5,6 +5,7 @@ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
5
  var __getOwnPropNames = Object.getOwnPropertyNames;
6
6
  var __getProtoOf = Object.getPrototypeOf;
7
7
  var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
8
9
  var __export = (target, all) => {
9
10
  for (var name in all)
10
11
  __defProp(target, name, { get: all[name], enumerable: true });
@@ -34,8 +35,14 @@ module.exports = __toCommonJS(blocklistManager_exports);
34
35
  var import_constants = require("@iobroker/js-controller-common-db/constants");
35
36
  var import_semver = __toESM(require("semver"), 1);
36
37
  class BlocklistManager {
38
+ static {
39
+ __name(this, "BlocklistManager");
40
+ }
37
41
  /** The objects client */
38
42
  objects;
43
+ /**
44
+ * @param options The objects client used to read the block list
45
+ */
39
46
  constructor(options) {
40
47
  this.objects = options.objects;
41
48
  }
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../../src/lib/blocklistManager.ts"],
4
- "sourcesContent": ["import type { Client as ObjectsClient } from '@iobroker/db-objects-redis';\nimport {\n HIGHEST_UNICODE_SYMBOL,\n SYSTEM_ADAPTER_PREFIX,\n SYSTEM_CONFIG_ID,\n SYSTEM_REPOSITORIES_ID,\n} from '@iobroker/js-controller-common-db/constants';\nimport semver from 'semver';\n\ninterface BlocklistManagerOptions {\n /** The objects client */\n objects: ObjectsClient;\n}\n\ninterface AdapterVersionBlockedOptions {\n /** The version of the adapter instance */\n version: string;\n /** Name of the adapter */\n adapterName: string;\n}\n\ninterface InternalAdapterVersionBlockedOptions extends AdapterVersionBlockedOptions {\n /** The system repository object */\n systemRepoObj: ioBroker.RepositoryObject;\n /** The system config object */\n systemConfigObj: ioBroker.SystemConfigObject;\n}\n\nexport class BlocklistManager {\n /** The objects client */\n private readonly objects: ObjectsClient;\n\n constructor(options: BlocklistManagerOptions) {\n this.objects = options.objects;\n }\n\n /**\n * Iterates over all instances, disables blocklisted once if enabled\n *\n * @returns A list of disabled instances\n */\n async disableAllBlocklistedInstances(): Promise<ioBroker.InstanceObject[]> {\n /** List of instances which we have disabled */\n const disabledList: ioBroker.InstanceObject[] = [];\n\n const systemRepoObj = await this.objects.getObject(SYSTEM_REPOSITORIES_ID);\n const systemConfigObj = await this.objects.getObject(SYSTEM_CONFIG_ID);\n\n if (!systemConfigObj || !systemRepoObj) {\n return disabledList;\n }\n\n const instancesView = await this.objects.getObjectViewAsync('system', 'instance', {\n startkey: SYSTEM_ADAPTER_PREFIX,\n endkey: SYSTEM_ADAPTER_PREFIX + HIGHEST_UNICODE_SYMBOL,\n });\n\n for (const row of instancesView.rows) {\n const obj = row.value;\n\n if (!obj.common.enabled) {\n continue;\n }\n\n const isBlocked = this.internalIsAdapterVersionBlocked({\n systemConfigObj,\n systemRepoObj,\n adapterName: obj.common.name,\n version: obj.common.version,\n });\n\n if (!isBlocked) {\n continue;\n }\n\n obj.common.enabled = false;\n\n await this.objects.setObject(obj._id, obj);\n disabledList.push(row.value);\n }\n\n return disabledList;\n }\n\n /**\n * Check if version of a specific adapter is blocked\n *\n * @param options adapter version and name information\n * @returns A boolean indicating if the adapter version is blocked\n */\n async isAdapterVersionBlocked(options: AdapterVersionBlockedOptions): Promise<boolean> {\n const systemRepoObj = await this.objects.getObject(SYSTEM_REPOSITORIES_ID);\n const systemConfigObj = await this.objects.getObject(SYSTEM_CONFIG_ID);\n\n if (!systemConfigObj || !systemRepoObj) {\n return false;\n }\n\n return this.internalIsAdapterVersionBlocked({ ...options, systemRepoObj, systemConfigObj });\n }\n\n /**\n * Check if version of a specific adapter is blocked\n *\n * @param options information about adapter, version and cached objects\n * @returns A boolean indicating if the adapter version is blocked\n */\n private internalIsAdapterVersionBlocked(options: InternalAdapterVersionBlockedOptions): boolean {\n const { adapterName, version, systemRepoObj, systemConfigObj } = options;\n\n for (const activeRepoName of systemConfigObj.common.activeRepo) {\n if (!(activeRepoName in systemRepoObj.native.repositories)) {\n return false;\n }\n\n const repo = systemRepoObj.native.repositories[activeRepoName];\n const adapterEntry = repo.json?.[adapterName];\n\n if (!adapterEntry || !('blockedVersions' in adapterEntry)) {\n return false;\n }\n\n for (const blockedVersion of adapterEntry.blockedVersions) {\n if (semver.satisfies(version, blockedVersion, { includePrerelease: true })) {\n return true;\n }\n }\n }\n\n return false;\n }\n}\n"],
5
- "mappings": ";;;;;;;;;;;;;;;;;;;;;;;;;;;;AACA;;;;;AAAA,uBAKO;AACP,oBAAmB;AAqBb,MAAO,iBAAgB;;EAER;EAEjB,YAAY,SAAgC;AACxC,SAAK,UAAU,QAAQ;EAC3B;;;;;;EAOA,MAAM,iCAA8B;AAEhC,UAAM,eAA0C,CAAA;AAEhD,UAAM,gBAAgB,MAAM,KAAK,QAAQ,UAAU,uCAAsB;AACzE,UAAM,kBAAkB,MAAM,KAAK,QAAQ,UAAU,iCAAgB;AAErE,QAAI,CAAC,mBAAmB,CAAC,eAAe;AACpC,aAAO;IACX;AAEA,UAAM,gBAAgB,MAAM,KAAK,QAAQ,mBAAmB,UAAU,YAAY;MAC9E,UAAU;MACV,QAAQ,yCAAwB;KACnC;AAED,eAAW,OAAO,cAAc,MAAM;AAClC,YAAM,MAAM,IAAI;AAEhB,UAAI,CAAC,IAAI,OAAO,SAAS;AACrB;MACJ;AAEA,YAAM,YAAY,KAAK,gCAAgC;QACnD;QACA;QACA,aAAa,IAAI,OAAO;QACxB,SAAS,IAAI,OAAO;OACvB;AAED,UAAI,CAAC,WAAW;AACZ;MACJ;AAEA,UAAI,OAAO,UAAU;AAErB,YAAM,KAAK,QAAQ,UAAU,IAAI,KAAK,GAAG;AACzC,mBAAa,KAAK,IAAI,KAAK;IAC/B;AAEA,WAAO;EACX;;;;;;;EAQA,MAAM,wBAAwB,SAAqC;AAC/D,UAAM,gBAAgB,MAAM,KAAK,QAAQ,UAAU,uCAAsB;AACzE,UAAM,kBAAkB,MAAM,KAAK,QAAQ,UAAU,iCAAgB;AAErE,QAAI,CAAC,mBAAmB,CAAC,eAAe;AACpC,aAAO;IACX;AAEA,WAAO,KAAK,gCAAgC,EAAE,GAAG,SAAS,eAAe,gBAAe,CAAE;EAC9F;;;;;;;EAQQ,gCAAgC,SAA6C;AACjF,UAAM,EAAE,aAAa,SAAS,eAAe,gBAAe,IAAK;AAEjE,eAAW,kBAAkB,gBAAgB,OAAO,YAAY;AAC5D,UAAI,EAAE,kBAAkB,cAAc,OAAO,eAAe;AACxD,eAAO;MACX;AAEA,YAAM,OAAO,cAAc,OAAO,aAAa,cAAc;AAC7D,YAAM,eAAe,KAAK,OAAO,WAAW;AAE5C,UAAI,CAAC,gBAAgB,EAAE,qBAAqB,eAAe;AACvD,eAAO;MACX;AAEA,iBAAW,kBAAkB,aAAa,iBAAiB;AACvD,YAAI,cAAAA,QAAO,UAAU,SAAS,gBAAgB,EAAE,mBAAmB,KAAI,CAAE,GAAG;AACxE,iBAAO;QACX;MACJ;IACJ;AAEA,WAAO;EACX;;",
4
+ "sourcesContent": ["import type { Client as ObjectsClient } from '@iobroker/db-objects-redis';\nimport {\n HIGHEST_UNICODE_SYMBOL,\n SYSTEM_ADAPTER_PREFIX,\n SYSTEM_CONFIG_ID,\n SYSTEM_REPOSITORIES_ID,\n} from '@iobroker/js-controller-common-db/constants';\nimport semver from 'semver';\n\ninterface BlocklistManagerOptions {\n /** The objects client */\n objects: ObjectsClient;\n}\n\ninterface AdapterVersionBlockedOptions {\n /** The version of the adapter instance */\n version: string;\n /** Name of the adapter */\n adapterName: string;\n}\n\ninterface InternalAdapterVersionBlockedOptions extends AdapterVersionBlockedOptions {\n /** The system repository object */\n systemRepoObj: ioBroker.RepositoryObject;\n /** The system config object */\n systemConfigObj: ioBroker.SystemConfigObject;\n}\n\n/**\n * Checks adapters and their versions against the configured block list\n */\nexport class BlocklistManager {\n /** The objects client */\n private readonly objects: ObjectsClient;\n\n /**\n * @param options The objects client used to read the block list\n */\n constructor(options: BlocklistManagerOptions) {\n this.objects = options.objects;\n }\n\n /**\n * Iterates over all instances, disables blocklisted once if enabled\n *\n * @returns A list of disabled instances\n */\n async disableAllBlocklistedInstances(): Promise<ioBroker.InstanceObject[]> {\n /** List of instances which we have disabled */\n const disabledList: ioBroker.InstanceObject[] = [];\n\n const systemRepoObj = await this.objects.getObject(SYSTEM_REPOSITORIES_ID);\n const systemConfigObj = await this.objects.getObject(SYSTEM_CONFIG_ID);\n\n if (!systemConfigObj || !systemRepoObj) {\n return disabledList;\n }\n\n const instancesView = await this.objects.getObjectViewAsync('system', 'instance', {\n startkey: SYSTEM_ADAPTER_PREFIX,\n endkey: SYSTEM_ADAPTER_PREFIX + HIGHEST_UNICODE_SYMBOL,\n });\n\n for (const row of instancesView.rows) {\n const obj = row.value;\n\n if (!obj.common.enabled) {\n continue;\n }\n\n const isBlocked = this.internalIsAdapterVersionBlocked({\n systemConfigObj,\n systemRepoObj,\n adapterName: obj.common.name,\n version: obj.common.version,\n });\n\n if (!isBlocked) {\n continue;\n }\n\n obj.common.enabled = false;\n\n await this.objects.setObject(obj._id, obj);\n disabledList.push(row.value);\n }\n\n return disabledList;\n }\n\n /**\n * Check if version of a specific adapter is blocked\n *\n * @param options adapter version and name information\n * @returns A boolean indicating if the adapter version is blocked\n */\n async isAdapterVersionBlocked(options: AdapterVersionBlockedOptions): Promise<boolean> {\n const systemRepoObj = await this.objects.getObject(SYSTEM_REPOSITORIES_ID);\n const systemConfigObj = await this.objects.getObject(SYSTEM_CONFIG_ID);\n\n if (!systemConfigObj || !systemRepoObj) {\n return false;\n }\n\n return this.internalIsAdapterVersionBlocked({ ...options, systemRepoObj, systemConfigObj });\n }\n\n /**\n * Check if version of a specific adapter is blocked\n *\n * @param options information about adapter, version and cached objects\n * @returns A boolean indicating if the adapter version is blocked\n */\n private internalIsAdapterVersionBlocked(options: InternalAdapterVersionBlockedOptions): boolean {\n const { adapterName, version, systemRepoObj, systemConfigObj } = options;\n\n for (const activeRepoName of systemConfigObj.common.activeRepo) {\n if (!(activeRepoName in systemRepoObj.native.repositories)) {\n return false;\n }\n\n const repo = systemRepoObj.native.repositories[activeRepoName];\n const adapterEntry = repo.json?.[adapterName];\n\n if (!adapterEntry || !('blockedVersions' in adapterEntry)) {\n return false;\n }\n\n for (const blockedVersion of adapterEntry.blockedVersions) {\n if (semver.satisfies(version, blockedVersion, { includePrerelease: true })) {\n return true;\n }\n }\n }\n\n return false;\n }\n}\n"],
5
+ "mappings": ";;;;;;;;;;;;;;;;;;;;;;;;;;;;;AACA;;;;;AAAA,uBAKO;AACP,oBAAmB;AAwBb,MAAO,iBAAgB;EA9B7B,OA8B6B;;;;EAER;;;;EAKjB,YAAY,SAAgC;AACxC,SAAK,UAAU,QAAQ;EAC3B;;;;;;EAOA,MAAM,iCAA8B;AAEhC,UAAM,eAA0C,CAAA;AAEhD,UAAM,gBAAgB,MAAM,KAAK,QAAQ,UAAU,uCAAsB;AACzE,UAAM,kBAAkB,MAAM,KAAK,QAAQ,UAAU,iCAAgB;AAErE,QAAI,CAAC,mBAAmB,CAAC,eAAe;AACpC,aAAO;IACX;AAEA,UAAM,gBAAgB,MAAM,KAAK,QAAQ,mBAAmB,UAAU,YAAY;MAC9E,UAAU;MACV,QAAQ,yCAAwB;KACnC;AAED,eAAW,OAAO,cAAc,MAAM;AAClC,YAAM,MAAM,IAAI;AAEhB,UAAI,CAAC,IAAI,OAAO,SAAS;AACrB;MACJ;AAEA,YAAM,YAAY,KAAK,gCAAgC;QACnD;QACA;QACA,aAAa,IAAI,OAAO;QACxB,SAAS,IAAI,OAAO;OACvB;AAED,UAAI,CAAC,WAAW;AACZ;MACJ;AAEA,UAAI,OAAO,UAAU;AAErB,YAAM,KAAK,QAAQ,UAAU,IAAI,KAAK,GAAG;AACzC,mBAAa,KAAK,IAAI,KAAK;IAC/B;AAEA,WAAO;EACX;;;;;;;EAQA,MAAM,wBAAwB,SAAqC;AAC/D,UAAM,gBAAgB,MAAM,KAAK,QAAQ,UAAU,uCAAsB;AACzE,UAAM,kBAAkB,MAAM,KAAK,QAAQ,UAAU,iCAAgB;AAErE,QAAI,CAAC,mBAAmB,CAAC,eAAe;AACpC,aAAO;IACX;AAEA,WAAO,KAAK,gCAAgC,EAAE,GAAG,SAAS,eAAe,gBAAe,CAAE;EAC9F;;;;;;;EAQQ,gCAAgC,SAA6C;AACjF,UAAM,EAAE,aAAa,SAAS,eAAe,gBAAe,IAAK;AAEjE,eAAW,kBAAkB,gBAAgB,OAAO,YAAY;AAC5D,UAAI,EAAE,kBAAkB,cAAc,OAAO,eAAe;AACxD,eAAO;MACX;AAEA,YAAM,OAAO,cAAc,OAAO,aAAa,cAAc;AAC7D,YAAM,eAAe,KAAK,OAAO,WAAW;AAE5C,UAAI,CAAC,gBAAgB,EAAE,qBAAqB,eAAe;AACvD,eAAO;MACX;AAEA,iBAAW,kBAAkB,aAAa,iBAAiB;AACvD,YAAI,cAAAA,QAAO,UAAU,SAAS,gBAAgB,EAAE,mBAAmB,KAAI,CAAE,GAAG;AACxE,iBAAO;QACX;MACJ;IACJ;AAEA,WAAO;EACX;;",
6
6
  "names": ["semver"]
7
7
  }
@@ -38,12 +38,27 @@ export declare class MHServer {
38
38
  private server;
39
39
  private initTimer;
40
40
  private stopped;
41
+ /**
42
+ * @param hostname The name of this host
43
+ * @param logger The logger instance
44
+ * @param config The ioBroker configuration
45
+ * @param info Multihost information such as the number of hosts
46
+ * @param secret Shared secret used for authentication, or false if authentication is disabled
47
+ */
41
48
  constructor(hostname: string, logger: InternalLogger, config: ioBroker.IoBrokerJson, info: MHInfo, secret: string | false);
42
49
  private send;
43
50
  private checkAuthList;
44
51
  private sha;
45
52
  private process;
53
+ /**
54
+ * Start the multihost discovery server and (re)initialize it
55
+ */
46
56
  init(): void;
57
+ /**
58
+ * Stop the multihost server and release the socket
59
+ *
60
+ * @param callback Called once the server has been closed
61
+ */
47
62
  close(callback?: () => void): void;
48
63
  }
49
64
  export {};
@@ -5,6 +5,7 @@ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
5
  var __getOwnPropNames = Object.getOwnPropertyNames;
6
6
  var __getProtoOf = Object.getPrototypeOf;
7
7
  var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
8
9
  var __export = (target, all) => {
9
10
  for (var name in all)
10
11
  __defProp(target, name, { get: all[name], enumerable: true });
@@ -37,6 +38,9 @@ var import_js_controller_common = require("@iobroker/js-controller-common");
37
38
  const PORT = 50005;
38
39
  const MULTICAST_ADDR = "239.255.255.250";
39
40
  class MHServer {
41
+ static {
42
+ __name(this, "MHServer");
43
+ }
40
44
  count = 0;
41
45
  buffer = {};
42
46
  lastFrame = {};
@@ -49,6 +53,13 @@ class MHServer {
49
53
  server = null;
50
54
  initTimer = null;
51
55
  stopped = false;
56
+ /**
57
+ * @param hostname The name of this host
58
+ * @param logger The logger instance
59
+ * @param config The ioBroker configuration
60
+ * @param info Multihost information such as the number of hosts
61
+ * @param secret Shared secret used for authentication, or false if authentication is disabled
62
+ */
52
63
  constructor(hostname, logger, config, info, secret) {
53
64
  this.hostname = hostname;
54
65
  this.config = config;
@@ -166,6 +177,9 @@ class MHServer {
166
177
  break;
167
178
  }
168
179
  }
180
+ /**
181
+ * Start the multihost discovery server and (re)initialize it
182
+ */
169
183
  init() {
170
184
  this.stopped = false;
171
185
  if (this.initTimer) {
@@ -219,7 +233,7 @@ class MHServer {
219
233
  const data = JSON.parse(this.buffer[id]);
220
234
  this.buffer[id] = "";
221
235
  if (data) {
222
- this.process(data, rinfo);
236
+ this.process(data, rinfo).catch((e) => this.logger.error(`Cannot process multihost message: ${e.message}`));
223
237
  }
224
238
  } catch {
225
239
  }
@@ -237,6 +251,11 @@ class MHServer {
237
251
  });
238
252
  this.server.bind(PORT);
239
253
  }
254
+ /**
255
+ * Stop the multihost server and release the socket
256
+ *
257
+ * @param callback Called once the server has been closed
258
+ */
240
259
  close(callback) {
241
260
  this.stopped = true;
242
261
  if (this.initTimer) {