iobroker.poolcontrol 1.3.10 → 1.3.11

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.
@@ -0,0 +1,889 @@
1
+ 'use strict';
2
+
3
+ /**
4
+ * chemistryTdsStates.js
5
+ * -------------------------------------------------------------
6
+ * States for the TDS evaluation area.
7
+ *
8
+ * Scope:
9
+ * - TDS input via manual value or external ioBroker state
10
+ * - Measurement location handling
11
+ * - Reference value
12
+ * - 24h / 7d / 30d trend structure
13
+ * - Text / HTML / JSON outputs
14
+ *
15
+ * No automatic dosing.
16
+ * No pump control.
17
+ * -------------------------------------------------------------
18
+ */
19
+
20
+ async function createChannel(adapter, id, name) {
21
+ await adapter.setObjectNotExistsAsync(id, {
22
+ type: 'channel',
23
+ common: { name },
24
+ native: {},
25
+ });
26
+ }
27
+
28
+ async function createState(adapter, id, common) {
29
+ await adapter.setObjectNotExistsAsync(id, {
30
+ type: 'state',
31
+ common,
32
+ native: {},
33
+ });
34
+ }
35
+
36
+ /**
37
+ * @param {import('iobroker').Adapter} adapter - ioBroker adapter instance
38
+ */
39
+ async function createChemistryTdsStates(adapter) {
40
+ adapter.log.debug('[chemistryTdsStates] Initialization started');
41
+
42
+ await createChannel(adapter, 'chemistry', {
43
+ en: 'Chemistry',
44
+ de: 'Chemie',
45
+ });
46
+
47
+ await createChannel(adapter, 'chemistry.tds', {
48
+ en: 'TDS evaluation',
49
+ de: 'TDS-Auswertung',
50
+ });
51
+
52
+ await createState(adapter, 'chemistry.tds.enabled', {
53
+ name: {
54
+ en: 'Enable TDS evaluation',
55
+ de: 'TDS-Auswertung aktivieren',
56
+ },
57
+ desc: {
58
+ en: 'Enables the TDS evaluation. No automatic control is performed.',
59
+ de: 'Aktiviert die TDS-Auswertung. Es erfolgt keine automatische Steuerung.',
60
+ },
61
+ type: 'boolean',
62
+ role: 'switch',
63
+ read: true,
64
+ write: true,
65
+ def: false,
66
+ persist: true,
67
+ });
68
+
69
+ // -------------------------------------------------------------
70
+ // Input
71
+ // -------------------------------------------------------------
72
+ await createChannel(adapter, 'chemistry.tds.input', {
73
+ en: 'Input',
74
+ de: 'Eingang',
75
+ });
76
+
77
+ await createState(adapter, 'chemistry.tds.input.source_mode', {
78
+ name: {
79
+ en: 'Source mode',
80
+ de: 'Quellenmodus',
81
+ },
82
+ desc: {
83
+ en: 'Defines how the TDS value is provided.',
84
+ de: 'Legt fest, wie der TDS-Wert bereitgestellt wird.',
85
+ },
86
+ type: 'string',
87
+ role: 'level',
88
+ read: true,
89
+ write: true,
90
+ def: 'disabled',
91
+ states: {
92
+ disabled: 'disabled',
93
+ manual: 'manual',
94
+ state: 'state',
95
+ },
96
+ persist: true,
97
+ });
98
+
99
+ await createState(adapter, 'chemistry.tds.input.source_state_id', {
100
+ name: {
101
+ en: 'Source state ID',
102
+ de: 'Quell-Datenpunkt',
103
+ },
104
+ desc: {
105
+ en: 'External ioBroker state ID that provides the TDS value.',
106
+ de: 'Externer ioBroker-Datenpunkt, der den TDS-Wert liefert.',
107
+ },
108
+ type: 'string',
109
+ role: 'text',
110
+ read: true,
111
+ write: true,
112
+ def: '',
113
+ persist: true,
114
+ });
115
+
116
+ await createState(adapter, 'chemistry.tds.input.manual_value', {
117
+ name: {
118
+ en: 'Manual TDS value',
119
+ de: 'Manueller TDS-Wert',
120
+ },
121
+ desc: {
122
+ en: 'Manually entered TDS value in ppm.',
123
+ de: 'Manuell eingetragener TDS-Wert in ppm.',
124
+ },
125
+ type: 'number',
126
+ role: 'value',
127
+ read: true,
128
+ write: true,
129
+ def: 0,
130
+ min: 0,
131
+ unit: 'ppm',
132
+ persist: true,
133
+ });
134
+
135
+ await createState(adapter, 'chemistry.tds.input.current_value', {
136
+ name: {
137
+ en: 'Current TDS value',
138
+ de: 'Aktueller TDS-Wert',
139
+ },
140
+ desc: {
141
+ en: 'Current TDS value received or used by PoolControl.',
142
+ de: 'Aktueller von PoolControl empfangener oder verwendeter TDS-Wert.',
143
+ },
144
+ type: 'number',
145
+ role: 'value',
146
+ read: true,
147
+ write: false,
148
+ def: 0,
149
+ min: 0,
150
+ unit: 'ppm',
151
+ persist: true,
152
+ });
153
+
154
+ await createState(adapter, 'chemistry.tds.input.source_valid', {
155
+ name: {
156
+ en: 'Source valid',
157
+ de: 'Quelle gültig',
158
+ },
159
+ desc: {
160
+ en: 'Shows whether the configured TDS source exists and can be used.',
161
+ de: 'Zeigt an, ob die konfigurierte TDS-Quelle existiert und genutzt werden kann.',
162
+ },
163
+ type: 'boolean',
164
+ role: 'indicator',
165
+ read: true,
166
+ write: false,
167
+ def: false,
168
+ persist: true,
169
+ });
170
+
171
+ await createState(adapter, 'chemistry.tds.input.value_valid', {
172
+ name: {
173
+ en: 'Value valid',
174
+ de: 'Wert gültig',
175
+ },
176
+ desc: {
177
+ en: 'Shows whether the current TDS value is plausible.',
178
+ de: 'Zeigt an, ob der aktuelle TDS-Wert plausibel ist.',
179
+ },
180
+ type: 'boolean',
181
+ role: 'indicator',
182
+ read: true,
183
+ write: false,
184
+ def: false,
185
+ persist: true,
186
+ });
187
+
188
+ await createState(adapter, 'chemistry.tds.input.source_status', {
189
+ name: {
190
+ en: 'Source status',
191
+ de: 'Quellenstatus',
192
+ },
193
+ desc: {
194
+ en: 'Readable status of the TDS input source.',
195
+ de: 'Lesbarer Status der TDS-Eingangsquelle.',
196
+ },
197
+ type: 'string',
198
+ role: 'text',
199
+ read: true,
200
+ write: false,
201
+ def: '',
202
+ persist: true,
203
+ });
204
+
205
+ await createState(adapter, 'chemistry.tds.input.last_value_at', {
206
+ name: {
207
+ en: 'Last value time',
208
+ de: 'Zeitpunkt des letzten Werts',
209
+ },
210
+ desc: {
211
+ en: 'Readable date and time when the last TDS value was received.',
212
+ de: 'Lesbares Datum und Uhrzeit, wann der letzte TDS-Wert empfangen wurde.',
213
+ },
214
+ type: 'string',
215
+ role: 'value.time',
216
+ read: true,
217
+ write: false,
218
+ def: '',
219
+ persist: true,
220
+ });
221
+
222
+ await createState(adapter, 'chemistry.tds.input.last_valid_value', {
223
+ name: {
224
+ en: 'Last valid TDS value',
225
+ de: 'Letzter gültiger TDS-Wert',
226
+ },
227
+ desc: {
228
+ en: 'Last valid and plausible TDS value.',
229
+ de: 'Letzter gültiger und plausibler TDS-Wert.',
230
+ },
231
+ type: 'number',
232
+ role: 'value',
233
+ read: true,
234
+ write: false,
235
+ def: 0,
236
+ min: 0,
237
+ unit: 'ppm',
238
+ persist: true,
239
+ });
240
+
241
+ await createState(adapter, 'chemistry.tds.input.last_valid_value_at', {
242
+ name: {
243
+ en: 'Last valid value time',
244
+ de: 'Zeitpunkt des letzten gültigen Werts',
245
+ },
246
+ desc: {
247
+ en: 'Readable date and time of the last valid TDS value.',
248
+ de: 'Lesbares Datum und Uhrzeit des letzten gültigen TDS-Werts.',
249
+ },
250
+ type: 'string',
251
+ role: 'value.time',
252
+ read: true,
253
+ write: false,
254
+ def: '',
255
+ persist: true,
256
+ });
257
+
258
+ await createState(adapter, 'chemistry.tds.input.previous_value', {
259
+ name: {
260
+ en: 'Previous valid TDS value',
261
+ de: 'Vorheriger gültiger TDS-Wert',
262
+ },
263
+ desc: {
264
+ en: 'Valid TDS value before the latest valid value.',
265
+ de: 'Gültiger TDS-Wert vor dem letzten gültigen Wert.',
266
+ },
267
+ type: 'number',
268
+ role: 'value',
269
+ read: true,
270
+ write: false,
271
+ def: 0,
272
+ min: 0,
273
+ unit: 'ppm',
274
+ persist: true,
275
+ });
276
+
277
+ await createState(adapter, 'chemistry.tds.input.previous_value_at', {
278
+ name: {
279
+ en: 'Previous valid value time',
280
+ de: 'Zeitpunkt des vorherigen gültigen Werts',
281
+ },
282
+ desc: {
283
+ en: 'Readable date and time of the previous valid TDS value.',
284
+ de: 'Lesbares Datum und Uhrzeit des vorherigen gültigen TDS-Werts.',
285
+ },
286
+ type: 'string',
287
+ role: 'value.time',
288
+ read: true,
289
+ write: false,
290
+ def: '',
291
+ persist: true,
292
+ });
293
+
294
+ await createState(adapter, 'chemistry.tds.input.minutes_since_previous_value', {
295
+ name: {
296
+ en: 'Minutes since previous value',
297
+ de: 'Minuten seit vorherigem Wert',
298
+ },
299
+ desc: {
300
+ en: 'Time difference between the last two valid TDS values.',
301
+ de: 'Zeitdifferenz zwischen den letzten beiden gültigen TDS-Werten.',
302
+ },
303
+ type: 'number',
304
+ role: 'value',
305
+ read: true,
306
+ write: false,
307
+ def: 0,
308
+ unit: 'min',
309
+ persist: true,
310
+ });
311
+
312
+ // -------------------------------------------------------------
313
+ // Measurement
314
+ // -------------------------------------------------------------
315
+ await createChannel(adapter, 'chemistry.tds.measurement', {
316
+ en: 'Measurement',
317
+ de: 'Messung',
318
+ });
319
+
320
+ await createState(adapter, 'chemistry.tds.measurement.location', {
321
+ name: {
322
+ en: 'Measurement location',
323
+ de: 'Messort',
324
+ },
325
+ desc: {
326
+ en: 'Defines where the TDS value is measured.',
327
+ de: 'Legt fest, wo der TDS-Wert gemessen wird.',
328
+ },
329
+ type: 'string',
330
+ role: 'level',
331
+ read: true,
332
+ write: true,
333
+ def: 'manual',
334
+ states: {
335
+ manual: 'manual',
336
+ pool: 'pool',
337
+ measurement_cell: 'measurement_cell',
338
+ pipe_section: 'pipe_section',
339
+ },
340
+ persist: true,
341
+ });
342
+
343
+ await createState(adapter, 'chemistry.tds.measurement.flow_required', {
344
+ name: {
345
+ en: 'Flow required',
346
+ de: 'Durchfluss erforderlich',
347
+ },
348
+ desc: {
349
+ en: 'If enabled, values are only evaluated when the pool pump is running.',
350
+ de: 'Wenn aktiv, werden Werte nur bei laufender Poolpumpe ausgewertet.',
351
+ },
352
+ type: 'boolean',
353
+ role: 'switch',
354
+ read: true,
355
+ write: true,
356
+ def: false,
357
+ persist: true,
358
+ });
359
+
360
+ await createState(adapter, 'chemistry.tds.measurement.stabilization_time_sec', {
361
+ name: {
362
+ en: 'Stabilization time',
363
+ de: 'Stabilisierungszeit',
364
+ },
365
+ desc: {
366
+ en: 'Delay after pump start before values from a measurement section are evaluated.',
367
+ de: 'Wartezeit nach Pumpenstart, bevor Werte aus einer Messstrecke ausgewertet werden.',
368
+ },
369
+ type: 'number',
370
+ role: 'level',
371
+ read: true,
372
+ write: true,
373
+ def: 120,
374
+ min: 0,
375
+ unit: 's',
376
+ persist: true,
377
+ });
378
+
379
+ await createState(adapter, 'chemistry.tds.measurement.pump_running', {
380
+ name: {
381
+ en: 'Pump running',
382
+ de: 'Pumpe läuft',
383
+ },
384
+ desc: {
385
+ en: 'Shows whether the pool pump is currently detected as running.',
386
+ de: 'Zeigt an, ob die Poolpumpe aktuell als laufend erkannt wird.',
387
+ },
388
+ type: 'boolean',
389
+ role: 'indicator',
390
+ read: true,
391
+ write: false,
392
+ def: false,
393
+ persist: true,
394
+ });
395
+
396
+ await createState(adapter, 'chemistry.tds.measurement.stabilized', {
397
+ name: {
398
+ en: 'Measurement stabilized',
399
+ de: 'Messung stabilisiert',
400
+ },
401
+ desc: {
402
+ en: 'Shows whether the stabilization time after pump start has elapsed.',
403
+ de: 'Zeigt an, ob die Stabilisierungszeit nach Pumpenstart abgelaufen ist.',
404
+ },
405
+ type: 'boolean',
406
+ role: 'indicator',
407
+ read: true,
408
+ write: false,
409
+ def: false,
410
+ persist: true,
411
+ });
412
+
413
+ await createState(adapter, 'chemistry.tds.measurement.allowed', {
414
+ name: {
415
+ en: 'Measurement allowed',
416
+ de: 'Messung erlaubt',
417
+ },
418
+ desc: {
419
+ en: 'Shows whether TDS values are currently allowed to be evaluated.',
420
+ de: 'Zeigt an, ob TDS-Werte aktuell ausgewertet werden dürfen.',
421
+ },
422
+ type: 'boolean',
423
+ role: 'indicator',
424
+ read: true,
425
+ write: false,
426
+ def: false,
427
+ persist: true,
428
+ });
429
+
430
+ await createState(adapter, 'chemistry.tds.measurement.ignored_reason', {
431
+ name: {
432
+ en: 'Ignored reason',
433
+ de: 'Ignorierter Grund',
434
+ },
435
+ desc: {
436
+ en: 'Reason why the current TDS value is not evaluated.',
437
+ de: 'Grund, warum der aktuelle TDS-Wert nicht ausgewertet wird.',
438
+ },
439
+ type: 'string',
440
+ role: 'text',
441
+ read: true,
442
+ write: false,
443
+ def: '',
444
+ persist: true,
445
+ });
446
+
447
+ // -------------------------------------------------------------
448
+ // Reference
449
+ // -------------------------------------------------------------
450
+ await createChannel(adapter, 'chemistry.tds.reference', {
451
+ en: 'Reference',
452
+ de: 'Referenz',
453
+ });
454
+
455
+ await createState(adapter, 'chemistry.tds.reference.initial_value', {
456
+ name: {
457
+ en: 'Initial reference value',
458
+ de: 'Initialer Referenzwert',
459
+ },
460
+ desc: {
461
+ en: 'Reference TDS value after fresh water, refill or manually selected start point.',
462
+ de: 'TDS-Referenzwert nach Frischwasser, Neubefüllung oder bewusst gesetztem Startpunkt.',
463
+ },
464
+ type: 'number',
465
+ role: 'value',
466
+ read: true,
467
+ write: true,
468
+ def: 0,
469
+ min: 0,
470
+ unit: 'ppm',
471
+ persist: true,
472
+ });
473
+
474
+ await createState(adapter, 'chemistry.tds.reference.initial_value_at', {
475
+ name: {
476
+ en: 'Initial reference time',
477
+ de: 'Zeitpunkt des Referenzwerts',
478
+ },
479
+ desc: {
480
+ en: 'Readable date and time when the initial reference value was set.',
481
+ de: 'Lesbares Datum und Uhrzeit, wann der Referenzwert gesetzt wurde.',
482
+ },
483
+ type: 'string',
484
+ role: 'value.time',
485
+ read: true,
486
+ write: false,
487
+ def: '',
488
+ persist: true,
489
+ });
490
+
491
+ await createState(adapter, 'chemistry.tds.reference.initial_set', {
492
+ name: {
493
+ en: 'Initial reference set',
494
+ de: 'Referenzwert gesetzt',
495
+ },
496
+ desc: {
497
+ en: 'Shows whether an initial reference value is available.',
498
+ de: 'Zeigt an, ob ein initialer Referenzwert vorhanden ist.',
499
+ },
500
+ type: 'boolean',
501
+ role: 'indicator',
502
+ read: true,
503
+ write: false,
504
+ def: false,
505
+ persist: true,
506
+ });
507
+
508
+ await createState(adapter, 'chemistry.tds.reference.reset_initial_reference', {
509
+ name: {
510
+ en: 'Set current value as reference',
511
+ de: 'Aktuellen Wert als Referenz setzen',
512
+ },
513
+ desc: {
514
+ en: 'Sets the current valid TDS value as new initial reference value.',
515
+ de: 'Setzt den aktuellen gültigen TDS-Wert als neuen initialen Referenzwert.',
516
+ },
517
+ type: 'boolean',
518
+ role: 'button',
519
+ read: true,
520
+ write: true,
521
+ def: false,
522
+ });
523
+
524
+ await createState(adapter, 'chemistry.tds.reference.delta_since_initial', {
525
+ name: {
526
+ en: 'Delta since initial reference',
527
+ de: 'Differenz seit Referenzwert',
528
+ },
529
+ desc: {
530
+ en: 'Difference between current TDS value and initial reference value.',
531
+ de: 'Differenz zwischen aktuellem TDS-Wert und initialem Referenzwert.',
532
+ },
533
+ type: 'number',
534
+ role: 'value',
535
+ read: true,
536
+ write: false,
537
+ def: 0,
538
+ unit: 'ppm',
539
+ persist: true,
540
+ });
541
+
542
+ // -------------------------------------------------------------
543
+ // Trend
544
+ // -------------------------------------------------------------
545
+ await createChannel(adapter, 'chemistry.tds.trend', {
546
+ en: 'Trend',
547
+ de: 'Trend',
548
+ });
549
+
550
+ const trendStates = [
551
+ ['reference_24h_value', '24h reference value', '24h-Referenzwert'],
552
+ ['reference_7d_value', '7 day reference value', '7-Tage-Referenzwert'],
553
+ ['reference_30d_value', '30 day reference value', '30-Tage-Referenzwert'],
554
+ ['delta_24h', '24h delta', '24h-Differenz'],
555
+ ['delta_7d', '7 day delta', '7-Tage-Differenz'],
556
+ ['delta_30d', '30 day delta', '30-Tage-Differenz'],
557
+ ];
558
+
559
+ for (const [stateId, enName, deName] of trendStates) {
560
+ await createState(adapter, `chemistry.tds.trend.${stateId}`, {
561
+ name: {
562
+ en: enName,
563
+ de: deName,
564
+ },
565
+ type: 'number',
566
+ role: 'value',
567
+ read: true,
568
+ write: false,
569
+ def: 0,
570
+ unit: 'ppm',
571
+ persist: true,
572
+ });
573
+ }
574
+
575
+ const trendTimeStates = [
576
+ ['reference_24h_at', '24h reference time', 'Zeitpunkt des 24h-Referenzwerts'],
577
+ ['reference_7d_at', '7 day reference time', 'Zeitpunkt des 7-Tage-Referenzwerts'],
578
+ ['reference_30d_at', '30 day reference time', 'Zeitpunkt des 30-Tage-Referenzwerts'],
579
+ ];
580
+
581
+ for (const [stateId, enName, deName] of trendTimeStates) {
582
+ await createState(adapter, `chemistry.tds.trend.${stateId}`, {
583
+ name: {
584
+ en: enName,
585
+ de: deName,
586
+ },
587
+ type: 'string',
588
+ role: 'value.time',
589
+ read: true,
590
+ write: false,
591
+ def: '',
592
+ persist: true,
593
+ });
594
+ }
595
+
596
+ await createState(adapter, 'chemistry.tds.trend.direction', {
597
+ name: {
598
+ en: 'Trend direction',
599
+ de: 'Trendrichtung',
600
+ },
601
+ desc: {
602
+ en: 'Overall trend direction: stable, rising, falling or not enough data.',
603
+ de: 'Gesamte Trendrichtung: stabil, steigend, fallend oder noch nicht genug Daten.',
604
+ },
605
+ type: 'string',
606
+ role: 'text',
607
+ read: true,
608
+ write: false,
609
+ def: 'not_enough_data',
610
+ persist: true,
611
+ });
612
+
613
+ await createState(adapter, 'chemistry.tds.trend.status', {
614
+ name: {
615
+ en: 'Trend status',
616
+ de: 'Trendstatus',
617
+ },
618
+ desc: {
619
+ en: 'Readable status of the TDS trend development.',
620
+ de: 'Lesbarer Status der TDS-Trendentwicklung.',
621
+ },
622
+ type: 'string',
623
+ role: 'text',
624
+ read: true,
625
+ write: false,
626
+ def: 'not_enough_data',
627
+ persist: true,
628
+ });
629
+
630
+ // -------------------------------------------------------------
631
+ // Evaluation
632
+ // -------------------------------------------------------------
633
+ await createChannel(adapter, 'chemistry.tds.evaluation', {
634
+ en: 'Evaluation',
635
+ de: 'Auswertung',
636
+ });
637
+
638
+ await createState(adapter, 'chemistry.tds.evaluation.absolute_level', {
639
+ name: {
640
+ en: 'Absolute level',
641
+ de: 'Absolutwert-Einstufung',
642
+ },
643
+ desc: {
644
+ en: 'Classification of the current absolute TDS value.',
645
+ de: 'Einordnung des aktuellen absoluten TDS-Werts.',
646
+ },
647
+ type: 'string',
648
+ role: 'text',
649
+ read: true,
650
+ write: false,
651
+ def: '',
652
+ persist: true,
653
+ });
654
+
655
+ await createState(adapter, 'chemistry.tds.evaluation.reference_level', {
656
+ name: {
657
+ en: 'Reference level',
658
+ de: 'Referenz-Einstufung',
659
+ },
660
+ desc: {
661
+ en: 'Classification of the delta since the initial reference value.',
662
+ de: 'Einordnung der Differenz seit dem initialen Referenzwert.',
663
+ },
664
+ type: 'string',
665
+ role: 'text',
666
+ read: true,
667
+ write: false,
668
+ def: '',
669
+ persist: true,
670
+ });
671
+
672
+ await createState(adapter, 'chemistry.tds.evaluation.overall_status', {
673
+ name: {
674
+ en: 'Overall status',
675
+ de: 'Gesamtstatus',
676
+ },
677
+ desc: {
678
+ en: 'Overall TDS evaluation status.',
679
+ de: 'Gesamtstatus der TDS-Auswertung.',
680
+ },
681
+ type: 'string',
682
+ role: 'text',
683
+ read: true,
684
+ write: false,
685
+ def: 'disabled',
686
+ persist: true,
687
+ });
688
+
689
+ await createState(adapter, 'chemistry.tds.evaluation.recommendation', {
690
+ name: {
691
+ en: 'Recommendation',
692
+ de: 'Empfehlung',
693
+ },
694
+ desc: {
695
+ en: 'Readable recommendation for the user. No automatic control.',
696
+ de: 'Lesbare Empfehlung für den Nutzer. Keine automatische Steuerung.',
697
+ },
698
+ type: 'string',
699
+ role: 'text',
700
+ read: true,
701
+ write: false,
702
+ def: '',
703
+ persist: true,
704
+ });
705
+
706
+ await createState(adapter, 'chemistry.tds.evaluation.action_required', {
707
+ name: {
708
+ en: 'Action required',
709
+ de: 'Handlung erforderlich',
710
+ },
711
+ desc: {
712
+ en: 'Shows whether user action is recommended.',
713
+ de: 'Zeigt an, ob eine Handlung durch den Nutzer empfohlen wird.',
714
+ },
715
+ type: 'boolean',
716
+ role: 'indicator',
717
+ read: true,
718
+ write: false,
719
+ def: false,
720
+ persist: true,
721
+ });
722
+
723
+ // -------------------------------------------------------------
724
+ // History
725
+ // -------------------------------------------------------------
726
+ await createChannel(adapter, 'chemistry.tds.history', {
727
+ en: 'History',
728
+ de: 'Historie',
729
+ });
730
+
731
+ await createState(adapter, 'chemistry.tds.history.samples_json', {
732
+ name: {
733
+ en: 'Samples JSON',
734
+ de: 'Messwerte JSON',
735
+ },
736
+ desc: {
737
+ en: 'Internal JSON list of valid TDS samples for up to 30 days.',
738
+ de: 'Interne JSON-Liste gültiger TDS-Messpunkte für bis zu 30 Tage.',
739
+ },
740
+ type: 'string',
741
+ role: 'json',
742
+ read: true,
743
+ write: false,
744
+ def: '[]',
745
+ persist: true,
746
+ });
747
+
748
+ await createState(adapter, 'chemistry.tds.history.samples_count', {
749
+ name: {
750
+ en: 'Samples count',
751
+ de: 'Anzahl Messwerte',
752
+ },
753
+ desc: {
754
+ en: 'Number of stored valid TDS samples.',
755
+ de: 'Anzahl gespeicherter gültiger TDS-Messpunkte.',
756
+ },
757
+ type: 'number',
758
+ role: 'value',
759
+ read: true,
760
+ write: false,
761
+ def: 0,
762
+ persist: true,
763
+ });
764
+
765
+ await createState(adapter, 'chemistry.tds.history.oldest_sample_at', {
766
+ name: {
767
+ en: 'Oldest sample time',
768
+ de: 'Ältester Messwert',
769
+ },
770
+ type: 'string',
771
+ role: 'value.time',
772
+ read: true,
773
+ write: false,
774
+ def: '',
775
+ persist: true,
776
+ });
777
+
778
+ await createState(adapter, 'chemistry.tds.history.newest_sample_at', {
779
+ name: {
780
+ en: 'Newest sample time',
781
+ de: 'Neuester Messwert',
782
+ },
783
+ type: 'string',
784
+ role: 'value.time',
785
+ read: true,
786
+ write: false,
787
+ def: '',
788
+ persist: true,
789
+ });
790
+
791
+ // -------------------------------------------------------------
792
+ // Outputs
793
+ // -------------------------------------------------------------
794
+ await createChannel(adapter, 'chemistry.tds.outputs', {
795
+ en: 'Outputs',
796
+ de: 'Ausgaben',
797
+ });
798
+
799
+ await createState(adapter, 'chemistry.tds.outputs.summary_text', {
800
+ name: {
801
+ en: 'Summary text',
802
+ de: 'Zusammenfassung Text',
803
+ },
804
+ desc: {
805
+ en: 'Readable TDS summary text.',
806
+ de: 'Lesbare TDS-Zusammenfassung.',
807
+ },
808
+ type: 'string',
809
+ role: 'text',
810
+ read: true,
811
+ write: false,
812
+ def: '',
813
+ persist: true,
814
+ });
815
+
816
+ await createState(adapter, 'chemistry.tds.outputs.summary_html', {
817
+ name: {
818
+ en: 'Summary HTML',
819
+ de: 'Zusammenfassung HTML',
820
+ },
821
+ desc: {
822
+ en: 'HTML summary for VIS or widgets.',
823
+ de: 'HTML-Zusammenfassung für VIS oder Widgets.',
824
+ },
825
+ type: 'string',
826
+ role: 'html',
827
+ read: true,
828
+ write: false,
829
+ def: '',
830
+ persist: true,
831
+ });
832
+
833
+ await createState(adapter, 'chemistry.tds.outputs.summary_json', {
834
+ name: {
835
+ en: 'Summary JSON',
836
+ de: 'Zusammenfassung JSON',
837
+ },
838
+ desc: {
839
+ en: 'Structured TDS summary as JSON.',
840
+ de: 'Strukturierte TDS-Zusammenfassung als JSON.',
841
+ },
842
+ type: 'string',
843
+ role: 'json',
844
+ read: true,
845
+ write: false,
846
+ def: '',
847
+ persist: true,
848
+ });
849
+
850
+ // -------------------------------------------------------------
851
+ // Debug
852
+ // -------------------------------------------------------------
853
+ await createChannel(adapter, 'chemistry.tds.debug', {
854
+ en: 'Debug',
855
+ de: 'Debug',
856
+ });
857
+
858
+ await createState(adapter, 'chemistry.tds.debug.last_update', {
859
+ name: {
860
+ en: 'Last update',
861
+ de: 'Letzte Aktualisierung',
862
+ },
863
+ type: 'string',
864
+ role: 'value.time',
865
+ read: true,
866
+ write: false,
867
+ def: '',
868
+ persist: true,
869
+ });
870
+
871
+ await createState(adapter, 'chemistry.tds.debug.last_reason', {
872
+ name: {
873
+ en: 'Last reason',
874
+ de: 'Letzter Grund',
875
+ },
876
+ type: 'string',
877
+ role: 'text',
878
+ read: true,
879
+ write: false,
880
+ def: '',
881
+ persist: true,
882
+ });
883
+
884
+ adapter.log.debug('[chemistryTdsStates] Initialization completed');
885
+ }
886
+
887
+ module.exports = {
888
+ createChemistryTdsStates,
889
+ };