@voltras/node-sdk 0.1.0

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 (203) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +272 -0
  3. package/dist/cjs/bluetooth/adapters/base.js +116 -0
  4. package/dist/cjs/bluetooth/adapters/base.js.map +1 -0
  5. package/dist/cjs/bluetooth/adapters/index.js +58 -0
  6. package/dist/cjs/bluetooth/adapters/index.js.map +1 -0
  7. package/dist/cjs/bluetooth/adapters/native.js +473 -0
  8. package/dist/cjs/bluetooth/adapters/native.js.map +1 -0
  9. package/dist/cjs/bluetooth/adapters/node.js +228 -0
  10. package/dist/cjs/bluetooth/adapters/node.js.map +1 -0
  11. package/dist/cjs/bluetooth/adapters/types.js +11 -0
  12. package/dist/cjs/bluetooth/adapters/types.js.map +1 -0
  13. package/dist/cjs/bluetooth/adapters/web-bluetooth-base.js +187 -0
  14. package/dist/cjs/bluetooth/adapters/web-bluetooth-base.js.map +1 -0
  15. package/dist/cjs/bluetooth/adapters/web.js +112 -0
  16. package/dist/cjs/bluetooth/adapters/web.js.map +1 -0
  17. package/dist/cjs/bluetooth/controllers/scanner-controller.js +145 -0
  18. package/dist/cjs/bluetooth/controllers/scanner-controller.js.map +1 -0
  19. package/dist/cjs/bluetooth/index.js +27 -0
  20. package/dist/cjs/bluetooth/index.js.map +1 -0
  21. package/dist/cjs/bluetooth/models/connection.js +68 -0
  22. package/dist/cjs/bluetooth/models/connection.js.map +1 -0
  23. package/dist/cjs/bluetooth/models/device.js +26 -0
  24. package/dist/cjs/bluetooth/models/device.js.map +1 -0
  25. package/dist/cjs/bluetooth/models/environment.js +106 -0
  26. package/dist/cjs/bluetooth/models/environment.js.map +1 -0
  27. package/dist/cjs/errors.js +167 -0
  28. package/dist/cjs/errors.js.map +1 -0
  29. package/dist/cjs/index.js +116 -0
  30. package/dist/cjs/index.js.map +1 -0
  31. package/dist/cjs/react/hooks.js +262 -0
  32. package/dist/cjs/react/hooks.js.map +1 -0
  33. package/dist/cjs/react/index.js +18 -0
  34. package/dist/cjs/react/index.js.map +1 -0
  35. package/dist/cjs/sdk/index.js +14 -0
  36. package/dist/cjs/sdk/index.js.map +1 -0
  37. package/dist/cjs/sdk/types.js +8 -0
  38. package/dist/cjs/sdk/types.js.map +1 -0
  39. package/dist/cjs/sdk/voltra-client.js +632 -0
  40. package/dist/cjs/sdk/voltra-client.js.map +1 -0
  41. package/dist/cjs/sdk/voltra-manager.js +419 -0
  42. package/dist/cjs/sdk/voltra-manager.js.map +1 -0
  43. package/dist/cjs/shared/index.js +12 -0
  44. package/dist/cjs/shared/index.js.map +1 -0
  45. package/dist/cjs/shared/utils.js +51 -0
  46. package/dist/cjs/shared/utils.js.map +1 -0
  47. package/dist/cjs/voltra/index.js +56 -0
  48. package/dist/cjs/voltra/index.js.map +1 -0
  49. package/dist/cjs/voltra/models/connection.js +68 -0
  50. package/dist/cjs/voltra/models/connection.js.map +1 -0
  51. package/dist/cjs/voltra/models/device-filter.js +28 -0
  52. package/dist/cjs/voltra/models/device-filter.js.map +1 -0
  53. package/dist/cjs/voltra/models/device.js +152 -0
  54. package/dist/cjs/voltra/models/device.js.map +1 -0
  55. package/dist/cjs/voltra/models/telemetry/frame.js +46 -0
  56. package/dist/cjs/voltra/models/telemetry/frame.js.map +1 -0
  57. package/dist/cjs/voltra/models/telemetry/index.js +14 -0
  58. package/dist/cjs/voltra/models/telemetry/index.js.map +1 -0
  59. package/dist/cjs/voltra/protocol/commands.js +230 -0
  60. package/dist/cjs/voltra/protocol/commands.js.map +1 -0
  61. package/dist/cjs/voltra/protocol/constants.js +136 -0
  62. package/dist/cjs/voltra/protocol/constants.js.map +1 -0
  63. package/dist/cjs/voltra/protocol/data/chains.json +830 -0
  64. package/dist/cjs/voltra/protocol/data/eccentric.json +1598 -0
  65. package/dist/cjs/voltra/protocol/data/protocol.json +54 -0
  66. package/dist/cjs/voltra/protocol/data/weights.json +62 -0
  67. package/dist/cjs/voltra/protocol/index.js +25 -0
  68. package/dist/cjs/voltra/protocol/index.js.map +1 -0
  69. package/dist/cjs/voltra/protocol/telemetry-decoder.js +146 -0
  70. package/dist/cjs/voltra/protocol/telemetry-decoder.js.map +1 -0
  71. package/dist/esm/bluetooth/adapters/base.js +112 -0
  72. package/dist/esm/bluetooth/adapters/base.js.map +1 -0
  73. package/dist/esm/bluetooth/adapters/index.js +51 -0
  74. package/dist/esm/bluetooth/adapters/index.js.map +1 -0
  75. package/dist/esm/bluetooth/adapters/native.js +469 -0
  76. package/dist/esm/bluetooth/adapters/native.js.map +1 -0
  77. package/dist/esm/bluetooth/adapters/node.js +191 -0
  78. package/dist/esm/bluetooth/adapters/node.js.map +1 -0
  79. package/dist/esm/bluetooth/adapters/types.js +10 -0
  80. package/dist/esm/bluetooth/adapters/types.js.map +1 -0
  81. package/dist/esm/bluetooth/adapters/web-bluetooth-base.js +183 -0
  82. package/dist/esm/bluetooth/adapters/web-bluetooth-base.js.map +1 -0
  83. package/dist/esm/bluetooth/adapters/web.js +108 -0
  84. package/dist/esm/bluetooth/adapters/web.js.map +1 -0
  85. package/dist/esm/bluetooth/controllers/scanner-controller.js +141 -0
  86. package/dist/esm/bluetooth/controllers/scanner-controller.js.map +1 -0
  87. package/dist/esm/bluetooth/index.js +17 -0
  88. package/dist/esm/bluetooth/index.js.map +1 -0
  89. package/dist/esm/bluetooth/models/connection.js +63 -0
  90. package/dist/esm/bluetooth/models/connection.js.map +1 -0
  91. package/dist/esm/bluetooth/models/device.js +22 -0
  92. package/dist/esm/bluetooth/models/device.js.map +1 -0
  93. package/dist/esm/bluetooth/models/environment.js +101 -0
  94. package/dist/esm/bluetooth/models/environment.js.map +1 -0
  95. package/dist/esm/errors.js +155 -0
  96. package/dist/esm/errors.js.map +1 -0
  97. package/dist/esm/index.js +72 -0
  98. package/dist/esm/index.js.map +1 -0
  99. package/dist/esm/react/hooks.js +257 -0
  100. package/dist/esm/react/hooks.js.map +1 -0
  101. package/dist/esm/react/index.js +12 -0
  102. package/dist/esm/react/index.js.map +1 -0
  103. package/dist/esm/sdk/index.js +9 -0
  104. package/dist/esm/sdk/index.js.map +1 -0
  105. package/dist/esm/sdk/types.js +7 -0
  106. package/dist/esm/sdk/types.js.map +1 -0
  107. package/dist/esm/sdk/voltra-client.js +628 -0
  108. package/dist/esm/sdk/voltra-client.js.map +1 -0
  109. package/dist/esm/sdk/voltra-manager.js +415 -0
  110. package/dist/esm/sdk/voltra-manager.js.map +1 -0
  111. package/dist/esm/shared/index.js +5 -0
  112. package/dist/esm/shared/index.js.map +1 -0
  113. package/dist/esm/shared/utils.js +45 -0
  114. package/dist/esm/shared/utils.js.map +1 -0
  115. package/dist/esm/voltra/index.js +26 -0
  116. package/dist/esm/voltra/index.js.map +1 -0
  117. package/dist/esm/voltra/models/connection.js +63 -0
  118. package/dist/esm/voltra/models/connection.js.map +1 -0
  119. package/dist/esm/voltra/models/device-filter.js +23 -0
  120. package/dist/esm/voltra/models/device-filter.js.map +1 -0
  121. package/dist/esm/voltra/models/device.js +148 -0
  122. package/dist/esm/voltra/models/device.js.map +1 -0
  123. package/dist/esm/voltra/models/telemetry/frame.js +40 -0
  124. package/dist/esm/voltra/models/telemetry/frame.js.map +1 -0
  125. package/dist/esm/voltra/models/telemetry/index.js +7 -0
  126. package/dist/esm/voltra/models/telemetry/index.js.map +1 -0
  127. package/dist/esm/voltra/protocol/commands.js +224 -0
  128. package/dist/esm/voltra/protocol/commands.js.map +1 -0
  129. package/dist/esm/voltra/protocol/constants.js +130 -0
  130. package/dist/esm/voltra/protocol/constants.js.map +1 -0
  131. package/dist/esm/voltra/protocol/data/chains.json +830 -0
  132. package/dist/esm/voltra/protocol/data/eccentric.json +1598 -0
  133. package/dist/esm/voltra/protocol/data/protocol.json +54 -0
  134. package/dist/esm/voltra/protocol/data/weights.json +62 -0
  135. package/dist/esm/voltra/protocol/index.js +9 -0
  136. package/dist/esm/voltra/protocol/index.js.map +1 -0
  137. package/dist/esm/voltra/protocol/telemetry-decoder.js +140 -0
  138. package/dist/esm/voltra/protocol/telemetry-decoder.js.map +1 -0
  139. package/dist/types/bluetooth/adapters/base.d.ts +85 -0
  140. package/dist/types/bluetooth/adapters/base.d.ts.map +1 -0
  141. package/dist/types/bluetooth/adapters/index.d.ts +35 -0
  142. package/dist/types/bluetooth/adapters/index.d.ts.map +1 -0
  143. package/dist/types/bluetooth/adapters/native.d.ts +109 -0
  144. package/dist/types/bluetooth/adapters/native.d.ts.map +1 -0
  145. package/dist/types/bluetooth/adapters/node.d.ts +91 -0
  146. package/dist/types/bluetooth/adapters/node.d.ts.map +1 -0
  147. package/dist/types/bluetooth/adapters/types.d.ts +102 -0
  148. package/dist/types/bluetooth/adapters/types.d.ts.map +1 -0
  149. package/dist/types/bluetooth/adapters/web-bluetooth-base.d.ts +90 -0
  150. package/dist/types/bluetooth/adapters/web-bluetooth-base.d.ts.map +1 -0
  151. package/dist/types/bluetooth/adapters/web.d.ts +57 -0
  152. package/dist/types/bluetooth/adapters/web.d.ts.map +1 -0
  153. package/dist/types/bluetooth/controllers/scanner-controller.d.ts +93 -0
  154. package/dist/types/bluetooth/controllers/scanner-controller.d.ts.map +1 -0
  155. package/dist/types/bluetooth/index.d.ts +14 -0
  156. package/dist/types/bluetooth/index.d.ts.map +1 -0
  157. package/dist/types/bluetooth/models/connection.d.ts +37 -0
  158. package/dist/types/bluetooth/models/connection.d.ts.map +1 -0
  159. package/dist/types/bluetooth/models/device.d.ts +25 -0
  160. package/dist/types/bluetooth/models/device.d.ts.map +1 -0
  161. package/dist/types/bluetooth/models/environment.d.ts +45 -0
  162. package/dist/types/bluetooth/models/environment.d.ts.map +1 -0
  163. package/dist/types/errors.d.ts +113 -0
  164. package/dist/types/errors.d.ts.map +1 -0
  165. package/dist/types/index.d.ts +55 -0
  166. package/dist/types/index.d.ts.map +1 -0
  167. package/dist/types/react/hooks.d.ts +130 -0
  168. package/dist/types/react/hooks.d.ts.map +1 -0
  169. package/dist/types/react/index.d.ts +12 -0
  170. package/dist/types/react/index.d.ts.map +1 -0
  171. package/dist/types/sdk/index.d.ts +11 -0
  172. package/dist/types/sdk/index.d.ts.map +1 -0
  173. package/dist/types/sdk/types.d.ts +104 -0
  174. package/dist/types/sdk/types.d.ts.map +1 -0
  175. package/dist/types/sdk/voltra-client.d.ts +221 -0
  176. package/dist/types/sdk/voltra-client.d.ts.map +1 -0
  177. package/dist/types/sdk/voltra-manager.d.ts +226 -0
  178. package/dist/types/sdk/voltra-manager.d.ts.map +1 -0
  179. package/dist/types/shared/index.d.ts +5 -0
  180. package/dist/types/shared/index.d.ts.map +1 -0
  181. package/dist/types/shared/utils.d.ts +25 -0
  182. package/dist/types/shared/utils.d.ts.map +1 -0
  183. package/dist/types/voltra/index.d.ts +13 -0
  184. package/dist/types/voltra/index.d.ts.map +1 -0
  185. package/dist/types/voltra/models/connection.d.ts +37 -0
  186. package/dist/types/voltra/models/connection.d.ts.map +1 -0
  187. package/dist/types/voltra/models/device-filter.d.ts +19 -0
  188. package/dist/types/voltra/models/device-filter.d.ts.map +1 -0
  189. package/dist/types/voltra/models/device.d.ts +105 -0
  190. package/dist/types/voltra/models/device.d.ts.map +1 -0
  191. package/dist/types/voltra/models/telemetry/frame.d.ts +41 -0
  192. package/dist/types/voltra/models/telemetry/frame.d.ts.map +1 -0
  193. package/dist/types/voltra/models/telemetry/index.d.ts +8 -0
  194. package/dist/types/voltra/models/telemetry/index.d.ts.map +1 -0
  195. package/dist/types/voltra/protocol/commands.d.ts +99 -0
  196. package/dist/types/voltra/protocol/commands.d.ts.map +1 -0
  197. package/dist/types/voltra/protocol/constants.d.ts +103 -0
  198. package/dist/types/voltra/protocol/constants.d.ts.map +1 -0
  199. package/dist/types/voltra/protocol/index.d.ts +9 -0
  200. package/dist/types/voltra/protocol/index.d.ts.map +1 -0
  201. package/dist/types/voltra/protocol/telemetry-decoder.d.ts +45 -0
  202. package/dist/types/voltra/protocol/telemetry-decoder.d.ts.map +1 -0
  203. package/package.json +111 -0
@@ -0,0 +1,632 @@
1
+ "use strict";
2
+ /**
3
+ * VoltraClient
4
+ *
5
+ * High-level API for connecting to and controlling a single Voltra device.
6
+ * Handles connection lifecycle, authentication, device settings, and telemetry.
7
+ *
8
+ * @example
9
+ * ```typescript
10
+ * import { VoltraClient, WebBLEAdapter, BLE } from '@voltras/node-sdk';
11
+ *
12
+ * const adapter = new WebBLEAdapter({ ble: BLE });
13
+ * const client = new VoltraClient({ adapter });
14
+ *
15
+ * // Connect to device
16
+ * const devices = await client.scan();
17
+ * await client.connect(devices[0]);
18
+ *
19
+ * // Configure settings
20
+ * await client.setWeight(50);
21
+ *
22
+ * // Listen for telemetry
23
+ * client.onFrame((frame) => {
24
+ * console.log('Position:', frame.position, 'Velocity:', frame.velocity);
25
+ * });
26
+ *
27
+ * // Start recording
28
+ * await client.startRecording();
29
+ * // ... workout ...
30
+ * await client.stopRecording();
31
+ *
32
+ * // Cleanup
33
+ * client.dispose();
34
+ * ```
35
+ */
36
+ Object.defineProperty(exports, "__esModule", { value: true });
37
+ exports.VoltraClient = void 0;
38
+ const connection_1 = require("../voltra/models/connection");
39
+ const device_filter_1 = require("../voltra/models/device-filter");
40
+ const constants_1 = require("../voltra/protocol/constants");
41
+ const commands_1 = require("../voltra/protocol/commands");
42
+ const telemetry_decoder_1 = require("../voltra/protocol/telemetry-decoder");
43
+ const utils_1 = require("../shared/utils");
44
+ const errors_1 = require("../errors");
45
+ /**
46
+ * Default client options.
47
+ */
48
+ const DEFAULT_OPTIONS = {
49
+ autoReconnect: false,
50
+ maxReconnectAttempts: 3,
51
+ reconnectDelayMs: 1000,
52
+ };
53
+ /**
54
+ * Default device settings.
55
+ */
56
+ const DEFAULT_SETTINGS = {
57
+ weight: 0,
58
+ chains: 0,
59
+ eccentric: 0,
60
+ };
61
+ /**
62
+ * High-level client for connecting to and controlling a Voltra device.
63
+ */
64
+ class VoltraClient {
65
+ constructor(options = {}) {
66
+ // State
67
+ this._connectionState = 'disconnected';
68
+ this._connectedDeviceId = null;
69
+ this._connectedDeviceName = null;
70
+ this._settings = { ...DEFAULT_SETTINGS };
71
+ this._recordingState = 'idle';
72
+ this._isReconnecting = false;
73
+ this._reconnectAttempt = 0;
74
+ this._error = null;
75
+ this._lastConnectedDevice = null;
76
+ // Notification handling
77
+ this.notificationUnsubscribe = null;
78
+ // Event listeners
79
+ this.listeners = new Set();
80
+ this.frameListeners = new Set();
81
+ // Disposed flag
82
+ this.disposed = false;
83
+ this.options = { ...DEFAULT_OPTIONS, ...options };
84
+ this.adapter = options.adapter ?? null;
85
+ }
86
+ // ===========================================================================
87
+ // Public Getters
88
+ // ===========================================================================
89
+ /**
90
+ * Get current connection state.
91
+ */
92
+ get connectionState() {
93
+ return this._connectionState;
94
+ }
95
+ /**
96
+ * Check if connected to a device.
97
+ */
98
+ get isConnected() {
99
+ return this._connectionState === 'connected';
100
+ }
101
+ /**
102
+ * Check if currently reconnecting.
103
+ */
104
+ get isReconnecting() {
105
+ return this._isReconnecting;
106
+ }
107
+ /**
108
+ * Get connected device ID.
109
+ */
110
+ get connectedDeviceId() {
111
+ return this._connectedDeviceId;
112
+ }
113
+ /**
114
+ * Get connected device name.
115
+ */
116
+ get connectedDeviceName() {
117
+ return this._connectedDeviceName;
118
+ }
119
+ /**
120
+ * Get current device settings.
121
+ */
122
+ get settings() {
123
+ return { ...this._settings };
124
+ }
125
+ /**
126
+ * Get current recording state.
127
+ */
128
+ get recordingState() {
129
+ return this._recordingState;
130
+ }
131
+ /**
132
+ * Check if currently recording.
133
+ */
134
+ get isRecording() {
135
+ return this._recordingState === 'active';
136
+ }
137
+ /**
138
+ * Get last error.
139
+ */
140
+ get error() {
141
+ return this._error;
142
+ }
143
+ /**
144
+ * Get full state snapshot.
145
+ */
146
+ get state() {
147
+ return {
148
+ connectionState: this._connectionState,
149
+ isConnected: this.isConnected,
150
+ isReconnecting: this._isReconnecting,
151
+ connectedDeviceId: this._connectedDeviceId,
152
+ connectedDeviceName: this._connectedDeviceName,
153
+ settings: { ...this._settings },
154
+ recordingState: this._recordingState,
155
+ isRecording: this.isRecording,
156
+ error: this._error,
157
+ };
158
+ }
159
+ // ===========================================================================
160
+ // Adapter Management
161
+ // ===========================================================================
162
+ /**
163
+ * Set the BLE adapter to use.
164
+ * Must be called before connect() if not provided in constructor.
165
+ */
166
+ setAdapter(adapter) {
167
+ this.ensureNotDisposed();
168
+ if (this.isConnected) {
169
+ throw new Error('Cannot change adapter while connected');
170
+ }
171
+ this.adapter = adapter;
172
+ }
173
+ /**
174
+ * Get the current adapter.
175
+ */
176
+ getAdapter() {
177
+ return this.adapter;
178
+ }
179
+ // ===========================================================================
180
+ // Discovery
181
+ // ===========================================================================
182
+ /**
183
+ * Scan for Voltra devices.
184
+ *
185
+ * Note: In browser environments, this triggers the Web Bluetooth device picker.
186
+ * The returned array will contain only the user-selected device.
187
+ *
188
+ * @param options Scan options
189
+ * @returns Array of discovered Voltra devices
190
+ */
191
+ async scan(options = {}) {
192
+ this.ensureNotDisposed();
193
+ this.ensureAdapter();
194
+ const { timeout = 10000, filterVoltra = true } = options;
195
+ const devices = await this.adapter.scan(timeout);
196
+ return filterVoltra ? (0, device_filter_1.filterVoltraDevices)(devices) : devices;
197
+ }
198
+ // ===========================================================================
199
+ // Connection
200
+ // ===========================================================================
201
+ /**
202
+ * Connect to a Voltra device.
203
+ * Handles BLE connection, authentication, and initialization.
204
+ *
205
+ * @param device Device to connect to
206
+ */
207
+ async connect(device) {
208
+ this.ensureNotDisposed();
209
+ this.ensureAdapter();
210
+ if (this.isConnected) {
211
+ throw new errors_1.ConnectionError('Already connected to a device', errors_1.ErrorCode.ALREADY_CONNECTED);
212
+ }
213
+ this._error = null;
214
+ this._lastConnectedDevice = device;
215
+ try {
216
+ // Connect
217
+ this.setConnectionState('connecting');
218
+ await this.adapter.connect(device.id);
219
+ // Setup notification handler before auth
220
+ this.setupNotificationHandler();
221
+ // Authenticate
222
+ this.setConnectionState('authenticating');
223
+ await this.authenticate();
224
+ // Initialize
225
+ await this.initialize();
226
+ // Success
227
+ this._connectedDeviceId = device.id;
228
+ this._connectedDeviceName = device.name ?? null;
229
+ this._settings = { ...DEFAULT_SETTINGS };
230
+ this.setConnectionState('connected');
231
+ this.emit({ type: 'connected', deviceId: device.id, deviceName: device.name ?? null });
232
+ // Setup disconnect handler for auto-reconnect
233
+ this.setupDisconnectHandler();
234
+ }
235
+ catch (e) {
236
+ this.cleanup();
237
+ this.setConnectionState('disconnected');
238
+ const error = this.wrapError(e, 'Connection failed');
239
+ this._error = error;
240
+ this.emit({ type: 'error', error });
241
+ throw error;
242
+ }
243
+ }
244
+ /**
245
+ * Disconnect from the current device.
246
+ */
247
+ async disconnect() {
248
+ if (!this._connectedDeviceId) {
249
+ return;
250
+ }
251
+ const deviceId = this._connectedDeviceId;
252
+ try {
253
+ // Stop recording if active
254
+ if (this._recordingState !== 'idle') {
255
+ await this.stopRecording().catch(() => { });
256
+ }
257
+ await this.adapter?.disconnect();
258
+ }
259
+ catch (e) {
260
+ console.warn('[VoltraClient] Disconnect error:', e);
261
+ }
262
+ this.cleanup();
263
+ this.setConnectionState('disconnected');
264
+ this.emit({ type: 'disconnected', deviceId });
265
+ }
266
+ // ===========================================================================
267
+ // Device Settings
268
+ // ===========================================================================
269
+ /**
270
+ * Set weight in pounds.
271
+ *
272
+ * @param lbs Weight (5-200 in increments of 5)
273
+ */
274
+ async setWeight(lbs) {
275
+ this.ensureConnected();
276
+ const cmd = commands_1.WeightCommands.get(lbs);
277
+ if (!cmd) {
278
+ throw new errors_1.InvalidSettingError('weight', lbs, commands_1.WeightCommands.getAvailable());
279
+ }
280
+ try {
281
+ await this.adapter.write(cmd);
282
+ this._settings.weight = lbs;
283
+ }
284
+ catch (e) {
285
+ throw new errors_1.CommandError(`Failed to set weight: ${this.getErrorMessage(e)}`, 'setWeight');
286
+ }
287
+ }
288
+ /**
289
+ * Set chains (reverse resistance) in pounds.
290
+ *
291
+ * @param lbs Chains weight (0-100)
292
+ */
293
+ async setChains(lbs) {
294
+ this.ensureConnected();
295
+ const cmds = commands_1.ChainsCommands.get(lbs);
296
+ if (!cmds) {
297
+ throw new errors_1.InvalidSettingError('chains', lbs, commands_1.ChainsCommands.getAvailable());
298
+ }
299
+ try {
300
+ await this.adapter.write(cmds.step1);
301
+ await (0, utils_1.delay)(constants_1.Timing.DUAL_COMMAND_DELAY_MS);
302
+ await this.adapter.write(cmds.step2);
303
+ this._settings.chains = lbs;
304
+ }
305
+ catch (e) {
306
+ throw new errors_1.CommandError(`Failed to set chains: ${this.getErrorMessage(e)}`, 'setChains');
307
+ }
308
+ }
309
+ /**
310
+ * Set eccentric load adjustment.
311
+ *
312
+ * @param percent Eccentric adjustment (-195 to +195)
313
+ */
314
+ async setEccentric(percent) {
315
+ this.ensureConnected();
316
+ const cmds = commands_1.EccentricCommands.get(percent);
317
+ if (!cmds) {
318
+ throw new errors_1.InvalidSettingError('eccentric', percent, commands_1.EccentricCommands.getAvailable());
319
+ }
320
+ try {
321
+ await this.adapter.write(cmds.step1);
322
+ await (0, utils_1.delay)(constants_1.Timing.DUAL_COMMAND_DELAY_MS);
323
+ await this.adapter.write(cmds.step2);
324
+ this._settings.eccentric = percent;
325
+ }
326
+ catch (e) {
327
+ throw new errors_1.CommandError(`Failed to set eccentric: ${this.getErrorMessage(e)}`, 'setEccentric');
328
+ }
329
+ }
330
+ /**
331
+ * Get available weight values.
332
+ */
333
+ getAvailableWeights() {
334
+ return commands_1.WeightCommands.getAvailable();
335
+ }
336
+ /**
337
+ * Get available chains values.
338
+ */
339
+ getAvailableChains() {
340
+ return commands_1.ChainsCommands.getAvailable();
341
+ }
342
+ /**
343
+ * Get available eccentric values.
344
+ */
345
+ getAvailableEccentric() {
346
+ return commands_1.EccentricCommands.getAvailable();
347
+ }
348
+ // ===========================================================================
349
+ // Recording
350
+ // ===========================================================================
351
+ /**
352
+ * Prepare for recording (sends PREPARE + SETUP commands).
353
+ * Call this before starting a set to minimize latency.
354
+ */
355
+ async prepareRecording() {
356
+ this.ensureConnected();
357
+ try {
358
+ this.setRecordingState('preparing');
359
+ await this.adapter.write(constants_1.Workout.PREPARE);
360
+ await (0, utils_1.delay)(200);
361
+ await this.adapter.write(constants_1.Workout.SETUP);
362
+ await (0, utils_1.delay)(300);
363
+ this.setRecordingState('ready');
364
+ }
365
+ catch (e) {
366
+ this.setRecordingState('idle');
367
+ throw new errors_1.CommandError(`Failed to prepare: ${this.getErrorMessage(e)}`, 'prepareRecording');
368
+ }
369
+ }
370
+ /**
371
+ * Start recording (engage motor).
372
+ * If not prepared, will prepare first.
373
+ */
374
+ async startRecording() {
375
+ this.ensureConnected();
376
+ // Prepare if not ready
377
+ if (this._recordingState !== 'ready') {
378
+ await this.prepareRecording();
379
+ }
380
+ try {
381
+ await this.adapter.write(constants_1.Workout.GO);
382
+ this.setRecordingState('active');
383
+ }
384
+ catch (e) {
385
+ throw new errors_1.CommandError(`Failed to start: ${this.getErrorMessage(e)}`, 'startRecording');
386
+ }
387
+ }
388
+ /**
389
+ * Stop recording (disengage motor and exit workout mode).
390
+ */
391
+ async stopRecording() {
392
+ if (this._recordingState === 'idle') {
393
+ return;
394
+ }
395
+ this.setRecordingState('stopping');
396
+ try {
397
+ if (this.adapter) {
398
+ await this.adapter.write(constants_1.Workout.STOP);
399
+ }
400
+ }
401
+ catch (e) {
402
+ console.warn('[VoltraClient] Stop error:', e);
403
+ }
404
+ this.setRecordingState('idle');
405
+ }
406
+ /**
407
+ * End the current set but stay in workout mode.
408
+ * Use this between sets when there are more sets to do.
409
+ */
410
+ async endSet() {
411
+ if (this._recordingState !== 'active') {
412
+ return;
413
+ }
414
+ try {
415
+ await this.adapter.write(constants_1.Workout.STOP);
416
+ this.setRecordingState('ready');
417
+ }
418
+ catch (e) {
419
+ console.warn('[VoltraClient] End set error:', e);
420
+ }
421
+ }
422
+ // ===========================================================================
423
+ // Event Subscriptions
424
+ // ===========================================================================
425
+ /**
426
+ * Subscribe to client events.
427
+ *
428
+ * @param listener Event listener
429
+ * @returns Unsubscribe function
430
+ */
431
+ subscribe(listener) {
432
+ this.listeners.add(listener);
433
+ return () => this.listeners.delete(listener);
434
+ }
435
+ /**
436
+ * Subscribe to telemetry frames.
437
+ * Shorthand for subscribing to 'frame' events.
438
+ *
439
+ * @param listener Frame listener
440
+ * @returns Unsubscribe function
441
+ */
442
+ onFrame(listener) {
443
+ this.frameListeners.add(listener);
444
+ return () => this.frameListeners.delete(listener);
445
+ }
446
+ /**
447
+ * Subscribe to connection state changes.
448
+ *
449
+ * @param listener State listener
450
+ * @returns Unsubscribe function
451
+ */
452
+ onConnectionStateChange(listener) {
453
+ const wrappedListener = (event) => {
454
+ if (event.type === 'connectionStateChanged') {
455
+ listener(event.state);
456
+ }
457
+ };
458
+ this.listeners.add(wrappedListener);
459
+ return () => this.listeners.delete(wrappedListener);
460
+ }
461
+ // ===========================================================================
462
+ // Lifecycle
463
+ // ===========================================================================
464
+ /**
465
+ * Dispose of the client and release all resources.
466
+ * After calling dispose(), the client cannot be used.
467
+ */
468
+ dispose() {
469
+ if (this.disposed) {
470
+ return;
471
+ }
472
+ this.disposed = true;
473
+ // Disconnect if connected
474
+ if (this.isConnected) {
475
+ this.disconnect().catch(() => { });
476
+ }
477
+ // Clear listeners
478
+ this.listeners.clear();
479
+ this.frameListeners.clear();
480
+ // Cleanup
481
+ this.cleanup();
482
+ }
483
+ // ===========================================================================
484
+ // Private Methods
485
+ // ===========================================================================
486
+ async authenticate() {
487
+ try {
488
+ await this.adapter.write(constants_1.Auth.DEVICE_ID);
489
+ await (0, utils_1.delay)(constants_1.Timing.AUTH_TIMEOUT_MS);
490
+ }
491
+ catch (e) {
492
+ throw new errors_1.AuthenticationError(`Authentication failed: ${this.getErrorMessage(e)}`);
493
+ }
494
+ }
495
+ async initialize() {
496
+ try {
497
+ for (const cmd of constants_1.Init.SEQUENCE) {
498
+ await this.adapter.write(cmd);
499
+ await (0, utils_1.delay)(constants_1.Timing.INIT_COMMAND_DELAY_MS);
500
+ }
501
+ }
502
+ catch (e) {
503
+ throw new errors_1.ConnectionError(`Initialization failed: ${this.getErrorMessage(e)}`);
504
+ }
505
+ }
506
+ setupNotificationHandler() {
507
+ if (!this.adapter)
508
+ return;
509
+ const handler = (data) => {
510
+ const result = (0, telemetry_decoder_1.decodeNotification)(data);
511
+ if (!result)
512
+ return;
513
+ if (result.type === 'frame') {
514
+ this.emit({ type: 'frame', frame: result.frame });
515
+ this.frameListeners.forEach((listener) => listener(result.frame));
516
+ }
517
+ };
518
+ this.notificationUnsubscribe = this.adapter.onNotification(handler);
519
+ }
520
+ setupDisconnectHandler() {
521
+ if (!this.adapter || !this.options.autoReconnect)
522
+ return;
523
+ // Monitor connection state
524
+ const checkConnection = this.adapter.onConnectionStateChange?.((state) => {
525
+ if (state === 'disconnected' && this._connectionState === 'connected') {
526
+ this.handleUnexpectedDisconnect();
527
+ }
528
+ });
529
+ // Store for cleanup if the adapter supports it
530
+ if (checkConnection) {
531
+ const originalUnsubscribe = this.notificationUnsubscribe;
532
+ this.notificationUnsubscribe = () => {
533
+ originalUnsubscribe?.();
534
+ checkConnection();
535
+ };
536
+ }
537
+ }
538
+ async handleUnexpectedDisconnect() {
539
+ if (!this.options.autoReconnect || !this._lastConnectedDevice) {
540
+ this.cleanup();
541
+ this.setConnectionState('disconnected');
542
+ this.emit({ type: 'disconnected', deviceId: this._connectedDeviceId ?? 'unknown' });
543
+ return;
544
+ }
545
+ this._isReconnecting = true;
546
+ this._reconnectAttempt = 0;
547
+ while (this._reconnectAttempt < this.options.maxReconnectAttempts) {
548
+ this._reconnectAttempt++;
549
+ this.emit({
550
+ type: 'reconnecting',
551
+ attempt: this._reconnectAttempt,
552
+ maxAttempts: this.options.maxReconnectAttempts,
553
+ });
554
+ try {
555
+ await (0, utils_1.delay)(this.options.reconnectDelayMs);
556
+ await this.connect(this._lastConnectedDevice);
557
+ this._isReconnecting = false;
558
+ return;
559
+ }
560
+ catch {
561
+ // Continue to next attempt
562
+ }
563
+ }
564
+ // Reconnect failed
565
+ this._isReconnecting = false;
566
+ this.cleanup();
567
+ this.setConnectionState('disconnected');
568
+ this.emit({ type: 'disconnected', deviceId: this._connectedDeviceId ?? 'unknown' });
569
+ }
570
+ cleanup() {
571
+ this.notificationUnsubscribe?.();
572
+ this.notificationUnsubscribe = null;
573
+ this._connectedDeviceId = null;
574
+ this._connectedDeviceName = null;
575
+ this._settings = { ...DEFAULT_SETTINGS };
576
+ this._recordingState = 'idle';
577
+ }
578
+ setConnectionState(state) {
579
+ if (!(0, connection_1.isValidVoltraTransition)(this._connectionState, state)) {
580
+ console.warn(`[VoltraClient] Invalid state transition: ${this._connectionState} -> ${state}`);
581
+ }
582
+ this._connectionState = state;
583
+ this.emit({ type: 'connectionStateChanged', state });
584
+ }
585
+ setRecordingState(state) {
586
+ this._recordingState = state;
587
+ this.emit({ type: 'recordingStateChanged', state });
588
+ }
589
+ emit(event) {
590
+ this.listeners.forEach((listener) => {
591
+ try {
592
+ listener(event);
593
+ }
594
+ catch (e) {
595
+ console.error('[VoltraClient] Event listener error:', e);
596
+ }
597
+ });
598
+ }
599
+ ensureNotDisposed() {
600
+ if (this.disposed) {
601
+ throw new Error('Client has been disposed');
602
+ }
603
+ }
604
+ ensureAdapter() {
605
+ if (!this.adapter) {
606
+ throw new Error('No adapter configured. Call setAdapter() or provide adapter in constructor.');
607
+ }
608
+ }
609
+ ensureConnected() {
610
+ this.ensureNotDisposed();
611
+ if (!this.isConnected) {
612
+ throw new errors_1.NotConnectedError();
613
+ }
614
+ }
615
+ wrapError(e, context) {
616
+ if (e instanceof Error) {
617
+ if (e.message.includes('timeout')) {
618
+ return new errors_1.TimeoutError(`${context}: ${e.message}`, constants_1.Timing.AUTH_TIMEOUT_MS, e);
619
+ }
620
+ if (e.message.includes('auth')) {
621
+ return new errors_1.AuthenticationError(`${context}: ${e.message}`, errors_1.ErrorCode.AUTH_FAILED, e);
622
+ }
623
+ return new errors_1.ConnectionError(`${context}: ${e.message}`, errors_1.ErrorCode.CONNECTION_FAILED, e);
624
+ }
625
+ return new errors_1.ConnectionError(`${context}: ${String(e)}`);
626
+ }
627
+ getErrorMessage(e) {
628
+ return e instanceof Error ? e.message : String(e);
629
+ }
630
+ }
631
+ exports.VoltraClient = VoltraClient;
632
+ //# sourceMappingURL=voltra-client.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"voltra-client.js","sourceRoot":"","sources":["../../../src/sdk/voltra-client.ts"],"names":[],"mappings":"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"}