@peers-app/peers-sdk 0.14.0 → 0.15.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 (210) hide show
  1. package/dist/context/data-context.d.ts +4 -4
  2. package/dist/context/data-context.js +1 -1
  3. package/dist/context/index.d.ts +3 -3
  4. package/dist/context/index.js +4 -0
  5. package/dist/context/user-context-singleton.js +13 -14
  6. package/dist/context/user-context.d.ts +4 -4
  7. package/dist/context/user-context.js +48 -31
  8. package/dist/data/assistants.d.ts +1 -1
  9. package/dist/data/assistants.js +35 -24
  10. package/dist/data/change-tracking.d.ts +8 -8
  11. package/dist/data/change-tracking.js +45 -39
  12. package/dist/data/channels.js +5 -5
  13. package/dist/data/data-locks.d.ts +2 -2
  14. package/dist/data/data-locks.js +21 -23
  15. package/dist/data/data-locks.test.js +73 -75
  16. package/dist/data/device-sync-info.d.ts +1 -1
  17. package/dist/data/device-sync-info.js +4 -4
  18. package/dist/data/devices.d.ts +1 -1
  19. package/dist/data/devices.js +9 -12
  20. package/dist/data/embeddings.js +14 -11
  21. package/dist/data/files/file-read-stream.d.ts +2 -2
  22. package/dist/data/files/file-read-stream.js +23 -14
  23. package/dist/data/files/file-write-stream.d.ts +2 -2
  24. package/dist/data/files/file-write-stream.js +8 -8
  25. package/dist/data/files/file.types.d.ts +2 -2
  26. package/dist/data/files/file.types.js +17 -11
  27. package/dist/data/files/files.d.ts +6 -6
  28. package/dist/data/files/files.js +17 -19
  29. package/dist/data/files/files.test.js +213 -214
  30. package/dist/data/files/index.d.ts +4 -4
  31. package/dist/data/files/index.js +4 -4
  32. package/dist/data/group-member-roles.js +2 -2
  33. package/dist/data/group-members.d.ts +5 -5
  34. package/dist/data/group-members.js +27 -18
  35. package/dist/data/group-members.test.js +73 -73
  36. package/dist/data/group-permissions.d.ts +3 -3
  37. package/dist/data/group-permissions.js +13 -11
  38. package/dist/data/group-share.d.ts +2 -2
  39. package/dist/data/group-share.js +29 -24
  40. package/dist/data/groups.d.ts +4 -4
  41. package/dist/data/groups.js +27 -19
  42. package/dist/data/groups.test.js +44 -44
  43. package/dist/data/index.d.ts +6 -6
  44. package/dist/data/index.js +6 -6
  45. package/dist/data/knowledge/peer-types.js +9 -9
  46. package/dist/data/messages.d.ts +5 -5
  47. package/dist/data/messages.js +43 -30
  48. package/dist/data/orm/client-proxy.data-source.d.ts +4 -4
  49. package/dist/data/orm/client-proxy.data-source.js +10 -12
  50. package/dist/data/orm/cursor.d.ts +1 -1
  51. package/dist/data/orm/cursor.js +2 -2
  52. package/dist/data/orm/cursor.test.js +92 -93
  53. package/dist/data/orm/data-query.d.ts +3 -3
  54. package/dist/data/orm/data-query.js +24 -18
  55. package/dist/data/orm/data-query.mongo.d.ts +1 -1
  56. package/dist/data/orm/data-query.mongo.js +49 -51
  57. package/dist/data/orm/data-query.mongo.test.js +173 -204
  58. package/dist/data/orm/data-query.sqlite.d.ts +1 -1
  59. package/dist/data/orm/data-query.sqlite.js +84 -73
  60. package/dist/data/orm/data-query.sqlite.test.js +164 -176
  61. package/dist/data/orm/data-query.test.js +216 -224
  62. package/dist/data/orm/decorators.js +3 -3
  63. package/dist/data/orm/dependency-injection.test.js +53 -56
  64. package/dist/data/orm/doc.d.ts +4 -4
  65. package/dist/data/orm/doc.js +17 -21
  66. package/dist/data/orm/event-registry.d.ts +1 -1
  67. package/dist/data/orm/event-registry.test.js +16 -16
  68. package/dist/data/orm/factory.d.ts +2 -2
  69. package/dist/data/orm/factory.js +33 -33
  70. package/dist/data/orm/index.d.ts +10 -10
  71. package/dist/data/orm/index.js +10 -10
  72. package/dist/data/orm/multi-cursors.d.ts +1 -1
  73. package/dist/data/orm/multi-cursors.js +6 -6
  74. package/dist/data/orm/multi-cursors.test.js +152 -144
  75. package/dist/data/orm/sql.data-source.d.ts +7 -7
  76. package/dist/data/orm/sql.data-source.js +88 -93
  77. package/dist/data/orm/sql.data-source.test.js +109 -101
  78. package/dist/data/orm/subscribable.data-source.d.ts +4 -4
  79. package/dist/data/orm/subscribable.data-source.js +5 -5
  80. package/dist/data/orm/table-container-events.test.js +34 -26
  81. package/dist/data/orm/table-container.d.ts +6 -6
  82. package/dist/data/orm/table-container.js +33 -21
  83. package/dist/data/orm/table-container.test.js +64 -53
  84. package/dist/data/orm/table-definitions.system.d.ts +3 -3
  85. package/dist/data/orm/table-definitions.system.js +3 -3
  86. package/dist/data/orm/table-definitions.type.d.ts +5 -5
  87. package/dist/data/orm/table-dependencies.d.ts +2 -2
  88. package/dist/data/orm/table.d.ts +5 -5
  89. package/dist/data/orm/table.event-source.test.js +105 -115
  90. package/dist/data/orm/table.js +35 -34
  91. package/dist/data/orm/types.d.ts +3 -3
  92. package/dist/data/orm/types.js +26 -25
  93. package/dist/data/orm/types.test.js +166 -92
  94. package/dist/data/package-permissions.d.ts +1 -1
  95. package/dist/data/package-permissions.js +2 -2
  96. package/dist/data/package-version-permissions.d.ts +1 -1
  97. package/dist/data/package-version-permissions.js +2 -2
  98. package/dist/data/package-versions.d.ts +9 -9
  99. package/dist/data/package-versions.js +47 -33
  100. package/dist/data/packages.d.ts +2 -2
  101. package/dist/data/packages.js +36 -18
  102. package/dist/data/packages.utils.d.ts +2 -2
  103. package/dist/data/packages.utils.js +4 -4
  104. package/dist/data/persistent-vars.d.ts +15 -15
  105. package/dist/data/persistent-vars.js +165 -154
  106. package/dist/data/table-definitions-table.d.ts +5 -5
  107. package/dist/data/table-definitions-table.js +13 -12
  108. package/dist/data/tool-tests.js +6 -6
  109. package/dist/data/tools.js +29 -19
  110. package/dist/data/user-permissions.d.ts +1 -1
  111. package/dist/data/user-permissions.js +5 -5
  112. package/dist/data/user-permissions.test.js +90 -88
  113. package/dist/data/user-trust-levels.js +10 -10
  114. package/dist/data/users.d.ts +4 -4
  115. package/dist/data/users.js +16 -15
  116. package/dist/data/voice-messages.d.ts +2 -2
  117. package/dist/data/voice-messages.js +13 -13
  118. package/dist/data/welcome-modal.pvar.js +3 -1
  119. package/dist/data/workflow-logs.js +26 -18
  120. package/dist/data/workflow-runs.d.ts +6 -6
  121. package/dist/data/workflow-runs.js +70 -44
  122. package/dist/data/workflows.d.ts +2 -2
  123. package/dist/data/workflows.js +7 -9
  124. package/dist/device/binary-peer-connection-v2.d.ts +7 -7
  125. package/dist/device/binary-peer-connection-v2.js +32 -28
  126. package/dist/device/binary-peer-connection-v2.test.js +80 -67
  127. package/dist/device/binary-peer-connection.d.ts +7 -7
  128. package/dist/device/binary-peer-connection.js +29 -28
  129. package/dist/device/binary-peer-connection.test.js +35 -31
  130. package/dist/device/connection.d.ts +5 -5
  131. package/dist/device/connection.js +59 -48
  132. package/dist/device/connection.test.js +74 -68
  133. package/dist/device/device-election.d.ts +2 -2
  134. package/dist/device/device-election.js +25 -20
  135. package/dist/device/device-election.test.js +35 -36
  136. package/dist/device/device.d.ts +2 -2
  137. package/dist/device/device.js +10 -4
  138. package/dist/device/device.test.js +16 -17
  139. package/dist/device/get-trust-level-fn.d.ts +2 -2
  140. package/dist/device/get-trust-level-fn.js +22 -11
  141. package/dist/device/get-trust-level-fn.test.js +58 -58
  142. package/dist/device/socket-io-binary-peer.d.ts +1 -1
  143. package/dist/device/socket-io-binary-peer.js +16 -13
  144. package/dist/device/socket.type.d.ts +2 -2
  145. package/dist/device/streamed-socket.d.ts +2 -2
  146. package/dist/device/streamed-socket.js +8 -8
  147. package/dist/device/streamed-socket.test.js +40 -40
  148. package/dist/device/tx-encoding.test.js +77 -77
  149. package/dist/events.d.ts +1 -1
  150. package/dist/events.js +5 -2
  151. package/dist/group-invite/group-invite.js +110 -19
  152. package/dist/group-invite/group-invite.pvars.d.ts +2 -2
  153. package/dist/group-invite/group-invite.pvars.js +21 -13
  154. package/dist/group-invite/group-invite.types.d.ts +1 -1
  155. package/dist/group-invite/index.d.ts +3 -3
  156. package/dist/group-invite/index.js +1 -1
  157. package/dist/index.d.ts +25 -24
  158. package/dist/index.js +30 -25
  159. package/dist/keys.d.ts +3 -3
  160. package/dist/keys.js +31 -30
  161. package/dist/keys.test.js +69 -61
  162. package/dist/logging/console-logger.d.ts +1 -1
  163. package/dist/logging/console-logger.js +35 -40
  164. package/dist/logging/console-logger.test.js +115 -115
  165. package/dist/logging/console-logs.table.d.ts +3 -3
  166. package/dist/logging/console-logs.table.js +28 -23
  167. package/dist/mentions.js +16 -12
  168. package/dist/observable.d.ts +2 -2
  169. package/dist/observable.js +15 -9
  170. package/dist/observable.test.js +47 -47
  171. package/dist/package-loader/get-require.js +3 -4
  172. package/dist/package-loader/package-loader.d.ts +2 -2
  173. package/dist/package-loader/package-loader.js +52 -34
  174. package/dist/peers-ui/peers-ui.d.ts +2 -2
  175. package/dist/peers-ui/peers-ui.js +2 -4
  176. package/dist/peers-ui/peers-ui.types.d.ts +3 -3
  177. package/dist/peers-ui/peers-ui.types.js +0 -1
  178. package/dist/rpc-types.d.ts +61 -59
  179. package/dist/rpc-types.js +61 -55
  180. package/dist/serial-json.d.ts +1 -1
  181. package/dist/serial-json.js +50 -43
  182. package/dist/serial-json.test.js +22 -22
  183. package/dist/system-ids.js +8 -8
  184. package/dist/tools/index.d.ts +1 -1
  185. package/dist/tools/tools-factory.d.ts +1 -1
  186. package/dist/tools/tools-factory.js +2 -2
  187. package/dist/types/assistant-runner-args.d.ts +3 -3
  188. package/dist/types/peer-device.d.ts +1 -1
  189. package/dist/types/peers-package.d.ts +3 -3
  190. package/dist/types/workflow-logger.d.ts +1 -1
  191. package/dist/types/workflow-run-context.d.ts +4 -4
  192. package/dist/types/workflow.d.ts +4 -4
  193. package/dist/types/workflow.js +27 -14
  194. package/dist/types/zod-types.d.ts +2 -1
  195. package/dist/types/zod-types.js +9 -3
  196. package/dist/user-connect/connection-code.d.ts +1 -1
  197. package/dist/user-connect/connection-code.js +7 -7
  198. package/dist/user-connect/connection-code.test.js +106 -106
  199. package/dist/user-connect/index.d.ts +3 -3
  200. package/dist/user-connect/index.js +1 -1
  201. package/dist/user-connect/user-connect.pvars.js +13 -11
  202. package/dist/user-connect/user-connect.types.d.ts +3 -3
  203. package/dist/users.query.d.ts +2 -2
  204. package/dist/users.query.js +40 -30
  205. package/dist/utils.d.ts +2 -2
  206. package/dist/utils.js +34 -32
  207. package/dist/utils.test.js +12 -8
  208. package/dist/workflow-log-formatter.d.ts +1 -1
  209. package/dist/workflow-log-formatter.js +17 -18
  210. package/package.json +14 -8
@@ -1,7 +1,7 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- const utils_1 = require("../utils");
4
3
  const keys_1 = require("../keys");
4
+ const utils_1 = require("../utils");
5
5
  const connection_1 = require("./connection");
6
6
  const device_1 = require("./device");
7
7
  function createTestSocket(localHandlers, remoteHandlers) {
@@ -17,7 +17,7 @@ function createTestSocket(localHandlers, remoteHandlers) {
17
17
  on(eventName, handler) {
18
18
  localHandlers.push({
19
19
  eventName,
20
- handler: async (...args) => handler(...args)
20
+ handler: async (...args) => handler(...args),
21
21
  });
22
22
  },
23
23
  removeAllListeners(eventName) {
@@ -28,7 +28,7 @@ function createTestSocket(localHandlers, remoteHandlers) {
28
28
  },
29
29
  disconnect() {
30
30
  // Simulate disconnection logic if needed
31
- }
31
+ },
32
32
  };
33
33
  return socket;
34
34
  }
@@ -51,35 +51,35 @@ describe(connection_1.Connection, () => {
51
51
  const clientDevice = new device_1.Device();
52
52
  const serverDevice = new device_1.Device();
53
53
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
54
- const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ['localhost']);
54
+ const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ["localhost"]);
55
55
  expect(clientConnection.connectionId).toBe(serverConnection.connectionId);
56
- const response = await clientConnection.doHandshake('localhost');
56
+ const response = await clientConnection.doHandshake("localhost");
57
57
  expect(response.userId).toBe(serverDevice.userId);
58
58
  expect(response.deviceId).toBe(serverDevice.deviceId);
59
59
  expect(response.publicKey).toBe(serverDevice.publicKey);
60
60
  expect(response.publicBoxKey).toBe(serverDevice.publicBoxKey);
61
- expect(response.serverAddress).toBe('localhost');
61
+ expect(response.serverAddress).toBe("localhost");
62
62
  expect(response.connectionId).toBe(serverConnection.connectionId);
63
- serverConnection.removeAllListeners('ping');
64
- serverConnection.exposeRPC('ping', async (n, s) => `pong - ${n}, ${s}`);
65
- const pong = await clientConnection.emit('ping', 1, "hello");
66
- expect(pong).toBe('pong - 1, hello');
63
+ serverConnection.removeAllListeners("ping");
64
+ serverConnection.exposeRPC("ping", async (n, s) => `pong - ${n}, ${s}`);
65
+ const pong = await clientConnection.emit("ping", 1, "hello");
66
+ expect(pong).toBe("pong - 1, hello");
67
67
  });
68
68
  it("should create a new id if socket doesn't have one", async () => {
69
69
  const socket = {
70
70
  id: (0, utils_1.newid)(),
71
- emit(eventName, args, callback) {
71
+ emit(_eventName, _args, _callback) {
72
72
  // do nothing
73
73
  },
74
- on(eventName, handler) {
74
+ on(_eventName, _handler) {
75
75
  // do nothing
76
76
  },
77
- removeAllListeners(eventName) {
77
+ removeAllListeners(_eventName) {
78
78
  // do nothing
79
79
  },
80
80
  disconnect() {
81
81
  // do nothing
82
- }
82
+ },
83
83
  };
84
84
  const connection = new connection_1.Connection(socket, new device_1.Device());
85
85
  expect(connection.connectionId).toBeTruthy();
@@ -89,11 +89,11 @@ describe(connection_1.Connection, () => {
89
89
  const clientDevice = new device_1.Device();
90
90
  const serverDevice = new device_1.Device();
91
91
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
92
- const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ['https://localhost']);
93
- await clientConnection.doHandshake('https://localhost');
92
+ const _serverConnection = new connection_1.Connection(serverSocket, serverDevice, ["https://localhost"]);
93
+ await clientConnection.doHandshake("https://localhost");
94
94
  expect(clientConnection.encryptTraffic).toBe(false);
95
95
  // and allow forcing insecure
96
- clientConnection.overrideEncryption = 'encrypt-traffic-regardless-of-protocol';
96
+ clientConnection.overrideEncryption = "encrypt-traffic-regardless-of-protocol";
97
97
  expect(clientConnection.encryptTraffic).toBe(true);
98
98
  // and only return a copy of the remoteDeviceInfo
99
99
  expect(clientConnection.remoteDeviceInfo).not.toBe(clientConnection.remoteDeviceInfo);
@@ -103,13 +103,15 @@ describe(connection_1.Connection, () => {
103
103
  const clientDevice = new device_1.Device();
104
104
  const serverDevice = new device_1.Device();
105
105
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
106
- const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ['https://localhost']);
107
- await clientConnection.doHandshake('https://localhost');
106
+ const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ["https://localhost"]);
107
+ await clientConnection.doHandshake("https://localhost");
108
108
  expect(clientConnection.encryptTraffic).toBe(false);
109
109
  expect(serverConnection.encryptTraffic).toBe(false);
110
- serverConnection.removeAllListeners('ping');
111
- serverConnection.exposeRPC('ping', async () => { throw new Error("fake error"); });
112
- const response = await clientConnection.emit('ping').catch((err) => err);
110
+ serverConnection.removeAllListeners("ping");
111
+ serverConnection.exposeRPC("ping", async () => {
112
+ throw new Error("fake error");
113
+ });
114
+ const response = await clientConnection.emit("ping").catch((err) => err);
113
115
  expect(response).toEqual({
114
116
  errorType: "RPC_ERROR",
115
117
  error: "fake error",
@@ -120,13 +122,15 @@ describe(connection_1.Connection, () => {
120
122
  const clientDevice = new device_1.Device();
121
123
  const serverDevice = new device_1.Device();
122
124
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
123
- const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ['http://localhost']);
124
- await clientConnection.doHandshake('http://localhost');
125
+ const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ["http://localhost"]);
126
+ await clientConnection.doHandshake("http://localhost");
125
127
  expect(clientConnection.encryptTraffic).toBe(true);
126
128
  expect(serverConnection.encryptTraffic).toBe(true);
127
- serverConnection.removeAllListeners('ping');
128
- serverConnection.exposeRPC('ping', async () => { throw new Error("fake error"); });
129
- const response = await clientConnection.emit('ping').catch((err) => err);
129
+ serverConnection.removeAllListeners("ping");
130
+ serverConnection.exposeRPC("ping", async () => {
131
+ throw new Error("fake error");
132
+ });
133
+ const response = await clientConnection.emit("ping").catch((err) => err);
130
134
  expect(response).toEqual({
131
135
  errorType: "RPC_ERROR",
132
136
  error: "fake error",
@@ -137,74 +141,74 @@ describe(connection_1.Connection, () => {
137
141
  const clientDevice = new device_1.Device();
138
142
  const serverDevice = new device_1.Device();
139
143
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
140
- const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ['https://localhost']);
141
- serverConnection.exposeRPC('ping', async () => 'pong');
144
+ const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ["https://localhost"]);
145
+ serverConnection.exposeRPC("ping", async () => "pong");
142
146
  expect(serverConnection.verified).toBe(false);
143
147
  expect(clientConnection.verified).toBe(false);
144
- const response = await clientConnection.emit('ping').catch((err) => err);
148
+ const response = await clientConnection.emit("ping").catch((err) => err);
145
149
  expect(response).toMatch(/Connection not verified/);
146
150
  });
147
151
  it("client should detect different connection ids during handshake", async () => {
148
- const serverAddress = 'http://localhost';
152
+ const serverAddress = "http://localhost";
149
153
  const { clientSocket, serverSocket } = createTestSocketPair();
150
154
  const clientDevice = new device_1.Device();
151
155
  const serverDevice = new device_1.Device();
152
156
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
153
157
  const serverConnection = new connection_1.Connection(serverSocket, serverDevice, [serverAddress]);
154
- serverConnection.exposeRPC('ping', async () => 'pong');
155
- serverConnection.socket.removeAllListeners('completeHandshake');
156
- serverConnection.exposeRPC('completeHandshake', async (handshakeBox) => {
158
+ serverConnection.exposeRPC("ping", async () => "pong");
159
+ serverConnection.socket.removeAllListeners("completeHandshake");
160
+ serverConnection.exposeRPC("completeHandshake", async (handshakeBox) => {
157
161
  const handshake = await serverConnection.completeHandshake(handshakeBox);
158
- handshake.connectionId = 'fake';
162
+ handshake.connectionId = "fake";
159
163
  return handshake;
160
164
  });
161
165
  const result = await clientConnection.doHandshake(serverAddress).catch((err) => String(err));
162
166
  expect(result).toMatch(/Invalid connectionId/);
163
167
  });
164
168
  it("client should detect different device ids during handshake", async () => {
165
- const serverAddress = 'http://localhost';
169
+ const serverAddress = "http://localhost";
166
170
  const { clientSocket, serverSocket } = createTestSocketPair();
167
171
  const clientDevice = new device_1.Device();
168
172
  const serverDevice = new device_1.Device();
169
173
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
170
174
  const serverConnection = new connection_1.Connection(serverSocket, serverDevice, [serverAddress]);
171
- serverConnection.exposeRPC('ping', async () => 'pong');
172
- serverConnection.socket.removeAllListeners('completeHandshake');
173
- serverConnection.exposeRPC('completeHandshake', async (handshakeBox) => {
175
+ serverConnection.exposeRPC("ping", async () => "pong");
176
+ serverConnection.socket.removeAllListeners("completeHandshake");
177
+ serverConnection.exposeRPC("completeHandshake", async (handshakeBox) => {
174
178
  const handshake = await serverConnection.completeHandshake(handshakeBox);
175
- handshake.deviceId = 'fake';
179
+ handshake.deviceId = "fake";
176
180
  return handshake;
177
181
  });
178
182
  const result = await clientConnection.doHandshake(serverAddress).catch((err) => String(err));
179
183
  expect(result).toMatch(/Inconsistent device info/);
180
184
  });
181
185
  it("client should detect different device ids during handshake", async () => {
182
- const serverAddress = 'http://localhost';
186
+ const serverAddress = "http://localhost";
183
187
  const { clientSocket, serverSocket } = createTestSocketPair();
184
188
  const clientDevice = new device_1.Device();
185
189
  const serverDevice = new device_1.Device();
186
190
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
187
191
  const serverConnection = new connection_1.Connection(serverSocket, serverDevice, [serverAddress]);
188
- serverConnection.exposeRPC('ping', async () => 'pong');
189
- serverConnection.socket.removeAllListeners('completeHandshake');
190
- serverConnection.exposeRPC('completeHandshake', async (handshakeBox) => {
192
+ serverConnection.exposeRPC("ping", async () => "pong");
193
+ serverConnection.socket.removeAllListeners("completeHandshake");
194
+ serverConnection.exposeRPC("completeHandshake", async (handshakeBox) => {
191
195
  const handshake = await serverConnection.completeHandshake(handshakeBox);
192
- handshake.userId = 'fake';
196
+ handshake.userId = "fake";
193
197
  return handshake;
194
198
  });
195
199
  const result = await clientConnection.doHandshake(serverAddress).catch((err) => String(err));
196
200
  expect(result).toMatch(/Inconsistent device info/);
197
201
  });
198
202
  it("client should detect different box key during handshake", async () => {
199
- const serverAddress = 'http://localhost';
203
+ const serverAddress = "http://localhost";
200
204
  const { clientSocket, serverSocket } = createTestSocketPair();
201
205
  const clientDevice = new device_1.Device();
202
206
  const serverDevice = new device_1.Device();
203
207
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
204
208
  const serverConnection = new connection_1.Connection(serverSocket, serverDevice, [serverAddress]);
205
- serverConnection.exposeRPC('ping', async () => 'pong');
206
- serverConnection.socket.removeAllListeners('completeHandshake');
207
- serverConnection.exposeRPC('completeHandshake', async (handshakeBox) => {
209
+ serverConnection.exposeRPC("ping", async () => "pong");
210
+ serverConnection.socket.removeAllListeners("completeHandshake");
211
+ serverConnection.exposeRPC("completeHandshake", async (handshakeBox) => {
208
212
  const handshake = await serverConnection.completeHandshake(handshakeBox);
209
213
  const _keys = (0, keys_1.newKeys)();
210
214
  handshake.publicBoxKey = _keys.publicBoxKey;
@@ -214,15 +218,15 @@ describe(connection_1.Connection, () => {
214
218
  expect(result).toMatch(/Inconsistent public keys/);
215
219
  });
216
220
  it("client should detect different public key during handshake", async () => {
217
- const serverAddress = 'http://localhost';
221
+ const serverAddress = "http://localhost";
218
222
  const { clientSocket, serverSocket } = createTestSocketPair();
219
223
  const clientDevice = new device_1.Device();
220
224
  const serverDevice = new device_1.Device();
221
225
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
222
226
  const serverConnection = new connection_1.Connection(serverSocket, serverDevice, [serverAddress]);
223
- serverConnection.exposeRPC('ping', async () => 'pong');
224
- serverConnection.socket.removeAllListeners('completeHandshake');
225
- serverConnection.exposeRPC('completeHandshake', async (handshakeBox) => {
227
+ serverConnection.exposeRPC("ping", async () => "pong");
228
+ serverConnection.socket.removeAllListeners("completeHandshake");
229
+ serverConnection.exposeRPC("completeHandshake", async (handshakeBox) => {
226
230
  const handshake = await serverConnection.completeHandshake(handshakeBox);
227
231
  const _keys = (0, keys_1.newKeys)();
228
232
  handshake.publicKey = _keys.publicKey;
@@ -236,21 +240,21 @@ describe(connection_1.Connection, () => {
236
240
  const clientDevice = new device_1.Device();
237
241
  const serverDevice = new device_1.Device();
238
242
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
239
- const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ['localhost']);
240
- await clientConnection.doHandshake('localhost');
243
+ const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ["localhost"]);
244
+ await clientConnection.doHandshake("localhost");
241
245
  // Create large data
242
246
  const largeData = {
243
247
  message: "A".repeat(500),
244
248
  metadata: "B".repeat(300),
245
- payload: "C".repeat(400)
249
+ payload: "C".repeat(400),
246
250
  };
247
- serverConnection.exposeRPC('processLargeData', async (data) => {
251
+ serverConnection.exposeRPC("processLargeData", async (data) => {
248
252
  return {
249
253
  received: data,
250
- processedSize: JSON.stringify(data).length
254
+ processedSize: JSON.stringify(data).length,
251
255
  };
252
256
  });
253
- const result = await clientConnection.emit('processLargeData', largeData);
257
+ const result = await clientConnection.emit("processLargeData", largeData);
254
258
  expect(result.received.message).toBe("A".repeat(500));
255
259
  expect(result.received.metadata).toBe("B".repeat(300));
256
260
  expect(result.received.payload).toBe("C".repeat(400));
@@ -261,18 +265,20 @@ describe(connection_1.Connection, () => {
261
265
  const clientDevice = new device_1.Device();
262
266
  const serverDevice = new device_1.Device();
263
267
  const clientConnection = new connection_1.Connection(clientSocket, clientDevice);
264
- const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ['localhost']);
268
+ const serverConnection = new connection_1.Connection(serverSocket, serverDevice, ["localhost"]);
265
269
  // Set a very strict timestamp tolerance (1 second) to make test reliable
266
270
  serverConnection.handshakeTimestampToleranceMs = 1000;
267
271
  // Mock the client device to send an old timestamp
268
272
  const originalGetHandshake = clientDevice.getHandshake.bind(clientDevice);
269
- clientDevice.getHandshake = function (connectionId, serverAddress) {
273
+ clientDevice.getHandshake = (connectionId, serverAddress) => {
270
274
  const handshake = originalGetHandshake(connectionId, serverAddress);
271
275
  // Make timestamp 2 seconds in the past (beyond tolerance)
272
276
  handshake.contents.timestamp = Date.now() - 2000;
273
277
  return handshake;
274
278
  };
275
- const result = await clientConnection.doHandshake('localhost').catch((err) => err.message || err.error || String(err));
279
+ const result = await clientConnection
280
+ .doHandshake("localhost")
281
+ .catch((err) => err.message || err.error || String(err));
276
282
  expect(result).toMatch(/Remote device's system clock is too far out of sync/);
277
283
  });
278
284
  it.todo("should handle RPC calls that return undefined");
@@ -289,9 +295,9 @@ describe(connection_1.Connection, () => {
289
295
  // Fix: after openSignedObject succeeds, assert
290
296
  // signedHandshake.publicKey === signedHandshake.contents.publicKey
291
297
  //
292
- describe('Security: key confusion — signing key vs claimed identity key', () => {
293
- it('rejects handshake where signing key (KA) differs from claimed identity key in contents (KV)', async () => {
294
- const serverAddress = 'http://localhost';
298
+ describe("Security: key confusion — signing key vs claimed identity key", () => {
299
+ it("rejects handshake where signing key (KA) differs from claimed identity key in contents (KV)", async () => {
300
+ const serverAddress = "http://localhost";
295
301
  const { clientSocket, serverSocket } = createTestSocketPair();
296
302
  const attackerDevice = new device_1.Device();
297
303
  const victimDevice = new device_1.Device(); // identity the attacker wants to impersonate
@@ -307,7 +313,7 @@ describe(connection_1.Connection, () => {
307
313
  // the attacker can decrypt it to finish the
308
314
  // handshake — making the whole flow succeed)
309
315
  const originalGetHandshake = attackerDevice.getHandshake.bind(attackerDevice);
310
- attackerDevice.getHandshake = function (connectionId, addr) {
316
+ attackerDevice.getHandshake = (connectionId, addr) => {
311
317
  const real = originalGetHandshake(connectionId, addr);
312
318
  const maliciousContents = {
313
319
  ...real.contents, // keep connectionId, timestamp, serverAddress
@@ -325,8 +331,8 @@ describe(connection_1.Connection, () => {
325
331
  // claimed identity key in the payload contents (KV).
326
332
  // Server-side errors travel back through the RPC layer as plain objects
327
333
  // { error: '...', errorType: 'RPC_ERROR' } rather than Error instances.
328
- const result = await attackerConnection.doHandshake(serverAddress).catch(err => err);
329
- const errorMessage = result instanceof Error ? result.message : result?.error ?? String(result);
334
+ const result = await attackerConnection.doHandshake(serverAddress).catch((err) => err);
335
+ const errorMessage = result instanceof Error ? result.message : (result?.error ?? String(result));
330
336
  expect(errorMessage).toMatch(/signing key does not match claimed identity key/i);
331
337
  // Neither side should be left in a verified state
332
338
  expect(attackerConnection.verified).toBe(false);
@@ -1,10 +1,10 @@
1
- import { IDeviceConnection, INetworkInfo } from "../types/peer-device";
1
+ import type { IDeviceConnection, INetworkInfo } from "../types/peer-device";
2
2
  export interface IElectionData {
3
3
  deviceId: string;
4
4
  myConnections: IDeviceConnection[];
5
5
  allNetworkInfo: INetworkInfo[];
6
6
  }
7
- export declare function electDevices({ deviceId, myConnections, allNetworkInfo, }: IElectionData): {
7
+ export declare function electDevices({ deviceId, myConnections, allNetworkInfo }: IElectionData): {
8
8
  preferredDeviceIds: string[];
9
9
  preferredByDeviceIds: string[];
10
10
  };
@@ -3,19 +3,22 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.electDevices = electDevices;
4
4
  exports.getLeastPreferredConnection = getLeastPreferredConnection;
5
5
  const lodash_1 = require("lodash");
6
- function electDevices({ deviceId, myConnections, allNetworkInfo, }) {
6
+ function electDevices({ deviceId, myConnections, allNetworkInfo }) {
7
7
  const allDeviceIdsSet = new Set();
8
8
  const _preferredByDeviceIdsSet = new Set();
9
- const allConnectionInfos = allNetworkInfo.map(networkInfo => {
10
- const deviceIds = [networkInfo.deviceId, ...networkInfo.connections.map(c => c.deviceId)];
11
- deviceIds.forEach(id => allDeviceIdsSet.add(id));
9
+ const allConnectionInfos = allNetworkInfo.map((networkInfo) => {
10
+ const deviceIds = [networkInfo.deviceId, ...networkInfo.connections.map((c) => c.deviceId)];
11
+ deviceIds.forEach((id) => {
12
+ allDeviceIdsSet.add(id);
13
+ });
12
14
  allDeviceIdsSet.add(networkInfo.deviceId);
13
15
  if (networkInfo.preferredDeviceIds.includes(deviceId)) {
14
16
  _preferredByDeviceIdsSet.add(networkInfo.deviceId);
15
17
  }
16
- const preferredByDeviceIds = allNetworkInfo.filter(n => n.preferredDeviceIds.includes(networkInfo.deviceId))
17
- .map(n => n.deviceId);
18
- const myConnection = myConnections.find(c => c.deviceId === networkInfo.deviceId);
18
+ const preferredByDeviceIds = allNetworkInfo
19
+ .filter((n) => n.preferredDeviceIds.includes(networkInfo.deviceId))
20
+ .map((n) => n.deviceId);
21
+ const myConnection = myConnections.find((c) => c.deviceId === networkInfo.deviceId);
19
22
  return {
20
23
  ...networkInfo,
21
24
  myConnection,
@@ -25,25 +28,27 @@ function electDevices({ deviceId, myConnections, allNetworkInfo, }) {
25
28
  });
26
29
  allDeviceIdsSet.delete(deviceId);
27
30
  const preferredConnections = [];
28
- let sortedConnections = allConnectionInfos.filter(c => c.myConnection);
31
+ let sortedConnections = allConnectionInfos.filter((c) => c.myConnection);
29
32
  while (allDeviceIdsSet.size && sortedConnections.length) {
30
33
  // sort connections (best will be first)
31
34
  sortedConnections = sortConnections({
32
35
  myDeviceId: deviceId,
33
36
  connections: sortedConnections,
34
- unconnectedDeviceIds: allDeviceIdsSet
37
+ unconnectedDeviceIds: allDeviceIdsSet,
35
38
  });
36
39
  const connection = sortedConnections.shift();
37
40
  if (connection) {
38
41
  preferredConnections.push(connection.myConnection);
39
- connection.connectedDeviceIds.forEach(id => allDeviceIdsSet.delete(id));
42
+ connection.connectedDeviceIds.forEach((id) => {
43
+ allDeviceIdsSet.delete(id);
44
+ });
40
45
  }
41
46
  else {
42
47
  break;
43
48
  }
44
49
  }
45
50
  return {
46
- preferredDeviceIds: preferredConnections.map(c => c.deviceId),
51
+ preferredDeviceIds: preferredConnections.map((c) => c.deviceId),
47
52
  preferredByDeviceIds: Array.from(_preferredByDeviceIdsSet),
48
53
  };
49
54
  }
@@ -57,8 +62,8 @@ function electDevices({ deviceId, myConnections, allNetworkInfo, }) {
57
62
  function sortConnections({ myDeviceId, connections, unconnectedDeviceIds }) {
58
63
  // sort by latency * error rate (smaller is better)
59
64
  connections.sort((a, b) => {
60
- const aLatency = (a.myConnection.latencyMs || 1) * (a.myConnection.errorRate || 0.00001);
61
- const bLatency = (b.myConnection.latencyMs || 1) * (b.myConnection.errorRate || 0.00001);
65
+ const aLatency = (a.myConnection?.latencyMs || 1) * (a.myConnection?.errorRate || 0.00001);
66
+ const bLatency = (b.myConnection?.latencyMs || 1) * (b.myConnection?.errorRate || 0.00001);
62
67
  return aLatency - bLatency;
63
68
  });
64
69
  // sort by preferred by other devices count (higher is better)
@@ -69,8 +74,8 @@ function sortConnections({ myDeviceId, connections, unconnectedDeviceIds }) {
69
74
  });
70
75
  // sort by links to new devices - in general, this is most important except for the later edge-cases
71
76
  connections.sort((a, b) => {
72
- const linksToDeviceA = a.connectedDeviceIds.filter(id => unconnectedDeviceIds.has(id)).length;
73
- const linksToDeviceB = b.connectedDeviceIds.filter(id => unconnectedDeviceIds.has(id)).length;
77
+ const linksToDeviceA = a.connectedDeviceIds.filter((id) => unconnectedDeviceIds.has(id)).length;
78
+ const linksToDeviceB = b.connectedDeviceIds.filter((id) => unconnectedDeviceIds.has(id)).length;
74
79
  return linksToDeviceB - linksToDeviceA;
75
80
  });
76
81
  //=============================================
@@ -89,8 +94,8 @@ function sortConnections({ myDeviceId, connections, unconnectedDeviceIds }) {
89
94
  // prefer devices that have a connection back to me
90
95
  // I think this is an artifact of testing and in the real world this should be a no-op (connections should be bidirectional)
91
96
  connections.sort((a, b) => {
92
- const aHasConn = a.connections.some(c => c.deviceId === myDeviceId);
93
- const bHasConn = b.connections.some(c => c.deviceId === myDeviceId);
97
+ const aHasConn = a.connections.some((c) => c.deviceId === myDeviceId);
98
+ const bHasConn = b.connections.some((c) => c.deviceId === myDeviceId);
94
99
  if (aHasConn && !bHasConn)
95
100
  return -1;
96
101
  if (!aHasConn && bHasConn)
@@ -101,14 +106,14 @@ function sortConnections({ myDeviceId, connections, unconnectedDeviceIds }) {
101
106
  }
102
107
  function getLeastPreferredConnection({ connections, preferredDeviceIds, preferredByDeviceIds, }) {
103
108
  // first consider connections that are not critical to me and I'm not critical to them
104
- let candidates = connections.filter(c => !(preferredByDeviceIds.includes(c.deviceId) || preferredDeviceIds.includes(c.deviceId)));
109
+ let candidates = connections.filter((c) => !(preferredByDeviceIds.includes(c.deviceId) || preferredDeviceIds.includes(c.deviceId)));
105
110
  if (!candidates.length) {
106
111
  // if none, next consider connections that are not critical to me
107
- candidates = connections.filter(c => !preferredDeviceIds.includes(c.deviceId));
112
+ candidates = connections.filter((c) => !preferredDeviceIds.includes(c.deviceId));
108
113
  }
109
114
  if (!candidates.length) {
110
115
  // if none, next consider connections that I am not critical to
111
- candidates = connections.filter(c => !preferredByDeviceIds.includes(c.deviceId));
116
+ candidates = connections.filter((c) => !preferredByDeviceIds.includes(c.deviceId));
112
117
  }
113
118
  if (!candidates.length) {
114
119
  // if none, then just consider all connections
@@ -1,8 +1,8 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- const device_election_1 = require("./device-election");
4
- const utils_1 = require("../utils");
5
3
  const lodash_1 = require("lodash");
4
+ const utils_1 = require("../utils");
5
+ const device_election_1 = require("./device-election");
6
6
  describe("device-election", () => {
7
7
  const createConnection = (deviceId, latencyMs = 10, errorRate = 0.001) => ({
8
8
  deviceId,
@@ -41,9 +41,7 @@ describe("device-election", () => {
41
41
  createConnection(device2),
42
42
  createConnection(device3),
43
43
  ]);
44
- const networkInfo2 = createNetworkInfo(device2, [
45
- createConnection(device1),
46
- ]);
44
+ const networkInfo2 = createNetworkInfo(device2, [createConnection(device1)]);
47
45
  const result = (0, device_election_1.electDevices)({
48
46
  deviceId: myDeviceId,
49
47
  myConnections: [myConnection1, myConnection2],
@@ -120,9 +118,7 @@ describe("device-election", () => {
120
118
  createConnection(device4),
121
119
  ]);
122
120
  // device2 only connects to device3
123
- const networkInfo2 = createNetworkInfo(device2, [
124
- createConnection(device3),
125
- ]);
121
+ const networkInfo2 = createNetworkInfo(device2, [createConnection(device3)]);
126
122
  const result = (0, device_election_1.electDevices)({
127
123
  deviceId: myDeviceId,
128
124
  myConnections: [myConnection1, myConnection2],
@@ -170,9 +166,7 @@ describe("device-election", () => {
170
166
  const myConnection1 = createConnection(device1);
171
167
  const myConnection2 = createConnection(device2);
172
168
  // device1 has a connection back to me
173
- const networkInfo1 = createNetworkInfo(device1, [
174
- createConnection(myDeviceId),
175
- ]);
169
+ const networkInfo1 = createNetworkInfo(device1, [createConnection(myDeviceId)]);
176
170
  // device2 doesn't have a connection back to me
177
171
  const networkInfo2 = createNetworkInfo(device2, []);
178
172
  const result = (0, device_election_1.electDevices)({
@@ -316,7 +310,7 @@ describe("device-election", () => {
316
310
  });
317
311
  });
318
312
  describe("Network simulations", () => {
319
- it.skip('should work as connections grow', () => {
313
+ it.skip("should work as connections grow", () => {
320
314
  const MAX_CONNECTIONS = 100;
321
315
  const groupId = (0, utils_1.newid)();
322
316
  const deviceInfos = [];
@@ -329,10 +323,10 @@ describe("device-election", () => {
329
323
  };
330
324
  deviceInfos.push(newDevice);
331
325
  }
332
- function removeDevice(d) {
326
+ function _removeDevice(d) {
333
327
  deviceInfos.splice(deviceInfos.indexOf(d), 1);
334
- d.connections.forEach(c => {
335
- const d2 = deviceInfos.find(d2 => d2.deviceId === c.deviceId);
328
+ d.connections.forEach((c) => {
329
+ const d2 = deviceInfos.find((d2) => d2.deviceId === c.deviceId);
336
330
  if (d2) {
337
331
  disconnectDevices(d, d2);
338
332
  }
@@ -344,7 +338,7 @@ describe("device-election", () => {
344
338
  return;
345
339
  }
346
340
  // already connected
347
- if (d1.connections.some(c => c.deviceId === d2.deviceId)) {
341
+ if (d1.connections.some((c) => c.deviceId === d2.deviceId)) {
348
342
  return;
349
343
  }
350
344
  d1.connections.push({
@@ -361,15 +355,19 @@ describe("device-election", () => {
361
355
  });
362
356
  }
363
357
  function disconnectDevices(d1, d2) {
364
- d1.connections = d1.connections.filter(c => c.deviceId !== d2.deviceId);
365
- d2.connections = d2.connections.filter(c => c.deviceId !== d1.deviceId);
366
- d1.preferredByDeviceIds = d1.preferredByDeviceIds.filter(id => id !== d2.deviceId);
367
- d2.preferredByDeviceIds = d2.preferredByDeviceIds.filter(id => id !== d1.deviceId);
368
- d1.preferredDeviceIds = d1.preferredDeviceIds.filter(id => id !== d2.deviceId);
369
- d2.preferredDeviceIds = d2.preferredDeviceIds.filter(id => id !== d1.deviceId);
358
+ d1.connections = d1.connections.filter((c) => c.deviceId !== d2.deviceId);
359
+ d2.connections = d2.connections.filter((c) => c.deviceId !== d1.deviceId);
360
+ d1.preferredByDeviceIds = d1.preferredByDeviceIds.filter((id) => id !== d2.deviceId);
361
+ d2.preferredByDeviceIds = d2.preferredByDeviceIds.filter((id) => id !== d1.deviceId);
362
+ d1.preferredDeviceIds = d1.preferredDeviceIds.filter((id) => id !== d2.deviceId);
363
+ d2.preferredDeviceIds = d2.preferredDeviceIds.filter((id) => id !== d1.deviceId);
370
364
  }
371
365
  // pre-populate with devices
372
- Array(25).fill(undefined).forEach(() => addDevice());
366
+ Array(25)
367
+ .fill(undefined)
368
+ .forEach(() => {
369
+ addDevice();
370
+ });
373
371
  const totalTicks = 200;
374
372
  for (let tick = 0; tick < totalTicks; tick++) {
375
373
  addDevice();
@@ -381,28 +379,29 @@ describe("device-election", () => {
381
379
  // }
382
380
  // // randomly disconnect
383
381
  // if (Math.random() < 0.1) {
384
- // const disconnect =
385
- // disconnectDevices()
382
+ // const disconnect =
383
+ // disconnectDevices()
386
384
  // }
387
385
  // simulate a device wanting to maintain a "well connected" network
388
386
  while (device.connections.length < 25) {
389
- const otherPreferredIds = device.connections.map(c => deviceInfos.find(d => d.deviceId === c.deviceId)?.preferredDeviceIds ?? []).flat();
390
- const newDeviceId = otherPreferredIds.find(deviceId => !device.connections.some(c => c.deviceId == deviceId) && deviceId !== device.deviceId);
391
- const newDevice = deviceInfos.find(d => d.deviceId === newDeviceId);
387
+ const otherPreferredIds = device.connections.flatMap((c) => deviceInfos.find((d) => d.deviceId === c.deviceId)?.preferredDeviceIds ?? []);
388
+ const newDeviceId = otherPreferredIds.find((deviceId) => !device.connections.some((c) => c.deviceId === deviceId) &&
389
+ deviceId !== device.deviceId);
390
+ const newDevice = deviceInfos.find((d) => d.deviceId === newDeviceId);
392
391
  if (newDevice) {
393
392
  connectDevices(device, newDevice);
394
393
  }
395
394
  else {
396
- const unconnectedDevices = deviceInfos.filter(d => !device.connections.some(c => c.deviceId === d.deviceId));
395
+ const unconnectedDevices = deviceInfos.filter((d) => !device.connections.some((c) => c.deviceId === d.deviceId));
397
396
  connectDevices(device, (0, lodash_1.shuffle)(unconnectedDevices)[0]);
398
397
  }
399
398
  }
400
399
  // do elections
401
- const networkInfo = device.connections.map(c => {
402
- const remoteDevice = deviceInfos.find(d => d.deviceId === c.deviceId);
400
+ const networkInfo = device.connections.map((c) => {
401
+ const remoteDevice = deviceInfos.find((d) => d.deviceId === c.deviceId);
403
402
  return {
404
403
  deviceId: remoteDevice.deviceId,
405
- connections: [...remoteDevice?.connections],
404
+ connections: [...remoteDevice.connections],
406
405
  connectionSlotsAvailable: MAX_CONNECTIONS - remoteDevice.connections.length,
407
406
  cpuPercent: 0.1,
408
407
  memPercent: 0.2,
@@ -413,23 +412,23 @@ describe("device-election", () => {
413
412
  const result = (0, device_election_1.electDevices)({
414
413
  deviceId: device.deviceId,
415
414
  myConnections: [...device.connections],
416
- allNetworkInfo: networkInfo
415
+ allNetworkInfo: networkInfo,
417
416
  });
418
417
  device.preferredDeviceIds = result.preferredDeviceIds;
419
418
  device.preferredByDeviceIds = result.preferredByDeviceIds;
420
419
  // now that we've done elections, remove connections if we have too many (note this is slightly unrealistic as this usually happens before elections in the real code)
421
420
  while (device.connections.length >= MAX_CONNECTIONS) {
422
421
  const removeConn = (0, device_election_1.getLeastPreferredConnection)({
423
- connections: device.connections.map(c => ({ ...c, groups: [groupId] })),
422
+ connections: device.connections.map((c) => ({ ...c, groups: [groupId] })),
424
423
  preferredDeviceIds: [...device.preferredDeviceIds],
425
424
  preferredByDeviceIds: [...device.preferredByDeviceIds],
426
425
  });
427
- const disconnectDevice = deviceInfos.find(d => d.deviceId === removeConn?.deviceId);
426
+ const disconnectDevice = deviceInfos.find((d) => d.deviceId === removeConn?.deviceId);
428
427
  disconnectDevices(device, disconnectDevice);
429
428
  }
430
429
  }
431
430
  }
432
- const output = (0, lodash_1.sortBy)(deviceInfos, d => -d.preferredByDeviceIds.length).map(d => {
431
+ const output = (0, lodash_1.sortBy)(deviceInfos, (d) => -d.preferredByDeviceIds.length).map((d) => {
433
432
  return {
434
433
  preferredBy: d.preferredByDeviceIds.length,
435
434
  preferred: d.preferredDeviceIds.length,
@@ -1,5 +1,5 @@
1
- import { IDataBox, ISignedObject } from "../keys";
2
- import { IDeviceHandshake, IDeviceInfo } from "../data";
1
+ import type { IDeviceHandshake, IDeviceInfo } from "../data";
2
+ import { type IDataBox, type ISignedObject } from "../keys";
3
3
  export declare class Device implements IDeviceInfo {
4
4
  readonly userId: string;
5
5
  readonly deviceId: string;