@bota-dev/react-native-sdk 0.0.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.
Files changed (177) hide show
  1. package/README.md +279 -0
  2. package/lib/commonjs/BotaClient.js +223 -0
  3. package/lib/commonjs/BotaClient.js.map +1 -0
  4. package/lib/commonjs/ble/BleManager.js +494 -0
  5. package/lib/commonjs/ble/BleManager.js.map +1 -0
  6. package/lib/commonjs/ble/constants.js +166 -0
  7. package/lib/commonjs/ble/constants.js.map +1 -0
  8. package/lib/commonjs/ble/index.js +54 -0
  9. package/lib/commonjs/ble/index.js.map +1 -0
  10. package/lib/commonjs/ble/parsers.js +345 -0
  11. package/lib/commonjs/ble/parsers.js.map +1 -0
  12. package/lib/commonjs/index.js +81 -0
  13. package/lib/commonjs/index.js.map +1 -0
  14. package/lib/commonjs/managers/DeviceManager.js +437 -0
  15. package/lib/commonjs/managers/DeviceManager.js.map +1 -0
  16. package/lib/commonjs/managers/OTAManager.js +227 -0
  17. package/lib/commonjs/managers/OTAManager.js.map +1 -0
  18. package/lib/commonjs/managers/RecordingManager.js +384 -0
  19. package/lib/commonjs/managers/RecordingManager.js.map +1 -0
  20. package/lib/commonjs/managers/index.js +27 -0
  21. package/lib/commonjs/managers/index.js.map +1 -0
  22. package/lib/commonjs/models/Device.js +2 -0
  23. package/lib/commonjs/models/Device.js.map +1 -0
  24. package/lib/commonjs/models/Recording.js +2 -0
  25. package/lib/commonjs/models/Recording.js.map +1 -0
  26. package/lib/commonjs/models/Status.js +6 -0
  27. package/lib/commonjs/models/Status.js.map +1 -0
  28. package/lib/commonjs/models/index.js +39 -0
  29. package/lib/commonjs/models/index.js.map +1 -0
  30. package/lib/commonjs/protocol/ProtocolHandler.js +343 -0
  31. package/lib/commonjs/protocol/ProtocolHandler.js.map +1 -0
  32. package/lib/commonjs/protocol/index.js +13 -0
  33. package/lib/commonjs/protocol/index.js.map +1 -0
  34. package/lib/commonjs/storage/StorageManager.js +333 -0
  35. package/lib/commonjs/storage/StorageManager.js.map +1 -0
  36. package/lib/commonjs/storage/index.js +19 -0
  37. package/lib/commonjs/storage/index.js.map +1 -0
  38. package/lib/commonjs/upload/S3Uploader.js +133 -0
  39. package/lib/commonjs/upload/S3Uploader.js.map +1 -0
  40. package/lib/commonjs/upload/UploadQueue.js +280 -0
  41. package/lib/commonjs/upload/UploadQueue.js.map +1 -0
  42. package/lib/commonjs/upload/index.js +20 -0
  43. package/lib/commonjs/upload/index.js.map +1 -0
  44. package/lib/commonjs/utils/errors.js +187 -0
  45. package/lib/commonjs/utils/errors.js.map +1 -0
  46. package/lib/commonjs/utils/index.js +40 -0
  47. package/lib/commonjs/utils/index.js.map +1 -0
  48. package/lib/commonjs/utils/logger.js +135 -0
  49. package/lib/commonjs/utils/logger.js.map +1 -0
  50. package/lib/commonjs/utils/retry.js +160 -0
  51. package/lib/commonjs/utils/retry.js.map +1 -0
  52. package/lib/module/BotaClient.js +216 -0
  53. package/lib/module/BotaClient.js.map +1 -0
  54. package/lib/module/ble/BleManager.js +484 -0
  55. package/lib/module/ble/BleManager.js.map +1 -0
  56. package/lib/module/ble/constants.js +159 -0
  57. package/lib/module/ble/constants.js.map +1 -0
  58. package/lib/module/ble/index.js +8 -0
  59. package/lib/module/ble/index.js.map +1 -0
  60. package/lib/module/ble/parsers.js +328 -0
  61. package/lib/module/ble/parsers.js.map +1 -0
  62. package/lib/module/index.js +22 -0
  63. package/lib/module/index.js.map +1 -0
  64. package/lib/module/managers/DeviceManager.js +429 -0
  65. package/lib/module/managers/DeviceManager.js.map +1 -0
  66. package/lib/module/managers/OTAManager.js +219 -0
  67. package/lib/module/managers/OTAManager.js.map +1 -0
  68. package/lib/module/managers/RecordingManager.js +376 -0
  69. package/lib/module/managers/RecordingManager.js.map +1 -0
  70. package/lib/module/managers/index.js +8 -0
  71. package/lib/module/managers/index.js.map +1 -0
  72. package/lib/module/models/Device.js +2 -0
  73. package/lib/module/models/Device.js.map +1 -0
  74. package/lib/module/models/Recording.js +2 -0
  75. package/lib/module/models/Recording.js.map +1 -0
  76. package/lib/module/models/Status.js +2 -0
  77. package/lib/module/models/Status.js.map +1 -0
  78. package/lib/module/models/index.js +8 -0
  79. package/lib/module/models/index.js.map +1 -0
  80. package/lib/module/protocol/ProtocolHandler.js +336 -0
  81. package/lib/module/protocol/ProtocolHandler.js.map +1 -0
  82. package/lib/module/protocol/index.js +6 -0
  83. package/lib/module/protocol/index.js.map +1 -0
  84. package/lib/module/storage/StorageManager.js +324 -0
  85. package/lib/module/storage/StorageManager.js.map +1 -0
  86. package/lib/module/storage/index.js +6 -0
  87. package/lib/module/storage/index.js.map +1 -0
  88. package/lib/module/upload/S3Uploader.js +126 -0
  89. package/lib/module/upload/S3Uploader.js.map +1 -0
  90. package/lib/module/upload/UploadQueue.js +272 -0
  91. package/lib/module/upload/UploadQueue.js.map +1 -0
  92. package/lib/module/upload/index.js +7 -0
  93. package/lib/module/upload/index.js.map +1 -0
  94. package/lib/module/utils/errors.js +173 -0
  95. package/lib/module/utils/errors.js.map +1 -0
  96. package/lib/module/utils/index.js +8 -0
  97. package/lib/module/utils/index.js.map +1 -0
  98. package/lib/module/utils/logger.js +129 -0
  99. package/lib/module/utils/logger.js.map +1 -0
  100. package/lib/module/utils/retry.js +149 -0
  101. package/lib/module/utils/retry.js.map +1 -0
  102. package/lib/typescript/src/BotaClient.d.ts +77 -0
  103. package/lib/typescript/src/BotaClient.d.ts.map +1 -0
  104. package/lib/typescript/src/ble/BleManager.d.ts +111 -0
  105. package/lib/typescript/src/ble/BleManager.d.ts.map +1 -0
  106. package/lib/typescript/src/ble/constants.d.ts +111 -0
  107. package/lib/typescript/src/ble/constants.d.ts.map +1 -0
  108. package/lib/typescript/src/ble/index.d.ts +7 -0
  109. package/lib/typescript/src/ble/index.d.ts.map +1 -0
  110. package/lib/typescript/src/ble/parsers.d.ts +100 -0
  111. package/lib/typescript/src/ble/parsers.d.ts.map +1 -0
  112. package/lib/typescript/src/index.d.ts +16 -0
  113. package/lib/typescript/src/index.d.ts.map +1 -0
  114. package/lib/typescript/src/managers/DeviceManager.d.ts +84 -0
  115. package/lib/typescript/src/managers/DeviceManager.d.ts.map +1 -0
  116. package/lib/typescript/src/managers/OTAManager.d.ts +78 -0
  117. package/lib/typescript/src/managers/OTAManager.d.ts.map +1 -0
  118. package/lib/typescript/src/managers/RecordingManager.d.ts +90 -0
  119. package/lib/typescript/src/managers/RecordingManager.d.ts.map +1 -0
  120. package/lib/typescript/src/managers/index.d.ts +7 -0
  121. package/lib/typescript/src/managers/index.d.ts.map +1 -0
  122. package/lib/typescript/src/models/Device.d.ts +139 -0
  123. package/lib/typescript/src/models/Device.d.ts.map +1 -0
  124. package/lib/typescript/src/models/Recording.d.ts +110 -0
  125. package/lib/typescript/src/models/Recording.d.ts.map +1 -0
  126. package/lib/typescript/src/models/Status.d.ts +104 -0
  127. package/lib/typescript/src/models/Status.d.ts.map +1 -0
  128. package/lib/typescript/src/models/index.d.ts +7 -0
  129. package/lib/typescript/src/models/index.d.ts.map +1 -0
  130. package/lib/typescript/src/protocol/ProtocolHandler.d.ts +69 -0
  131. package/lib/typescript/src/protocol/ProtocolHandler.d.ts.map +1 -0
  132. package/lib/typescript/src/protocol/index.d.ts +5 -0
  133. package/lib/typescript/src/protocol/index.d.ts.map +1 -0
  134. package/lib/typescript/src/storage/StorageManager.d.ts +116 -0
  135. package/lib/typescript/src/storage/StorageManager.d.ts.map +1 -0
  136. package/lib/typescript/src/storage/index.d.ts +5 -0
  137. package/lib/typescript/src/storage/index.d.ts.map +1 -0
  138. package/lib/typescript/src/upload/S3Uploader.d.ts +38 -0
  139. package/lib/typescript/src/upload/S3Uploader.d.ts.map +1 -0
  140. package/lib/typescript/src/upload/UploadQueue.d.ts +95 -0
  141. package/lib/typescript/src/upload/UploadQueue.d.ts.map +1 -0
  142. package/lib/typescript/src/upload/index.d.ts +6 -0
  143. package/lib/typescript/src/upload/index.d.ts.map +1 -0
  144. package/lib/typescript/src/utils/errors.d.ts +82 -0
  145. package/lib/typescript/src/utils/errors.d.ts.map +1 -0
  146. package/lib/typescript/src/utils/index.d.ts +7 -0
  147. package/lib/typescript/src/utils/index.d.ts.map +1 -0
  148. package/lib/typescript/src/utils/logger.d.ts +68 -0
  149. package/lib/typescript/src/utils/logger.d.ts.map +1 -0
  150. package/lib/typescript/src/utils/retry.d.ts +53 -0
  151. package/lib/typescript/src/utils/retry.d.ts.map +1 -0
  152. package/package.json +95 -0
  153. package/src/BotaClient.ts +238 -0
  154. package/src/ble/BleManager.ts +573 -0
  155. package/src/ble/constants.ts +158 -0
  156. package/src/ble/index.ts +7 -0
  157. package/src/ble/parsers.ts +395 -0
  158. package/src/index.ts +64 -0
  159. package/src/managers/DeviceManager.ts +545 -0
  160. package/src/managers/OTAManager.ts +263 -0
  161. package/src/managers/RecordingManager.ts +434 -0
  162. package/src/managers/index.ts +12 -0
  163. package/src/models/Device.ts +164 -0
  164. package/src/models/Recording.ts +123 -0
  165. package/src/models/Status.ts +126 -0
  166. package/src/models/index.ts +7 -0
  167. package/src/protocol/ProtocolHandler.ts +459 -0
  168. package/src/protocol/index.ts +5 -0
  169. package/src/storage/StorageManager.ts +343 -0
  170. package/src/storage/index.ts +5 -0
  171. package/src/upload/S3Uploader.ts +164 -0
  172. package/src/upload/UploadQueue.ts +310 -0
  173. package/src/upload/index.ts +6 -0
  174. package/src/utils/errors.ts +310 -0
  175. package/src/utils/index.ts +7 -0
  176. package/src/utils/logger.ts +137 -0
  177. package/src/utils/retry.ts +177 -0
@@ -0,0 +1,429 @@
1
+ /**
2
+ * Device Manager - Handles device discovery, connection, and provisioning
3
+ */
4
+
5
+ import { Buffer } from 'buffer';
6
+ import EventEmitter from 'eventemitter3';
7
+ import { getBleManager } from '../ble/BleManager';
8
+ import { SERVICE_DEVICE_INFO, SERVICE_BOTA_PROVISIONING, SERVICE_BOTA_CONTROL, CHAR_SERIAL_NUMBER, CHAR_FIRMWARE_REVISION, CHAR_HARDWARE_REVISION, CHAR_PAIRING_STATE, CHAR_DEVICE_TOKEN, CHAR_API_ENDPOINT, CHAR_PROVISIONING_RESULT, CHAR_DEVICE_STATUS, CHAR_TIME_SYNC, API_ENDPOINT_PRODUCTION, API_ENDPOINT_SANDBOX, PROVISIONING_SUCCESS, PROVISIONING_INVALID_TOKEN, PROVISIONING_STORAGE_ERROR, PROVISIONING_CHUNK_ERROR, OPERATION_TIMEOUT } from '../ble/constants';
9
+ import { parsePairingState, parseDeviceStatus, createTimeSyncData } from '../ble/parsers';
10
+ import { DeviceError, ProvisioningError } from '../utils/errors';
11
+ import { logger } from '../utils/logger';
12
+ const log = logger.tag('DeviceManager');
13
+
14
+ /**
15
+ * Device Manager class
16
+ */
17
+ export class DeviceManager extends EventEmitter {
18
+ connectedDevices = new Map();
19
+ statusSubscriptions = new Map();
20
+ isInitialized = false;
21
+ constructor() {
22
+ super();
23
+ this.bleManager = getBleManager();
24
+ this.setupBleListeners();
25
+ }
26
+
27
+ /**
28
+ * Initialize the device manager
29
+ */
30
+ initialize() {
31
+ if (this.isInitialized) {
32
+ return;
33
+ }
34
+ this.isInitialized = true;
35
+ log.info('DeviceManager initialized');
36
+ }
37
+
38
+ /**
39
+ * Set up BLE event listeners
40
+ */
41
+ setupBleListeners() {
42
+ this.bleManager.on('deviceDiscovered', device => {
43
+ this.emit('deviceDiscovered', device);
44
+ });
45
+ this.bleManager.on('deviceConnected', deviceId => {
46
+ const device = this.connectedDevices.get(deviceId);
47
+ if (device) {
48
+ this.emit('deviceConnected', device);
49
+ }
50
+ });
51
+ this.bleManager.on('deviceDisconnected', (deviceId, error) => {
52
+ const device = this.connectedDevices.get(deviceId);
53
+ if (device) {
54
+ // Update connection state
55
+ device.connectionState = 'disconnected';
56
+ }
57
+ this.connectedDevices.delete(deviceId);
58
+
59
+ // Clean up status subscription
60
+ this.statusSubscriptions.get(deviceId)?.remove();
61
+ this.statusSubscriptions.delete(deviceId);
62
+ this.emit('deviceDisconnected', deviceId, error);
63
+ });
64
+ }
65
+
66
+ /**
67
+ * Start scanning for Bota devices
68
+ */
69
+ async startScan(options = {}) {
70
+ log.info('Starting device scan', options);
71
+ this.emit('scanStarted');
72
+ try {
73
+ await this.bleManager.startScan(options);
74
+ } catch (error) {
75
+ this.emit('scanError', error);
76
+ throw error;
77
+ }
78
+ }
79
+
80
+ /**
81
+ * Stop scanning for devices
82
+ */
83
+ stopScan() {
84
+ log.info('Stopping device scan');
85
+ this.bleManager.stopScan();
86
+ this.emit('scanStopped');
87
+ }
88
+
89
+ /**
90
+ * Get list of discovered devices
91
+ */
92
+ getDiscoveredDevices() {
93
+ return this.bleManager.getDiscoveredDevices();
94
+ }
95
+
96
+ /**
97
+ * Get list of connected devices
98
+ */
99
+ getConnectedDevices() {
100
+ return Array.from(this.connectedDevices.values());
101
+ }
102
+
103
+ /**
104
+ * Connect to a discovered device
105
+ */
106
+ async connect(device) {
107
+ log.info('Connecting to device', {
108
+ deviceId: device.id,
109
+ name: device.name
110
+ });
111
+
112
+ // Check if already connected
113
+ const existing = this.connectedDevices.get(device.id);
114
+ if (existing && existing.connectionState === 'connected') {
115
+ log.debug('Device already connected', {
116
+ deviceId: device.id
117
+ });
118
+ return existing;
119
+ }
120
+
121
+ // Emit connecting state
122
+ this.emit('connectionStateChanged', device.id, 'connecting');
123
+ try {
124
+ // Connect via BLE manager
125
+ await this.bleManager.connect(device.id);
126
+
127
+ // Read device information
128
+ const serialNumber = await this.readSerialNumber(device.id);
129
+ const firmwareVersion = await this.readFirmwareVersion(device.id);
130
+ const hardwareRevision = await this.readHardwareRevision(device.id);
131
+ const pairingState = await this.readPairingState(device.id);
132
+ const mtu = await this.bleManager.getMtu(device.id);
133
+ const connectedDevice = {
134
+ id: device.id,
135
+ serialNumber,
136
+ deviceType: device.deviceType,
137
+ firmwareVersion,
138
+ hardwareRevision,
139
+ isProvisioned: pairingState === 'paired',
140
+ connectionState: 'connected',
141
+ mtu
142
+ };
143
+ this.connectedDevices.set(device.id, connectedDevice);
144
+ log.info('Device connected successfully', {
145
+ deviceId: device.id,
146
+ serialNumber,
147
+ isProvisioned: connectedDevice.isProvisioned
148
+ });
149
+ this.emit('connectionStateChanged', device.id, 'connected');
150
+ return connectedDevice;
151
+ } catch (error) {
152
+ this.emit('connectionStateChanged', device.id, 'disconnected');
153
+ throw error;
154
+ }
155
+ }
156
+
157
+ /**
158
+ * Disconnect from a device
159
+ */
160
+ async disconnect(device) {
161
+ log.info('Disconnecting from device', {
162
+ deviceId: device.id
163
+ });
164
+ this.emit('connectionStateChanged', device.id, 'disconnecting');
165
+
166
+ // Clean up status subscription
167
+ this.statusSubscriptions.get(device.id)?.remove();
168
+ this.statusSubscriptions.delete(device.id);
169
+ await this.bleManager.disconnect(device.id);
170
+ this.connectedDevices.delete(device.id);
171
+ this.emit('connectionStateChanged', device.id, 'disconnected');
172
+ }
173
+
174
+ /**
175
+ * Check if a device is connected
176
+ */
177
+ isConnected(deviceId) {
178
+ return this.bleManager.isConnected(deviceId);
179
+ }
180
+
181
+ /**
182
+ * Provision a device with a token
183
+ */
184
+ async provision(device, deviceToken, environment = 'production') {
185
+ log.info('Provisioning device', {
186
+ deviceId: device.id,
187
+ environment
188
+ });
189
+ if (!this.isConnected(device.id)) {
190
+ throw DeviceError.notConnected(device.id);
191
+ }
192
+
193
+ // Check current pairing state
194
+ const pairingState = await this.readPairingState(device.id);
195
+ if (pairingState === 'paired') {
196
+ log.warn('Device is already provisioned', {
197
+ deviceId: device.id
198
+ });
199
+ throw ProvisioningError.alreadyProvisioned(device.id);
200
+ }
201
+
202
+ // Set up provisioning result listener
203
+ const resultPromise = this.waitForProvisioningResult(device.id);
204
+ try {
205
+ // Write API endpoint
206
+ await this.writeApiEndpoint(device.id, environment);
207
+
208
+ // Write device token (chunked)
209
+ await this.writeDeviceToken(device.id, deviceToken);
210
+
211
+ // Wait for provisioning result
212
+ const result = await resultPromise;
213
+ if (!result.success) {
214
+ switch (result.error) {
215
+ case 'invalid_token':
216
+ throw ProvisioningError.invalidToken(device.id);
217
+ case 'storage_error':
218
+ throw ProvisioningError.storageError(device.id);
219
+ case 'chunk_error':
220
+ throw ProvisioningError.chunkError(device.id);
221
+ default:
222
+ throw new ProvisioningError('Provisioning failed', 'PROVISIONING_FAILED', device.id);
223
+ }
224
+ }
225
+
226
+ // Sync time to device
227
+ await this.syncTime(device.id);
228
+
229
+ // Update device state
230
+ device.isProvisioned = true;
231
+ log.info('Device provisioned successfully', {
232
+ deviceId: device.id
233
+ });
234
+ } catch (error) {
235
+ log.error('Provisioning failed', error, {
236
+ deviceId: device.id
237
+ });
238
+ throw error;
239
+ }
240
+ }
241
+
242
+ /**
243
+ * Check if a device is provisioned
244
+ */
245
+ async isProvisioned(device) {
246
+ const pairingState = await this.readPairingState(device.id);
247
+ return pairingState === 'paired';
248
+ }
249
+
250
+ /**
251
+ * Get device status
252
+ */
253
+ async getStatus(device) {
254
+ if (!this.isConnected(device.id)) {
255
+ throw DeviceError.notConnected(device.id);
256
+ }
257
+ const data = await this.bleManager.readCharacteristic(device.id, SERVICE_BOTA_CONTROL, CHAR_DEVICE_STATUS);
258
+ return parseDeviceStatus(data);
259
+ }
260
+
261
+ /**
262
+ * Subscribe to device status updates
263
+ */
264
+ subscribeToStatus(device, callback) {
265
+ if (!this.isConnected(device.id)) {
266
+ throw DeviceError.notConnected(device.id);
267
+ }
268
+
269
+ // Remove existing subscription
270
+ this.statusSubscriptions.get(device.id)?.remove();
271
+ const subscription = this.bleManager.subscribeToCharacteristic(device.id, SERVICE_BOTA_CONTROL, CHAR_DEVICE_STATUS, data => {
272
+ try {
273
+ const status = parseDeviceStatus(data);
274
+ this.emit('deviceStatusUpdated', device.id, status);
275
+ callback(status);
276
+ } catch (error) {
277
+ log.error('Failed to parse status update', error);
278
+ }
279
+ }, error => {
280
+ log.error('Status subscription error', error);
281
+ });
282
+ this.statusSubscriptions.set(device.id, subscription);
283
+ return () => {
284
+ subscription.remove();
285
+ this.statusSubscriptions.delete(device.id);
286
+ };
287
+ }
288
+
289
+ /**
290
+ * Sync time to device
291
+ */
292
+ async syncTime(deviceId) {
293
+ log.debug('Syncing time to device', {
294
+ deviceId
295
+ });
296
+ const timeSyncData = createTimeSyncData();
297
+ await this.bleManager.writeCharacteristic(deviceId, SERVICE_BOTA_CONTROL, CHAR_TIME_SYNC, timeSyncData);
298
+ }
299
+
300
+ // Private helper methods
301
+
302
+ async readSerialNumber(deviceId) {
303
+ const data = await this.bleManager.readCharacteristic(deviceId, SERVICE_DEVICE_INFO, CHAR_SERIAL_NUMBER);
304
+ return data.toString('utf8').replace(/\0/g, '');
305
+ }
306
+ async readFirmwareVersion(deviceId) {
307
+ const data = await this.bleManager.readCharacteristic(deviceId, SERVICE_DEVICE_INFO, CHAR_FIRMWARE_REVISION);
308
+ return data.toString('utf8').replace(/\0/g, '');
309
+ }
310
+ async readHardwareRevision(deviceId) {
311
+ try {
312
+ const data = await this.bleManager.readCharacteristic(deviceId, SERVICE_DEVICE_INFO, CHAR_HARDWARE_REVISION);
313
+ return data.toString('utf8').replace(/\0/g, '');
314
+ } catch {
315
+ return undefined;
316
+ }
317
+ }
318
+ async readPairingState(deviceId) {
319
+ const data = await this.bleManager.readCharacteristic(deviceId, SERVICE_BOTA_PROVISIONING, CHAR_PAIRING_STATE);
320
+ if (data.length < 1) {
321
+ return 'unpaired';
322
+ }
323
+ return parsePairingState(data[0]);
324
+ }
325
+ async writeApiEndpoint(deviceId, environment) {
326
+ const endpointByte = environment === 'production' ? API_ENDPOINT_PRODUCTION : API_ENDPOINT_SANDBOX;
327
+ await this.bleManager.writeCharacteristic(deviceId, SERVICE_BOTA_PROVISIONING, CHAR_API_ENDPOINT, Buffer.from([endpointByte]));
328
+ }
329
+ async writeDeviceToken(deviceId, token) {
330
+ const mtu = await this.bleManager.getMtu(deviceId);
331
+ const maxChunkSize = mtu - 5; // Account for BLE overhead + chunk header
332
+
333
+ const tokenBuffer = Buffer.from(token, 'utf8');
334
+ const totalChunks = Math.ceil(tokenBuffer.length / (maxChunkSize - 2));
335
+ log.debug('Writing device token', {
336
+ deviceId,
337
+ tokenLength: token.length,
338
+ totalChunks,
339
+ mtu
340
+ });
341
+ for (let i = 0; i < totalChunks; i++) {
342
+ const start = i * (maxChunkSize - 2);
343
+ const end = Math.min(start + (maxChunkSize - 2), tokenBuffer.length);
344
+ const chunkData = tokenBuffer.slice(start, end);
345
+
346
+ // Create chunk with header: [chunk_index, total_chunks, ...data]
347
+ const chunk = Buffer.alloc(2 + chunkData.length);
348
+ chunk.writeUInt8(i, 0);
349
+ chunk.writeUInt8(totalChunks, 1);
350
+ chunkData.copy(chunk, 2);
351
+ await this.bleManager.writeCharacteristic(deviceId, SERVICE_BOTA_PROVISIONING, CHAR_DEVICE_TOKEN, chunk);
352
+ log.debug('Wrote token chunk', {
353
+ chunk: i + 1,
354
+ total: totalChunks
355
+ });
356
+ }
357
+ }
358
+ waitForProvisioningResult(deviceId) {
359
+ return new Promise((resolve, reject) => {
360
+ const timeout = setTimeout(() => {
361
+ subscription.remove();
362
+ reject(ProvisioningError.timeout(deviceId));
363
+ }, OPERATION_TIMEOUT);
364
+ const subscription = this.bleManager.subscribeToCharacteristic(deviceId, SERVICE_BOTA_PROVISIONING, CHAR_PROVISIONING_RESULT, data => {
365
+ clearTimeout(timeout);
366
+ subscription.remove();
367
+ if (data.length < 1) {
368
+ resolve({
369
+ success: false,
370
+ error: 'unknown'
371
+ });
372
+ return;
373
+ }
374
+ const resultCode = data[0];
375
+ switch (resultCode) {
376
+ case PROVISIONING_SUCCESS:
377
+ resolve({
378
+ success: true
379
+ });
380
+ break;
381
+ case PROVISIONING_INVALID_TOKEN:
382
+ resolve({
383
+ success: false,
384
+ error: 'invalid_token'
385
+ });
386
+ break;
387
+ case PROVISIONING_STORAGE_ERROR:
388
+ resolve({
389
+ success: false,
390
+ error: 'storage_error'
391
+ });
392
+ break;
393
+ case PROVISIONING_CHUNK_ERROR:
394
+ resolve({
395
+ success: false,
396
+ error: 'chunk_error'
397
+ });
398
+ break;
399
+ default:
400
+ resolve({
401
+ success: false,
402
+ error: 'unknown'
403
+ });
404
+ }
405
+ }, error => {
406
+ clearTimeout(timeout);
407
+ subscription.remove();
408
+ reject(new ProvisioningError(`Provisioning notification error: ${error.message}`, 'NOTIFICATION_ERROR', deviceId, error));
409
+ });
410
+ });
411
+ }
412
+
413
+ /**
414
+ * Clean up resources
415
+ */
416
+ destroy() {
417
+ log.info('Destroying DeviceManager');
418
+
419
+ // Clean up all status subscriptions
420
+ for (const sub of this.statusSubscriptions.values()) {
421
+ sub.remove();
422
+ }
423
+ this.statusSubscriptions.clear();
424
+ this.connectedDevices.clear();
425
+ this.removeAllListeners();
426
+ this.isInitialized = false;
427
+ }
428
+ }
429
+ //# sourceMappingURL=DeviceManager.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"names":["Buffer","EventEmitter","getBleManager","SERVICE_DEVICE_INFO","SERVICE_BOTA_PROVISIONING","SERVICE_BOTA_CONTROL","CHAR_SERIAL_NUMBER","CHAR_FIRMWARE_REVISION","CHAR_HARDWARE_REVISION","CHAR_PAIRING_STATE","CHAR_DEVICE_TOKEN","CHAR_API_ENDPOINT","CHAR_PROVISIONING_RESULT","CHAR_DEVICE_STATUS","CHAR_TIME_SYNC","API_ENDPOINT_PRODUCTION","API_ENDPOINT_SANDBOX","PROVISIONING_SUCCESS","PROVISIONING_INVALID_TOKEN","PROVISIONING_STORAGE_ERROR","PROVISIONING_CHUNK_ERROR","OPERATION_TIMEOUT","parsePairingState","parseDeviceStatus","createTimeSyncData","DeviceError","ProvisioningError","logger","log","tag","DeviceManager","connectedDevices","Map","statusSubscriptions","isInitialized","constructor","bleManager","setupBleListeners","initialize","info","on","device","emit","deviceId","get","error","connectionState","delete","remove","startScan","options","stopScan","getDiscoveredDevices","getConnectedDevices","Array","from","values","connect","id","name","existing","debug","serialNumber","readSerialNumber","firmwareVersion","readFirmwareVersion","hardwareRevision","readHardwareRevision","pairingState","readPairingState","mtu","getMtu","connectedDevice","deviceType","isProvisioned","set","disconnect","isConnected","provision","deviceToken","environment","notConnected","warn","alreadyProvisioned","resultPromise","waitForProvisioningResult","writeApiEndpoint","writeDeviceToken","result","success","invalidToken","storageError","chunkError","syncTime","getStatus","data","readCharacteristic","subscribeToStatus","callback","subscription","subscribeToCharacteristic","status","timeSyncData","writeCharacteristic","toString","replace","undefined","length","endpointByte","token","maxChunkSize","tokenBuffer","totalChunks","Math","ceil","tokenLength","i","start","end","min","chunkData","slice","chunk","alloc","writeUInt8","copy","total","Promise","resolve","reject","timeout","setTimeout","clearTimeout","resultCode","message","destroy","sub","clear","removeAllListeners"],"sourceRoot":"../../../src","sources":["managers/DeviceManager.ts"],"mappings":"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","ignoreList":[]}
@@ -0,0 +1,219 @@
1
+ /**
2
+ * OTA Manager - Handles firmware over-the-air updates
3
+ *
4
+ * Note: Full Nordic DFU implementation requires native modules.
5
+ * This is a placeholder that handles version checking and update preparation.
6
+ * Actual DFU transfer would need react-native-nordic-dfu or similar.
7
+ */
8
+
9
+ import EventEmitter from 'eventemitter3';
10
+ import { getBleManager } from '../ble/BleManager';
11
+ import { SERVICE_BOTA_CONTROL, CHAR_DEVICE_COMMAND, DEVICE_CMD_ENTER_DFU } from '../ble/constants';
12
+ import { DeviceError } from '../utils/errors';
13
+ import { logger } from '../utils/logger';
14
+ import { Buffer } from 'buffer';
15
+ const log = logger.tag('OTAManager');
16
+
17
+ /**
18
+ * Firmware info
19
+ */
20
+
21
+ /**
22
+ * OTA progress stages
23
+ */
24
+
25
+ /**
26
+ * OTA progress
27
+ */
28
+
29
+ /**
30
+ * Events emitted by OTAManager
31
+ */
32
+
33
+ /**
34
+ * OTA Manager class
35
+ */
36
+ export class OTAManager extends EventEmitter {
37
+ constructor(firmwareCdnUrl = 'https://cdn.bota.dev/firmware') {
38
+ super();
39
+ this.firmwareCdnUrl = firmwareCdnUrl;
40
+ }
41
+
42
+ /**
43
+ * Check for available firmware updates
44
+ */
45
+ async checkForUpdate(device) {
46
+ log.info('Checking for firmware update', {
47
+ deviceId: device.id,
48
+ currentVersion: device.firmwareVersion,
49
+ deviceType: device.deviceType
50
+ });
51
+ this.emit('progress', device.id, {
52
+ stage: 'checking',
53
+ progress: 0
54
+ });
55
+ try {
56
+ // Fetch latest firmware info from CDN
57
+ const response = await fetch(`${this.firmwareCdnUrl}/latest?device_type=${device.deviceType}&current=${device.firmwareVersion}`);
58
+ if (!response.ok) {
59
+ if (response.status === 404) {
60
+ log.info('No update available', {
61
+ deviceId: device.id
62
+ });
63
+ return null;
64
+ }
65
+ throw new Error(`Failed to check for updates: ${response.status}`);
66
+ }
67
+ const firmware = await response.json();
68
+
69
+ // Compare versions
70
+ if (this.isNewerVersion(firmware.version, device.firmwareVersion)) {
71
+ log.info('Update available', {
72
+ deviceId: device.id,
73
+ currentVersion: device.firmwareVersion,
74
+ newVersion: firmware.version
75
+ });
76
+ this.emit('updateAvailable', firmware);
77
+ return firmware;
78
+ }
79
+ log.info('Device is up to date', {
80
+ deviceId: device.id,
81
+ version: device.firmwareVersion
82
+ });
83
+ return null;
84
+ } catch (error) {
85
+ log.error('Failed to check for update', error, {
86
+ deviceId: device.id
87
+ });
88
+ throw error;
89
+ }
90
+ }
91
+
92
+ /**
93
+ * Download firmware package
94
+ */
95
+ async downloadFirmware(firmware) {
96
+ log.info('Downloading firmware', {
97
+ version: firmware.version,
98
+ size: firmware.size
99
+ });
100
+ const response = await fetch(firmware.url);
101
+ if (!response.ok) {
102
+ throw new Error(`Failed to download firmware: ${response.status}`);
103
+ }
104
+ const data = await response.arrayBuffer();
105
+
106
+ // Verify checksum
107
+ // Note: In production, implement proper checksum verification
108
+ log.info('Firmware downloaded', {
109
+ size: data.byteLength
110
+ });
111
+ return data;
112
+ }
113
+
114
+ /**
115
+ * Prepare device for DFU mode
116
+ */
117
+ async enterDfuMode(device) {
118
+ if (!getBleManager().isConnected(device.id)) {
119
+ throw DeviceError.notConnected(device.id);
120
+ }
121
+ log.info('Entering DFU mode', {
122
+ deviceId: device.id
123
+ });
124
+
125
+ // Send DFU command to device
126
+ await getBleManager().writeCharacteristic(device.id, SERVICE_BOTA_CONTROL, CHAR_DEVICE_COMMAND, Buffer.from([DEVICE_CMD_ENTER_DFU]));
127
+
128
+ // Device will disconnect and reboot into DFU mode
129
+ log.info('DFU command sent, device will reboot', {
130
+ deviceId: device.id
131
+ });
132
+ }
133
+
134
+ /**
135
+ * Perform firmware update
136
+ *
137
+ * Note: This is a placeholder. Full implementation requires:
138
+ * 1. react-native-nordic-dfu for actual DFU transfer
139
+ * 2. Native module integration
140
+ * 3. DFU package preparation
141
+ */
142
+ async performUpdate(device, firmware) {
143
+ log.info('Starting firmware update', {
144
+ deviceId: device.id,
145
+ version: firmware.version
146
+ });
147
+ this.emit('progress', device.id, {
148
+ stage: 'downloading',
149
+ progress: 0
150
+ });
151
+ try {
152
+ // Download firmware
153
+ await this.downloadFirmware(firmware);
154
+ this.emit('progress', device.id, {
155
+ stage: 'downloading',
156
+ progress: 1
157
+ });
158
+ this.emit('progress', device.id, {
159
+ stage: 'preparing',
160
+ progress: 0
161
+ });
162
+
163
+ // Enter DFU mode
164
+ await this.enterDfuMode(device);
165
+ this.emit('progress', device.id, {
166
+ stage: 'preparing',
167
+ progress: 1
168
+ });
169
+
170
+ // Note: At this point, we would use react-native-nordic-dfu
171
+ // to perform the actual firmware transfer.
172
+ // For now, we throw an error indicating this needs native implementation.
173
+
174
+ throw new Error('Full DFU implementation requires react-native-nordic-dfu native module. ' + 'Device has entered DFU mode and is advertising as "BotaDFU-xxx".');
175
+
176
+ // After DFU completes:
177
+ // this.emit('progress', device.id, { stage: 'completed', progress: 1 });
178
+ // this.emit('completed', device.id, firmware.version);
179
+ } catch (error) {
180
+ const err = error;
181
+ log.error('Firmware update failed', err, {
182
+ deviceId: device.id
183
+ });
184
+ this.emit('progress', device.id, {
185
+ stage: 'failed',
186
+ progress: 0,
187
+ error: err.message
188
+ });
189
+ this.emit('failed', device.id, err);
190
+ throw error;
191
+ }
192
+ }
193
+
194
+ /**
195
+ * Compare semantic versions
196
+ */
197
+ isNewerVersion(newVersion, currentVersion) {
198
+ const parseVersion = v => {
199
+ return v.split('.').map(n => parseInt(n, 10) || 0);
200
+ };
201
+ const newParts = parseVersion(newVersion);
202
+ const currentParts = parseVersion(currentVersion);
203
+ for (let i = 0; i < Math.max(newParts.length, currentParts.length); i++) {
204
+ const newPart = newParts[i] || 0;
205
+ const currentPart = currentParts[i] || 0;
206
+ if (newPart > currentPart) return true;
207
+ if (newPart < currentPart) return false;
208
+ }
209
+ return false;
210
+ }
211
+
212
+ /**
213
+ * Clean up resources
214
+ */
215
+ destroy() {
216
+ this.removeAllListeners();
217
+ }
218
+ }
219
+ //# sourceMappingURL=OTAManager.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"names":["EventEmitter","getBleManager","SERVICE_BOTA_CONTROL","CHAR_DEVICE_COMMAND","DEVICE_CMD_ENTER_DFU","DeviceError","logger","Buffer","log","tag","OTAManager","constructor","firmwareCdnUrl","checkForUpdate","device","info","deviceId","id","currentVersion","firmwareVersion","deviceType","emit","stage","progress","response","fetch","ok","status","Error","firmware","json","isNewerVersion","version","newVersion","error","downloadFirmware","size","url","data","arrayBuffer","byteLength","enterDfuMode","isConnected","notConnected","writeCharacteristic","from","performUpdate","err","message","parseVersion","v","split","map","n","parseInt","newParts","currentParts","i","Math","max","length","newPart","currentPart","destroy","removeAllListeners"],"sourceRoot":"../../../src","sources":["managers/OTAManager.ts"],"mappings":"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","ignoreList":[]}