iobroker.bmw 4.3.1 → 4.3.2

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.
package/README.md CHANGED
@@ -209,6 +209,16 @@ If you're not seeing expected data in `VIN.api.*`:
209
209
  This adapter is available at: [https://github.com/TA2k/ioBroker.bmw](https://github.com/TA2k/ioBroker.bmw)
210
210
 
211
211
  ## Changelog
212
+
213
+ <!--
214
+ Placeholder for the next version (at the beginning of the line):
215
+ ### **WORK IN PROGRESS**
216
+ -->
217
+ ### 4.3.2 (2025-12-15)
218
+
219
+ - update telemetry ids for container creation
220
+ - optimize dependabot config (#209)
221
+
212
222
  ### 4.3.1 (2025-10-11)
213
223
 
214
224
  - fix gps coordinate parsing
package/io-package.json CHANGED
@@ -1,8 +1,21 @@
1
1
  {
2
2
  "common": {
3
3
  "name": "bmw",
4
- "version": "4.3.1",
4
+ "version": "4.3.2",
5
5
  "news": {
6
+ "4.3.2": {
7
+ "en": "update telemetry ids for container creation\noptimize dependabot config (#209)",
8
+ "de": "aktualisierung von telemetrie-ids für die container-erstellung\noptimieren abhängigabot config (#209)",
9
+ "ru": "обновление телеметрических идентификаторов для создания контейнеров\nоптимизируйте конфигурацию зависимого робота (#209)",
10
+ "pt": "atualizar ids de telemetria para criação de containers\notimizar a configuração do dependebot (# 209)",
11
+ "nl": "update telemetrie-id's voor het aanmaken van containers\ndependabot config optimaliseren (#209)",
12
+ "fr": "mettre à jour les ids de télémétrie pour la création de conteneurs\noptimiser la configuration de base (#209)",
13
+ "it": "aggiornare ids di telemetria per la creazione di container\nottimizzare la configurazione dipendeabot (#209)",
14
+ "es": "actualización de los sistemas de telemetría para la creación de contenedores\noptimizar config de dependabot (#209)",
15
+ "pl": "aktualizacja identyfikatorów telemetrii do tworzenia kontenerów\noptymalizacja konfiguracji zależnej (# 209)",
16
+ "uk": "оновлення телеметрії кришок для створення контейнерів\nоптимізація налаштування залежностей (#209)",
17
+ "zh-cn": "更新用于创建容器的遥测标识\n优化依赖配置 (# 209)"
18
+ },
6
19
  "4.3.1": {
7
20
  "en": "fix gps coordinate parsing",
8
21
  "de": "fix gps koordinate paring",
@@ -80,19 +93,6 @@
80
93
  "pl": "Zmiana na zalecaną stabilną wersję admin 7.6.17 (#159)\nMigracja do iobroker/eslint-config (#146)\nNaprawa podatności w form-data\nCzyszczenie kodu\nAktualizacja axios\nAktualizacja adapter-core\nNaprawa problemów wykrytych przez sprawdzacz repozytorium (#170)\nAktualizacja zależności",
81
94
  "uk": "Перехід на рекомендовану стабільну версію admin 7.6.17 (#159)\nМіграція на iobroker/eslint-config (#146)\nВиправлення вразливості form-data\nОчищення коду\nОновлення axios\nОновлення adapter-core\nВиправлення проблем, виявлених перевіркою репозиторію (#170)\nОновлення залежностей",
82
95
  "zh-cn": "切换到推荐的稳定版 admin 7.6.17 (#159)\n迁移到 iobroker/eslint-config (#146)\n修复 form-data 漏洞\n代码清理\n更新 axios\n更新 adapter-core\n修复仓库检查器检测到的问题 (#170)\n更新依赖项"
83
- },
84
- "3.0.0": {
85
- "en": "BREAKING: Dropped support for Node.js 18 (#88)\nBREAKING: Dropped support for js-controller 5 (#111)\nBREAKING: change to admin 7.4.10 as recommended by ioBroker (#111)\nencrypt and protect second user password - has to be reentered (#111)\nbump dependencies",
86
- "de": "BREAKING: Unterstützung für Node.js 18 (#88) eingestellt\nBREAKING: Unterstützung für js-controller 5 (#111) eingestellt\nBREAKING: Wechsel zu admin 7.4.10 wie von ioBroker empfohlen (#111)\nzweites Benutzerpasswort verschlüsseln und schützen - muss erneut eingegeben werden (#111)\nAbhängigkeiten aktualisiert",
87
- "ru": "Отказ от поддержки Node.js 18 (#88)\nОтказ от поддержки js-контроллера 5 (#111)\nBREAKING: изменение на админ 7.4.10 в соответствии с рекомендациями ioBroker (#111)\nшифровать и защищать пароль второго пользователя - должен быть повторно введен (#111)\nбамп зависимости",
88
- "pt": "BREAKING: Suporte suspenso para Node.js 18 (# 88)\nBREAKING: Suporte suspenso para o js-controller 5 (# 111)\nBREAKING: mudança para admin 7.4.10 conforme recomendado pelo ioBroker (# 111)\ncriptografar e proteger a segunda senha do usuário - tem que ser reentrada (# 111)\ndependências de colisão",
89
- "nl": "BREAKING: Gestopte ondersteuning voor Node.js 18 (#88)\nBreaking: Dropped support for js-controller 5 (#111)\nBREAKING: overstappen op admin 7.4.10 zoals aanbevolen door ioBroker (#111)\ntweede gebruikerswachtwoord versleutelen en beschermen - moet opnieuw worden ingevoerd (#111)\nbump afhankelijkheden",
90
- "fr": "Soutien abandonné pour Node.js 18 (#88)\nSoutien abandonné pour le contrôleur de js 5 (#111)\nBREAKING: changement à l'administrateur 7.4.10 recommandé par ioBroker (#111)\nchiffrer et protéger le mot de passe du deuxième utilisateur - doit être réintroduit (#111)\ndépendances des bosses",
91
- "it": "BREAKING: Supporto a goccia per Node.js 18 (#88)\nBREAKING: Supporto a goccia per js-controller 5 (#111)\nBREAKING: cambiamento a admin 7.4.10 come raccomandato da ioBroker (#111)\ncrittografare e proteggere la seconda password dell'utente - deve essere riattivata (#111)\nindipendenza urto",
92
- "es": "BREAKING: Soporte abandonado para Node.js 18 (#88)\nBREAKING: Soporte desechado para js-controller 5 (#111)\nBREAKING: cambio a admin 7.4.10 según lo recomendado por ioBroker (#111)\nencriptar y proteger la segunda contraseña de usuario - tiene que ser reiniciado (#111)\ndependencia de los gastos",
93
- "pl": "BREAKING: Upuszczone wsparcie dla Node.js 18 (# 88)\nBREAKING: Utracone wsparcie dla kontrolera js- 5 (# 111)\nBREAKING: zmiana na admin 7.4.10 zgodnie z zaleceniami jOBrokera (# 111)\nszyfrowanie i ochrona hasła drugiego użytkownika - należy ponownie wprowadzić (# 111)\nuzależnienia od guza",
94
- "uk": "BREAKING: Dropped підтримка для Node.js 18 (#88)\nBREAKING: Dropped підтримка для js-controller 5 (#111)\nBREAKING: зміни до адміністратора 7.4.10, як рекомендовано ioBroker (#111)\nзашифрувати і захистити другий пароль користувача - повинен бути повторний (#111)\nbump залежності",
95
- "zh-cn": "对节点18(#88)的支持下降\n中断 : js 控制器 5 已放弃支持 (# 111)\n根据ioBroker的建议(# 111) 改为admin 7.4.10\n加密和保护第二个用户密码 - 必须重新输入( # 111)\n意外依赖"
96
96
  }
97
97
  },
98
98
  "titleLang": {
package/main.js CHANGED
@@ -74,8 +74,8 @@ class Bmw extends utils.Adapter {
74
74
 
75
75
  // Validate configuration
76
76
  if (!this.config.clientId) {
77
- this.log.error('BMW CarData Client ID not configured! Please set up in adapter settings.');
78
- this.log.info('Visit BMW ConnectedDrive portal, go to CarData section, and generate a client ID');
77
+ this.log.error(`BMW CarData Client ID not configured! Please set up in adapter settings.`);
78
+ this.log.info(`Visit BMW ConnectedDrive portal, go to CarData section, and generate a client ID`);
79
79
  return;
80
80
  }
81
81
 
@@ -156,10 +156,10 @@ class Bmw extends utils.Adapter {
156
156
 
157
157
  // Periodic telematic data refresh - MQTT provides real-time updates
158
158
  if (!this.containerId) {
159
- this.log.warn('No container ID available for periodic telematic data fetch, setting up container...');
159
+ this.log.warn(`No container ID available for periodic telematic data fetch, setting up container...`);
160
160
  const setupSuccess = await this.setupTelematicContainer();
161
161
  if (!setupSuccess) {
162
- this.log.error('Failed to setup telematic container for periodic updates');
162
+ this.log.error(`Failed to setup telematic container for periodic updates`);
163
163
  return;
164
164
  }
165
165
  }
@@ -260,22 +260,22 @@ class Bmw extends utils.Adapter {
260
260
  // Special handling for 400 Bad Request - likely client configuration issue
261
261
  if (error.response.status === 400) {
262
262
  this.log.error('='.repeat(80));
263
- this.log.error('BMW CLIENT ID CONFIGURATION ERROR (400 Bad Request)');
263
+ this.log.error(`BMW CLIENT ID CONFIGURATION ERROR (400 Bad Request)`);
264
264
  this.log.error('='.repeat(80));
265
- this.log.error('This error usually means:');
266
- this.log.error('1. CarData API access is not activated for your Client ID');
267
- this.log.error('2. CarData Streaming is not enabled for your Client ID');
268
- this.log.error('3. Your Client ID is invalid or has been revoked');
265
+ this.log.error(`This error usually means:`);
266
+ this.log.error(`1. CarData API access is not activated for your Client ID`);
267
+ this.log.error(`2. CarData Streaming is not enabled for your Client ID`);
268
+ this.log.error(`3. Your Client ID is invalid or has been revoked`);
269
269
  this.log.error('');
270
- this.log.error('To fix this issue:');
271
- this.log.error('1. Visit BMW ConnectedDrive portal: https://www.bmw.de/de-de/mybmw/vehicle-overview');
272
- this.log.error('2. Go to CarData section');
270
+ this.log.error(`To fix this issue:`);
271
+ this.log.error(`1. Visit BMW ConnectedDrive portal: https://www.bmw.de/de-de/mybmw/vehicle-overview`);
272
+ this.log.error(`2. Go to CarData section`);
273
273
  this.log.error(
274
- '3. Check if CarData API and CarData Streaming are both activated. Sometimes it needs 30s to save the selection',
274
+ `3. Check if CarData API and CarData Streaming are both activated. Sometimes it needs 30s to save the selection`,
275
275
  );
276
- this.log.error('4. If not activated, enable both services');
277
- this.log.error('5. If already activated, delete and recreate your Client ID');
278
- this.log.error('6. Update the adapter configuration with the new Client ID');
276
+ this.log.error(`4. If not activated, enable both services`);
277
+ this.log.error(`5. If already activated, delete and recreate your Client ID`);
278
+ this.log.error(`6. Update the adapter configuration with the new Client ID`);
279
279
  this.log.error('='.repeat(80));
280
280
  }
281
281
  }
@@ -300,13 +300,13 @@ class Bmw extends utils.Adapter {
300
300
 
301
301
  // Show user instructions
302
302
  this.log.info('='.repeat(80));
303
- this.log.info('BMW CARDATA AUTHORIZATION REQUIRED');
303
+ this.log.info(`BMW CARDATA AUTHORIZATION REQUIRED`);
304
304
  this.log.info('='.repeat(80));
305
305
  this.log.info(`1. Visit: ${verification_uri_complete}`);
306
306
  this.log.info(`2. Or visit: ${deviceResponse.data.verification_uri} and enter code: ${user_code}`);
307
307
  this.log.info(`3. Login with your BMW account and authorize`);
308
308
  this.log.info(`4. Code expires in ${Math.floor(expires_in / 60)} minutes`);
309
- this.log.info('The adapter will automatically continue after authorization');
309
+ this.log.info(`The adapter will automatically continue after authorization`);
310
310
  this.log.info('='.repeat(80));
311
311
 
312
312
  // Step 2: Poll for tokens
@@ -358,7 +358,7 @@ class Bmw extends utils.Adapter {
358
358
 
359
359
  await this.setState('cardataauth.session', JSON.stringify(this.session), true);
360
360
  this.setState('info.connection', true, true);
361
- this.log.info('BMW CarData authorization successful!');
361
+ this.log.info(`BMW CarData authorization successful!`);
362
362
 
363
363
  // Mark this as an initial login so basicData will be fetched
364
364
  this.initialLogin = true;
@@ -369,14 +369,14 @@ class Bmw extends utils.Adapter {
369
369
  this.log.debug(`Token polling error: ${errorCode || error.message}`);
370
370
 
371
371
  if (errorCode === 'authorization_pending') {
372
- this.log.debug('Authorization still pending, continuing to poll...');
372
+ this.log.debug(`Authorization still pending, continuing to poll...`);
373
373
  continue; // Keep polling
374
374
  } else if (errorCode === 'slow_down') {
375
- this.log.debug('Rate limit hit, slowing down polling...');
375
+ this.log.debug(`Rate limit hit, slowing down polling...`);
376
376
  await this.sleep(5000); // Additional delay
377
377
  continue;
378
378
  } else if (errorCode === 'expired_token') {
379
- this.log.error('Authorization code expired, please restart adapter');
379
+ this.log.error(`Authorization code expired, please restart adapter`);
380
380
  return false;
381
381
  } else {
382
382
  this.log.error(`Token request failed: ${errorCode || error.message}`);
@@ -437,7 +437,7 @@ class Bmw extends utils.Adapter {
437
437
  }
438
438
 
439
439
  if (mappings.length === 0) {
440
- this.log.info('No BMW vehicles found in CarData mappings');
440
+ this.log.info(`No BMW vehicles found in CarData mappings`);
441
441
  return;
442
442
  }
443
443
 
@@ -480,7 +480,7 @@ class Bmw extends utils.Adapter {
480
480
  if (error.response) {
481
481
  this.log.error(`Response: ${JSON.stringify(error.response.data)}`);
482
482
  if (error.response.status === 403 || error.response.status === 429) {
483
- this.log.warn('Rate limit exceeded or access denied');
483
+ this.log.warn(`Rate limit exceeded or access denied`);
484
484
  }
485
485
  }
486
486
  });
@@ -488,13 +488,17 @@ class Bmw extends utils.Adapter {
488
488
  // Reset initialLogin flag after processing all vehicles
489
489
  if (this.initialLogin) {
490
490
  this.initialLogin = false;
491
- this.log.info('Initial login basicData fetching completed');
491
+ this.log.info(`Initial login basicData fetching completed`);
492
492
  }
493
493
 
494
494
  await this.sleep(2000);
495
495
  }
496
496
 
497
- // Create complete vehicle structure including basic states and remote buttons
497
+ /**
498
+ * Create complete vehicle structure including basic states and remote buttons
499
+ *
500
+ * @param {string} vin - The vehicle VIN
501
+ */
498
502
  async createVehicleStates(vin) {
499
503
  // Create vehicle device
500
504
  await this.extendObject(vin, {
@@ -640,7 +644,6 @@ class Bmw extends utils.Adapter {
640
644
 
641
645
  const used = this.apiCalls.length;
642
646
  const remaining = API_QUOTA_LIMIT - used;
643
-
644
647
  // Quota states removed - using only apiCallsHistory for persistence
645
648
 
646
649
  return { used, remaining };
@@ -722,10 +725,20 @@ class Bmw extends utils.Adapter {
722
725
  }
723
726
  }
724
727
 
728
+ /**
729
+ * Pauses execution for a specified duration.
730
+ *
731
+ * @param {number} ms - The duration to pause in milliseconds.
732
+ */
725
733
  sleep(ms) {
726
734
  return new Promise(resolve => setTimeout(resolve, ms));
727
735
  }
728
736
 
737
+ /**
738
+ * Function to clean up old states from previous adapter versions
739
+ *
740
+ * @param {string} vin - The vehicle VIN
741
+ */
729
742
  async cleanObjects(vin) {
730
743
  // Check if this is an upgrade from old version by looking for remotev2 states
731
744
  const remoteState = await this.getObjectAsync(`${vin}.remotev2`);
@@ -733,7 +746,7 @@ class Bmw extends utils.Adapter {
733
746
  this.log.info(`Cleaning old states for ${vin} (upgrading from previous version)`);
734
747
 
735
748
  // Delete all old state structures recursively
736
- await this.delObjectAsync(`${vin}`, { recursive: true });
749
+ await this.delObjectAsync(vin, { recursive: true });
737
750
 
738
751
  // Create fresh vehicle device
739
752
  await this.extendObject(vin, {
@@ -755,20 +768,20 @@ class Bmw extends utils.Adapter {
755
768
  await this.delObjectAsync(`${vin}.chargingprofile`, { recursive: true });
756
769
  await this.delObjectAsync(`${vin}.serviceExecutionHistory`, { recursive: true });
757
770
  await this.delObjectAsync(`${vin}.apiV2`, { recursive: true });
758
- await this.delObject(`${vin}.remote`, { recursive: true });
771
+ await this.delObjectAsync(`${vin}.remote`, { recursive: true });
759
772
  }
760
773
  }
761
774
 
762
775
  // Clean up old global states
763
- await this.delObject(`_DatenNeuLaden`);
764
- await this.delObject(`_LetzterDatenabrufOK`);
765
- await this.delObject(`_LetzerFehler`);
776
+ await this.delObjectAsync(`_DatenNeuLaden`);
777
+ await this.delObjectAsync(`_LetzterDatenabrufOK`);
778
+ await this.delObjectAsync(`_LetzerFehler`);
766
779
 
767
780
  // Clean up old authentication objects (v3.x used different auth structure)
768
- const oldAuthObjects = await this.getObjectAsync('auth');
781
+ const oldAuthObjects = await this.getObjectAsync(`auth`);
769
782
  if (oldAuthObjects) {
770
- this.log.info('Cleaning up complete old auth folder from previous version');
771
- await this.delObjectAsync('auth', { recursive: true });
783
+ this.log.info(`Cleaning up complete old auth folder from previous version`);
784
+ await this.delObjectAsync(`auth`, { recursive: true });
772
785
  }
773
786
  }
774
787
 
@@ -778,7 +791,7 @@ class Bmw extends utils.Adapter {
778
791
  return await this.login();
779
792
  }
780
793
 
781
- this.log.debug('Refreshing BMW CarData tokens');
794
+ this.log.debug(`Refreshing BMW CarData tokens`);
782
795
  this.log.debug(`Refresh token URL: ${this.authApiBase}/token`);
783
796
  this.log.debug(`Client ID: ${this.config.clientId}`);
784
797
 
@@ -800,9 +813,9 @@ class Bmw extends utils.Adapter {
800
813
  .then(async res => {
801
814
  // Store refreshed tokens (keep existing session structure)
802
815
  this.session = res.data;
803
- this.setState('cardataauth.session', JSON.stringify(this.session), true);
804
- this.setState('info.connection', true, true);
805
- this.log.debug('Tokens refreshed successfully - MQTT will auto-reconnect with new credentials');
816
+ this.setState(`cardataauth.session`, JSON.stringify(this.session), true);
817
+ this.setState(`info.connection`, true, true);
818
+ this.log.debug(`Tokens refreshed successfully - MQTT will auto-reconnect with new credentials`);
806
819
  this.mqtt?.options && (this.mqtt.options.password = this.session.id_token);
807
820
  return res.data;
808
821
  })
@@ -817,7 +830,7 @@ class Bmw extends utils.Adapter {
817
830
  if (status >= 400 && status < 500) {
818
831
  // 4xx errors indicate authentication problems - reset needed
819
832
  this.log.error(`Token refresh failed with HTTP ${status} auth error - starting new device flow`);
820
- this.setState('info.connection', false, true);
833
+ this.setState(`info.connection`, false, true);
821
834
  return await this.login();
822
835
  }
823
836
  }
@@ -825,20 +838,20 @@ class Bmw extends utils.Adapter {
825
838
  this.log.warn(
826
839
  `Token refresh failed, will retry on next refresh cycle. You can also delete bmw.0.cardataauth.session state to force re-login.`,
827
840
  );
828
- this.setState('info.connection', false, true);
841
+ this.setState(`info.connection`, false, true);
829
842
  return;
830
843
  });
831
844
  }
832
845
 
833
846
  async connectMQTT() {
834
847
  if (!this.session.id_token) {
835
- this.log.warn('No MQTT credentials available (missing ID token)');
848
+ this.log.warn(`No MQTT credentials available (missing ID token)`);
836
849
  return false;
837
850
  }
838
851
 
839
852
  if (!this.config.cardataStreamingUsername) {
840
- this.log.error('CarData Streaming Username not configured! Please set it in adapter settings.');
841
- this.log.error('Find your streaming username in BMW ConnectedDrive portal under CarData > Streaming section.');
853
+ this.log.error(`CarData Streaming Username not configured! Please set it in adapter settings.`);
854
+ this.log.error(`Find your streaming username in BMW ConnectedDrive portal under CarData > Streaming section.`);
842
855
  return false;
843
856
  }
844
857
 
@@ -862,12 +875,12 @@ class Bmw extends utils.Adapter {
862
875
  this.mqtt = mqtt.connect(options);
863
876
 
864
877
  this.mqtt.on('connect', () => {
865
- this.log.info('BMW MQTT stream connected');
866
- this.setState('info.mqttConnected', true, true);
878
+ this.log.info(`BMW MQTT stream connected`);
879
+ this.setState(`info.mqttConnected`, true, true);
867
880
 
868
881
  // Subscribe to all vehicle topics for this CarData Streaming username
869
882
  const topic = `${this.config.cardataStreamingUsername}/+`;
870
- this.mqtt.subscribe(topic, err => {
883
+ this.mqtt?.subscribe(topic, err => {
871
884
  if (err) {
872
885
  this.log.error(`MQTT subscription failed: ${err.message}`);
873
886
  } else {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "iobroker.bmw",
3
- "version": "4.3.1",
3
+ "version": "4.3.2",
4
4
  "description": "Adapter for BMW",
5
5
  "author": {
6
6
  "name": "TA2k",
@@ -36,7 +36,7 @@
36
36
  "@iobroker/eslint-config": "^2.2.0",
37
37
  "@iobroker/testing": "^5.2.2",
38
38
  "@tsconfig/node20": "^20.1.8",
39
- "@types/node": "^24.10.1",
39
+ "@types/node": "^24.10.4",
40
40
  "@types/qs": "^6.14.0",
41
41
  "globals": "^16.5.0",
42
42
  "typescript": "~5.9.3"
package/telematic.json CHANGED
@@ -101,8 +101,8 @@
101
101
  {
102
102
  "cardata_element": "Charging port status text",
103
103
  "cardata_element_de": "Status-Text des Ladeanschlusses",
104
- "description": "Required alongside Vehicle.Body.ChargingPort.Status to ensure correct handling of charging sessions for G08 BEV vehicles (for details, contact DE-3-E; onboard fix expected by 2021-03)",
105
- "description_de": "Erforderlich zusammen mit Vehicle.Body.ChargingPort.Status, um eine korrekte Handhabbarkeit der Ladesitzungen bei G08 BEV Fahrzeugen sicherzustellen (für Details bitte DE-3-E kontaktieren; Korrektur im Fahrzeug bis 2021-03 erwartet)",
104
+ "description": "Required alongside Vehicle.Body.ChargingPort.Status to ensure correct handling of charging sessions for G08 BEV vehicles.",
105
+ "description_de": "Erforderlich zusammen mit Vehicle.Body.ChargingPort.Status, um eine korrekte Handhabbarkeit der Ladesitzungen bei G08 BEV Fahrzeugen sicherzustellen.",
106
106
  "technical_identifier": "vehicle.body.chargingPort.statusClearText",
107
107
  "data_type": "string",
108
108
  "typical_value_range": [
@@ -2712,7 +2712,7 @@
2712
2712
  "description_de": "Der Fehlerspeicher gibt Auskunft über potenzielle Störungen oder technische Defekte im Fahrzeug. Diese Informationen sind für Werkstätten gedacht. Kundenrelevante Störungen, die dem Fahrer im Fahrzeug angezeigt werden, sind unter dem CarData Element „Check Control Meldungen“ zu finden. Details hierzu sind in der Betriebsanleitung des Fahrzeugs dokumentiert.",
2713
2713
  "technical_identifier": "vehicle.electronicControlUnit.diagnosticTroubleCodes.raw",
2714
2714
  "data_type": "",
2715
- "typical_value_range": "The JSON structure is appended at the end of the table (4).",
2715
+ "typical_value_range": "-",
2716
2716
  "unit": "",
2717
2717
  "streaming_capable": true
2718
2718
  },
@@ -2742,17 +2742,6 @@
2742
2742
  "unit": "",
2743
2743
  "streaming_capable": true
2744
2744
  },
2745
- {
2746
- "cardata_element": "Learning navigation",
2747
- "cardata_element_de": "Lernende Navigation",
2748
- "description": "Displays the learned navigation recommendations (preferred routes and destinations of the customer).",
2749
- "description_de": "Gibt die gelernten Navigationsempfehlungen (bevorzugte Routen und Ziele des Kunden) an.",
2750
- "technical_identifier": "vehicle.learningNavigation",
2751
- "data_type": "",
2752
- "typical_value_range": "Details can be found in the corresponding Swagger documentation: ../learningNavigation",
2753
- "unit": "",
2754
- "streaming_capable": false
2755
- },
2756
2745
  {
2757
2746
  "cardata_element": "Vehicle image",
2758
2747
  "cardata_element_de": "Fahrzeugbild",
@@ -3485,7 +3474,7 @@
3485
3474
  "description_de": "Der Wert gibt die letzten relevanten Check-Control-Meldungen an, welche im Fahrzeug angezeigt und an BMW übertragen wurden. Check-Control überwacht Funktionen im Fahrzeug und meldet, wenn in überwachten Systemen eine Störung vorliegt. Eine Check-Control-Meldung wird als Kombination von Kontroll- oder Warnleuchten und Textmeldungen in der Instrumentenkombination und ggf. im Head-Up Display angezeigt. Hinweis: Nicht alle Check-Control-Meldungen, die im Fahrzeug angezeigt werden, werden an BMW übertragen.",
3486
3475
  "technical_identifier": "vehicle.status.checkControlMessages",
3487
3476
  "data_type": "",
3488
- "typical_value_range": "The Check Control example is appended at the end of the table (2).",
3477
+ "typical_value_range": "-",
3489
3478
  "unit": "",
3490
3479
  "streaming_capable": false
3491
3480
  },
@@ -3496,7 +3485,7 @@
3496
3485
  "description_de": "Sensoren und spezielle Algorithmen berücksichtigen die Einsatzbedingungen des Fahrzeugs. CBS ermittelt damit den Wartungsbedarf. Das System ermöglicht somit den Wartungsumfang an das individuelle Nutzungsprofil anzupassen.",
3497
3486
  "technical_identifier": "vehicle.status.conditionBasedServices",
3498
3487
  "data_type": "",
3499
- "typical_value_range": "The Condition Based Service example is appended at the end of the table (3).",
3488
+ "typical_value_range": "-",
3500
3489
  "unit": "",
3501
3490
  "streaming_capable": false
3502
3491
  },
package/lib/tools.js DELETED
@@ -1,110 +0,0 @@
1
- // DEACTIVATED
2
-
3
- // const axios = require('axios').default;
4
-
5
- /**
6
- * Tests whether the given variable is a real object and not an Array
7
- *
8
- * @param {any} it The variable to test
9
- * @returns {it is Record<string, any>} True if the variable is a real object, false otherwise.
10
- */
11
- /*
12
- function isObject(it) {
13
- // This is necessary because:
14
- // typeof null === 'object'
15
- // typeof [] === 'object'
16
- // [] instanceof Object === true
17
- return Object.prototype.toString.call(it) === '[object Object]';
18
- }*/
19
-
20
- /**
21
- * Tests whether the given variable is really an Array
22
- *
23
- * @param {any} it The variable to test
24
- * @returns {it is any[]} True if the variable is an array, false otherwise.
25
- */
26
- /*function isArray(it) {
27
- if (typeof Array.isArray === 'function') {
28
- return Array.isArray(it);
29
- }
30
- return Object.prototype.toString.call(it) === '[object Array]';
31
- }*/
32
-
33
- /**
34
- * Translates text to the target language. Automatically chooses the right translation API.
35
- *
36
- * @param {string} text The text to translate
37
- * @param {string} targetLang The target languate
38
- * @param {string} [yandexApiKey] The yandex API key. You can create one for free at https://translate.yandex.com/developers
39
- * @returns {Promise<string>} A promise that resolves to the translated text.
40
- */
41
- /*async function translateText(text, targetLang, yandexApiKey) {
42
- if (targetLang === 'en') {
43
- return text;
44
- } else if (!text) {
45
- return '';
46
- }
47
- if (yandexApiKey) {
48
- return translateYandex(text, targetLang, yandexApiKey);
49
- }
50
- return translateGoogle(text, targetLang);
51
- }*/
52
-
53
- /**
54
- * Translates text with Yandex API
55
- *
56
- * @param {string} text The text to translate
57
- * @param {string} targetLang The target languate
58
- * @param {string} apiKey The yandex API key. You can create one for free at https://translate.yandex.com/developers
59
- * @returns {Promise<string>} A promise that resolves to the translated text.
60
- */
61
- /*async function translateYandex(text, targetLang, apiKey) {
62
- if (targetLang === 'zh-cn') {
63
- targetLang = 'zh';
64
- }
65
- try {
66
- const url = `https://translate.yandex.net/api/v1.5/tr.json/translate?key=${apiKey}&text=${encodeURIComponent(
67
- text,
68
- )}&lang=en-${targetLang}`;
69
- const response = await axios({ url, timeout: 15000 });
70
- if (response.data && response.data.text && isArray(response.data.text)) {
71
- return response.data.text[0];
72
- }
73
- throw new Error('Invalid response for translate request');
74
- } catch (e) {
75
- throw new Error(`Could not translate to "${targetLang}": ${e}`);
76
- }
77
- }*/
78
-
79
- /**
80
- * Translates text with Google API
81
- *
82
- * @param {string} text The text to translate
83
- * @param {string} targetLang The target languate
84
- * @returns {Promise<string>} A promise that resolves to the translated text.
85
- */
86
- /*async function translateGoogle(text, targetLang) {
87
- try {
88
- const url = `http://translate.googleapis.com/translate_a/single?client=gtx&sl=en&tl=${targetLang}&dt=t&q=${encodeURIComponent(
89
- text,
90
- )}&ie=UTF-8&oe=UTF-8`;
91
- const response = await axios({ url, timeout: 15000 });
92
- if (isArray(response.data)) {
93
- // we got a valid response
94
- return response.data[0][0][0];
95
- }
96
- throw new Error('Invalid response for translate request');
97
- } catch (e) {
98
- if (e.response && e.response.status === 429) {
99
- throw new Error(`Could not translate to "${targetLang}": Rate-limited by Google Translate`);
100
- } else {
101
- throw new Error(`Could not translate to "${targetLang}": ${e}`);
102
- }
103
- }
104
- }*/
105
-
106
- /*module.exports = {
107
- isArray,
108
- isObject,
109
- translateText,
110
- };*/