iobroker.metermaster 0.9.3 → 0.9.6

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 (4) hide show
  1. package/README.md +151 -117
  2. package/io-package.json +41 -2
  3. package/main.js +655 -264
  4. package/package.json +5 -4
package/README.md CHANGED
@@ -1,49 +1,104 @@
1
- # ioBroker MeterMaster Adapter
1
+ ![Logo](admin/metermaster.svg)
2
2
 
3
- [![MeterMaster Banner](https://github.com/MPunktBPunkt/ioBroker.metermaster/raw/main/github-banner.svg)](https://github.com/MPunktBPunkt/ioBroker.metermaster)
3
+ # ioBroker.metermaster
4
4
 
5
- [![Version](https://img.shields.io/badge/version-0.9.3-blue.svg)](https://github.com/MPunktBPunkt/ioBroker.metermaster)
6
- [![License](https://img.shields.io/badge/license-MIT-green.svg)](https://github.com/MPunktBPunkt/ioBroker.metermaster/blob/main/LICENSE)
7
- [![Node.js](https://img.shields.io/badge/node-%3E%3D22-brightgreen.svg)](https://nodejs.org)
5
+ [![NPM version](https://img.shields.io/npm/v/iobroker.metermaster.svg)](https://www.npmjs.com/package/iobroker.metermaster)
6
+ ![Number of Installations](https://iobroker.live/badges/metermaster-installed.svg)
7
+ ![Current version in stable repository](https://iobroker.live/badges/metermaster-stable.svg)
8
+ [![Downloads](https://img.shields.io/npm/dm/iobroker.metermaster.svg)](https://www.npmjs.com/package/iobroker.metermaster)
8
9
 
9
- Receives meter readings from the **[MeterMaster Android app](https://play.google.com/store/apps/details?id=com.propertymanagement.metermaster)**, stores them as ioBroker data points, and manages **ESP32 display nodes** for showing meter values on OLED displays. Source code: [GitHub](https://github.com/MPunktBPunkt/MeterMaster).
10
+ [![NPM](https://nodei.co/npm/iobroker.metermaster.png?downloads=true)](https://nodei.co/npm/iobroker.metermaster/)
11
+
12
+ **Bring meter readings from your phone into ioBroker — automatically.**
13
+
14
+ MeterMaster is the bridge between the [MeterMaster Android app](https://play.google.com/store/apps/details?id=com.propertymanagement.metermaster) and your smart home. Record electricity, gas, water or heat meters on your smartphone; the adapter stores them as ioBroker states with correct timestamps and full history — ready for scripts, visualizations and billing workflows.
15
+
16
+ No cloud account. Readings stay in your network.
17
+
18
+ [![Get it on Google Play](https://play.google.com/intl/en_us/badges/static/images/badges/en_badge_web_generic.png)](https://play.google.com/store/apps/details?id=com.propertymanagement.metermaster)
19
+
20
+ ---
21
+
22
+ ## Why use this adapter?
23
+
24
+ | Without MeterMaster | With MeterMaster |
25
+ |---|---|
26
+ | Manual entry into ioBroker or spreadsheets | One tap in the app → state updated |
27
+ | Guessed timestamps | State `ts` = real reading date |
28
+ | No history per meter | Full `readings.history` array |
29
+ | Separate tools for charts/CSV | Built-in Web UI with charts and export |
30
+
31
+ Typical users: homeowners, landlords and property managers who already read meters on site and want those values in ioBroker without retyping.
32
+
33
+ ---
34
+
35
+ ## Quick start
36
+
37
+ 1. Install **MeterMaster** from the official ioBroker adapter list and create an instance.
38
+ 2. Note the HTTP port (default `8089`) and set a Basic Auth password.
39
+ 3. Install the [Android app](https://play.google.com/store/apps/details?id=com.propertymanagement.metermaster) → **Settings → ioBroker → MeterMaster adapter**.
40
+ 4. Enter your ioBroker host, port, username and password → **Test connection**.
41
+ 5. Record a reading in the app — it appears under `metermaster.0.…` and in the Web UI.
42
+
43
+ ```
44
+ Android app ──HTTP──► MeterMaster adapter ──► ioBroker states + history + Web UI
45
+ ```
46
+
47
+ Open the Web UI anytime at `http://{ioBroker-IP}:8089/` (no password required for viewing).
10
48
 
11
49
  ---
12
50
 
13
51
  ## Features
14
52
 
15
- - **HTTP receiver** – accepts readings directly from the app
16
- - **Automatic data points** – states are created automatically on first sync
17
- - **Correct timestamps** – state `ts` reflects the actual reading date
18
- - **History** – each meter keeps a full `readings.history` array
19
- - **Basic Auth** – optional username/password protection
20
- - **Web UI** – built-in browser viewer with 5 tabs (Data, Nodes, Import, Logs, System)
21
- - **Charts & CSV** – history charts, monthly consumption, and CSV export per meter
22
- - **DE/EN** – language switch in the Web UI
23
- - **Import** – app backup (schema 2.0) via the Web UI
24
- - **ESP32 node management** – view and configure registered display nodes
25
- - **Remote control** – control meter selection and LED of ESP32 nodes from the Web UI
53
+ - **HTTP receiver** — accepts readings from the MeterMaster Android app (single or batch)
54
+ - **Automatic states** — house / apartment / meter objects are created on first sync
55
+ - **Correct timestamps** — `readings.latest` uses the actual reading date as state `ts`
56
+ - **Full history** — every meter keeps a `readings.history` JSON array
57
+ - **Basic Auth** — optional username/password protection for write endpoints
58
+ - **Built-in Web UI** — Data, Import, Logs and System tabs in DE/EN
59
+ - **Charts & CSV** — history charts, monthly consumption and per-meter CSV export
60
+ - **Backup import** — restore MeterMaster app backups (schema 2.0) via drag & drop
61
+
62
+ Optional: [ESP32 OLED display nodes](#optional-esp32-display-nodes) can show selected meter values on a small display.
26
63
 
27
64
  ---
28
65
 
29
- ## Screenshots
66
+ ## MeterMaster Android app
30
67
 
31
- The built-in Web UI offers five tabs — overview:
68
+ The adapter is the ioBroker side of [MeterMaster](https://play.google.com/store/apps/details?id=com.propertymanagement.metermaster) — a local-first Android app for utility meters.
69
+
70
+ - Manage properties, apartments and meters (electricity, gas, water, heat, custom)
71
+ - Record readings with date/time and optional photos
72
+ - Consumption charts and annual billing / CSV / HTML export
73
+ - Local storage only — no cloud, no account, no tracking
74
+ - Optional integrations: ioBroker (this adapter), MQTT, Google Sheets, InfluxDB
32
75
 
33
76
  | | |
34
77
  |---|---|
35
- | **Data** – meter cards with consumption KPI, history, chart & CSV | ![Data tab](docs/screenshots/webui-daten.png) |
36
- | **Chart modal** – meter reading (linear time axis) & monthly consumption | ![Chart modal](docs/screenshots/webui-chart.png) |
37
- | **Nodes** – ESP32 status, IP, firmware | ![Nodes tab](docs/screenshots/webui-nodes.png) |
38
- | **Import** – app backup via drag & drop | ![Import tab](docs/screenshots/webui-import.png) |
39
- | **Logs** – real-time log with filter & export | ![Logs tab](docs/screenshots/webui-logs.png) |
40
- | **System** – statistics & version check | ![System tab](docs/screenshots/webui-system.png) |
78
+ | **Google Play** | [MeterMaster](https://play.google.com/store/apps/details?id=com.propertymanagement.metermaster) |
79
+ | **Source & docs** | [MPunktBPunkt/MeterMaster](https://github.com/MPunktBPunkt/MeterMaster) |
80
+
81
+ ---
82
+
83
+ ## Screenshots
84
+
85
+ | Data — meter cards, KPI, history, chart & CSV | Chart — linear time axis & monthly consumption |
86
+ |---|---|
87
+ | ![Data tab](docs/screenshots/webui-daten.png) | ![Chart modal](docs/screenshots/webui-chart.png) |
88
+
89
+ | Import — app backup via drag & drop | Logs — live filter & export |
90
+ |---|---|
91
+ | ![Import tab](docs/screenshots/webui-import.png) | ![Logs tab](docs/screenshots/webui-logs.png) |
92
+
93
+ | System — statistics & version check | Nodes — optional ESP32 status |
94
+ |---|---|
95
+ | ![System tab](docs/screenshots/webui-system.png) | ![Nodes tab](docs/screenshots/webui-nodes.png) |
41
96
 
42
97
  ---
43
98
 
44
99
  ## Installation
45
100
 
46
- Install the adapter from the official ioBroker adapter list:
101
+ Install from the official ioBroker adapter list:
47
102
 
48
103
  1. Open **ioBroker Admin** → **Adapters**
49
104
  2. Search for **MeterMaster**
@@ -56,91 +111,58 @@ iobroker add metermaster
56
111
  iobroker start metermaster
57
112
  ```
58
113
 
59
- Open the firewall if needed: `sudo ufw allow 8089/tcp`
114
+ If the app cannot reach the adapter, open the firewall for the configured port, e.g. `sudo ufw allow 8089/tcp`.
60
115
 
61
- More details: [INSTALLATION.md](INSTALLATION.md)
116
+ More notes: [INSTALLATION.md](INSTALLATION.md)
62
117
 
63
118
  ---
64
119
 
65
120
  ## Instance configuration
66
121
 
67
- After installation → ioBroker Admin → **Adapters → MeterMaster** → create instance:
122
+ **ioBroker Admin → Adapters → MeterMaster → instance settings**
68
123
 
69
124
  | Setting | Default | Description |
70
125
  |---|---|---|
71
126
  | HTTP port | `8089` | Port the adapter listens on |
72
- | Username | `metermaster` | Basic auth username |
73
- | Password | – | Basic auth password |
74
- | Verbose logging | enabled | Show DEBUG entries in log viewer |
75
- | Log buffer | `500` | Max. stored log entries |
76
- | Keep history | `0` | 0 = unlimited |
77
-
78
- ---
79
-
80
- ## MeterMaster Android app
81
-
82
- Capture meters and sync with ioBroker:
83
-
84
- | | |
85
- |---|---|
86
- | **Google Play** | [**MeterMaster**](https://play.google.com/store/apps/details?id=com.propertymanagement.metermaster) – install the app, read meters, and send to the adapter |
87
- | **GitHub** | [**MPunktBPunkt/MeterMaster**](https://github.com/MPunktBPunkt/MeterMaster) – source code, APK build, and documentation |
88
-
89
- [![Get it on Google Play](https://play.google.com/intl/en_us/badges/static/images/badges/en_badge_web_generic.png)](https://play.google.com/store/apps/details?id=com.propertymanagement.metermaster)
127
+ | Username | `metermaster` | Basic Auth username |
128
+ | Password | – | Basic Auth password (set a strong one) |
129
+ | Verbose logging | enabled | Show DEBUG entries in the log viewer |
130
+ | Log buffer | `500` | Maximum stored log entries |
131
+ | Keep history | `0` | `0` = unlimited readings per meter |
90
132
 
91
133
  ---
92
134
 
93
- ## Configure the MeterMaster app
135
+ ## Configure the Android app
94
136
 
95
- **Settings → ioBroker → MeterMaster adapter:**
137
+ **Settings → ioBroker → MeterMaster adapter**
96
138
 
97
139
  | Field | Value |
98
140
  |---|---|
99
141
  | Enable ioBroker | on |
100
- | IP / hostname | IP of the ioBroker server |
101
- | Adapter port | `8089` |
102
- | Username | as configured in the adapter |
103
- | Password | as configured in the adapter |
142
+ | IP / hostname | IP address of the ioBroker server |
143
+ | Adapter port | `8089` (or your configured port) |
144
+ | Username | as in the adapter instance |
145
+ | Password | as in the adapter instance |
104
146
 
105
- "Test connection" should return `MeterMaster adapter reachable ✓`.
147
+ Use **Test connection**. Success looks like: `MeterMaster adapter reachable ✓`
106
148
 
107
149
  ---
108
150
 
109
151
  ## Web UI
110
152
 
111
- Accessible without password:
112
-
113
153
  ```
114
154
  http://{ioBroker-IP}:8089/
115
155
  ```
116
156
 
117
157
  | Tab | Content |
118
158
  |---|---|
119
- | **Data** | All received meters grouped by house/apartment, with history, chart modal, and CSV export |
120
- | **Nodes** | Registered ESP32 nodes: status, IP link, firmware, meter dropdown, LED control |
121
- | **Import** | App backup (JSON schema 2.0) via drag & drop |
122
- | **Logs** | Real-time log with filter, auto-scroll, export |
123
- | **System** | Statistics, GitHub version check, one-click update |
124
-
125
- Screenshots: see [Screenshots](#screenshots) above.
126
-
127
- ---
128
-
129
- ## ESP32 display node
159
+ | **Data** | Meters grouped by house/apartment — history, charts, CSV |
160
+ | **Import** | MeterMaster app backup (JSON schema 2.0) via drag & drop |
161
+ | **Logs** | Real-time log with filter, auto-scroll and export |
162
+ | **System** | Statistics and update check |
163
+ | **Nodes** | Optional ESP32 displays (see below) |
130
164
 
131
- The adapter supports the [MeterMaster ESP32 node](https://github.com/MPunktBPunkt/esp32.MeterMaster) as an OLED display companion.
132
-
133
- ### Flow
134
- 1. ESP32 sends heartbeat every 60 s: `POST :8089/api/register`
135
- 2. Adapter creates `metermaster.0.nodes.{MAC}.*` states automatically
136
- 3. ESP32 polls every 15 s: `GET :8089/api/nodes/{MAC}/config`
137
- 4. Adapter returns config and optional immediate commands (cmd)
138
-
139
- ### Nodes tab
140
- - Online/offline badge (green if heartbeat < 120 s)
141
- - IP as clickable link → opens ESP32 Web UI
142
- - Meter dropdown: assign meter → ESP32 picks it up on next poll
143
- - LED buttons: on/off → immediate command via cmd state
165
+ Language switch: DE / EN in the Web UI.
144
166
 
145
167
  ---
146
168
 
@@ -160,14 +182,9 @@ metermaster.0.
160
182
  │ ├── unit string
161
183
  │ └── typeName string
162
184
  │
163
- └── nodes/{MAC}/
164
- ├── ip string ESP32 IP address
165
- ├── name string Device name
166
- ├── version string Firmware version
167
- ├── lastSeen number Timestamp of last heartbeat (ms)
168
- ├── config string JSON config (adapter writes, ESP32 reads)
169
- ├── configAck string Acknowledgement by ESP32
170
- └── cmd string Immediate command (adapter writes, ESP32 reads+clears)
185
+ └── nodes/{MAC}/ (only if ESP32 nodes are used)
186
+ ├── ip, name, version, lastSeen
187
+ ├── config, configAck, cmd
171
188
  ```
172
189
 
173
190
  ---
@@ -180,63 +197,62 @@ metermaster.0.
180
197
  |---|---|---|
181
198
  | GET | `/` | Web UI |
182
199
  | GET | `/api/version` | Version + GitHub check |
183
- | GET | `/api/stats` | Statistics (readings, uptime, nodes) |
200
+ | GET | `/api/stats` | Statistics |
184
201
  | GET | `/api/data` | All cached readings |
185
- | GET | `/api/logs` | Log buffer (with `?level=&category=&text=` filter) |
186
- | GET | `/api/nodes` | All registered ESP32 nodes |
202
+ | GET | `/api/logs` | Log buffer (`?level=&category=&text=`) |
203
+ | GET | `/api/nodes` | Registered ESP32 nodes |
187
204
  | GET | `/api/discover` | Known meter state IDs |
188
- | POST | `/api/register` | ESP32 heartbeat (no auth required) |
189
- | POST | `/api/update` | Start adapter update |
205
+ | POST | `/api/register` | ESP32 heartbeat |
190
206
 
191
207
  ### With Basic Auth
192
208
 
193
209
  | Method | Path | Description |
194
210
  |---|---|---|
195
211
  | GET | `/api/ping` | Connection test |
196
- | POST | `/api/reading` | Store single reading |
212
+ | POST | `/api/reading` | Store a single reading |
197
213
  | POST | `/api/readings` | Store batch readings |
198
214
  | POST | `/api/import` | Import app backup |
199
- | GET | `/api/nodes/{MAC}/config` | Get config for ESP32 |
200
- | POST | `/api/nodes/{MAC}/config` | Set config for ESP32 |
201
- | POST | `/api/nodes/{MAC}/configAck` | Receive config acknowledgement |
202
- | POST | `/api/nodes/{MAC}/cmd` | Send immediate command (LED, meter) |
215
+ | GET/POST | `/api/nodes/{MAC}/config` | Get / set ESP32 config |
216
+ | POST | `/api/nodes/{MAC}/configAck` | Config acknowledgement |
217
+ | POST | `/api/nodes/{MAC}/cmd` | Immediate command (e.g. LED) |
203
218
 
204
219
  ### Example: single reading
205
220
 
206
- ```
221
+ ```http
207
222
  POST http://host:8089/api/reading
208
223
  Authorization: Basic base64(user:password)
209
224
  Content-Type: application/json
210
225
 
211
226
  {
212
- "house": "MyHouse",
213
- "apartment": "West",
214
- "meter": "HotWater",
215
- "value": 128.75,
216
- "unit": "m³",
217
- "typeName": "HotWater",
227
+ "house": "MyHouse",
228
+ "apartment": "West",
229
+ "meter": "HotWater",
230
+ "value": 128.75,
231
+ "unit": "m³",
232
+ "typeName": "HotWater",
218
233
  "readingDate": "2024-02-12T09:30:00.000Z"
219
234
  }
220
235
  ```
221
236
 
222
- ### Example: immediate command to ESP32
237
+ ---
223
238
 
224
- ```
225
- POST http://host:8089/api/nodes/C8C9A3CB7B08/cmd
226
- Authorization: Basic base64(user:password)
227
- Content-Type: application/json
239
+ ## Optional: ESP32 display nodes
228
240
 
229
- { "ledOn": true }
230
- ```
241
+ As an **optional add-on**, the adapter can manage [MeterMaster ESP32 nodes](https://github.com/MPunktBPunkt/esp32.MeterMaster) that show selected meter values on a small OLED.
242
+
243
+ - Nodes register via heartbeat (`POST /api/register`) and poll config every 15 s
244
+ - States under `metermaster.0.nodes.{MAC}.*`
245
+ - Web UI **Nodes** tab: online status, IP link, meter selection, LED control, firmware
246
+
247
+ You do **not** need an ESP32 to use the adapter or the Android app.
231
248
 
232
249
  ---
233
250
 
234
251
  ## Update
235
252
 
236
- ### Via Web UI (recommended)
237
- `http://IP:8089/` → **System** tab → "Check for updates" → "Install update"
253
+ **Web UI:** `http://IP:8089/` → **System** → Check for updates (install via CLI).
238
254
 
239
- ### Command line
255
+ **Command line:**
240
256
 
241
257
  ```bash
242
258
  iobroker upgrade metermaster
@@ -247,6 +263,21 @@ iobroker restart metermaster.0
247
263
 
248
264
  ## Changelog
249
265
 
266
+
267
+ ### **WORK IN PROGRESS**
268
+ - (ioBroker-Bot) Adapter requires admin >= 7.8.23 now.
269
+
270
+ ### 0.9.4
271
+ - All adapter log messages and API JSON error responses in English
272
+ - State common names and roles corrected (readings channel, date/text/json roles, info.firmware for nodes)
273
+ - Web UI i18n: full DE/EN coverage, English default HTML
274
+ - Config validation: clamped port (1024–65535), logBufferSize (50–5000), keepHistory (0–100000)
275
+ - Removed `/api/update` endpoint and one-click Web UI update (CLI commands card retained)
276
+ - `migrateStateRoles()` uses `getAdapterObjectsAsync` (own adapter states only)
277
+ - Removed dead `houseName` config; import default house is `MyHouse`
278
+ - Fixed redundant state check in stateChange handler
279
+ - `@types/node` pinned to `^22.0.0`
280
+
250
281
  ### 0.9.3
251
282
  - Fix state roles for ioBroker object structure check (repochecker E1008/E1009/E1011)
252
283
  - Migration of existing objects on adapter start
@@ -280,9 +311,12 @@ See [io-package.json](io-package.json) `common.news` for full history. Older ent
280
311
 
281
312
  ---
282
313
 
314
+ [Older changelogs can be found there](CHANGELOG_OLD.md)
315
+
283
316
  ## License
284
317
 
285
- Copyright (c) 2026 MPunktBPunkt
318
+ MIT License
286
319
 
287
- MIT License – see [LICENSE](LICENSE) for the full license text.
320
+ Copyright (c) 2026 MPunktBPunkt
288
321
 
322
+ See [LICENSE](LICENSE) for the full license text.
package/io-package.json CHANGED
@@ -1,8 +1,47 @@
1
1
  {
2
2
  "common": {
3
3
  "name": "metermaster",
4
- "version": "0.9.3",
4
+ "version": "0.9.6",
5
5
  "news": {
6
+ "0.9.6": {
7
+ "en": "Assign display nodes via chips on meter cards in the Data tab",
8
+ "de": "Anzeige-Nodes per Chips auf den Zähler-Kacheln im Daten-Tab zuweisen",
9
+ "ru": "Assign nodes via chips on meter cards",
10
+ "pt": "Assign nodes via chips on meter cards",
11
+ "nl": "Nodes toewijzen via chips op meterkarten",
12
+ "fr": "Assigner des nodes via des chips sur les cartes compteur",
13
+ "it": "Assegna node tramite chip sulle card contatore",
14
+ "es": "Asignar nodes mediante chips en las tarjetas de contador",
15
+ "pl": "Przypisywanie node przez chipy na kartach liczników",
16
+ "uk": "Призначення node через чіпи на картках лічильників",
17
+ "zh-cn": "在数据页计量表卡片上通过芯片分配显示节点"
18
+ },
19
+ "0.9.5": {
20
+ "en": "Correct history on re-sync; edit values in Web UI; print chart and apartment/house latest readings",
21
+ "de": "Historie bei erneutem Sync korrigieren; Werte in der Web-UI bearbeiten; Chart sowie Wohnungs-/Haus-Stände drucken",
22
+ "ru": "Correction of history; Web UI edit; print chart and readings",
23
+ "pt": "Correct history; Web UI edit; print",
24
+ "nl": "History corrigeren; Web UI edit; printen",
25
+ "fr": "Corriger l'historique; édition Web UI; impression",
26
+ "it": "Correggi cronologia; modifica Web UI; stampa",
27
+ "es": "Corregir historial; edición Web UI; imprimir",
28
+ "pl": "Korekta historii; edycja Web UI; druk",
29
+ "uk": "Корекція історії; редагування Web UI; друк",
30
+ "zh-cn": "更正历史记录;Web UI 编辑;打印图表与读数"
31
+ },
32
+ "0.9.4": {
33
+ "en": "Review fixes: English logs/states/API errors, Web UI i18n, config validation, removed /api/update",
34
+ "de": "Review-Fixes: Englische Logs/States/API-Fehler, Web-UI-i18n, Config-Validierung, /api/update entfernt",
35
+ "ru": "Исправления review: английские логи/states/API, i18n Web UI, валидация config, удалён /api/update",
36
+ "pt": "Correções de review: logs/states/erros API em inglês, i18n Web UI, validação config, removido /api/update",
37
+ "nl": "Review-fixes: Engelse logs/states/API-fouten, Web UI i18n, config-validatie, /api/update verwijderd",
38
+ "fr": "Corrections review : logs/states/erreurs API en anglais, i18n Web UI, validation config, /api/update supprimé",
39
+ "it": "Correzioni review: log/states/errori API in inglese, i18n Web UI, validazione config, rimosso /api/update",
40
+ "es": "Correcciones de review: logs/states/errores API en inglés, i18n Web UI, validación config, eliminado /api/update",
41
+ "pl": "Poprawki review: angielskie logi/states/błędy API, i18n Web UI, walidacja config, usunięto /api/update",
42
+ "uk": "Виправлення review: англійські логи/states/API, i18n Web UI, валідація config, видалено /api/update",
43
+ "zh-cn": "审查修复:英文日志/states/API 错误、Web UI 国际化、配置验证、移除 /api/update"
44
+ },
6
45
  "0.9.3": {
7
46
  "en": "Fix state roles for ioBroker object structure check (date, text, json, info.firmware)",
8
47
  "de": "State-Rollen für ioBroker-Objektstruktur-Prüfung korrigiert (date, text, json, info.firmware)",
@@ -104,7 +143,7 @@
104
143
  ],
105
144
  "globalDependencies": [
106
145
  {
107
- "admin": ">=7.6.20"
146
+ "admin": ">=7.8.23"
108
147
  }
109
148
  ]
110
149
  },