hypha-rpc 0.1.4 → 0.1.6-post1

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.
package/index.js CHANGED
@@ -1 +1 @@
1
- module.exports = { hyphaWebsocketClient: require("./dist/hypha-rpc-websocket.js"), hyphaSSEClient: require("./dist/hypha-rpc-sse.js") };
1
+ module.exports = { hyphaWebsocketClient: require("./dist/hypha-rpc-websocket.js")};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "hypha-rpc",
3
- "version": "0.1.4",
3
+ "version": "0.1.6-post1",
4
4
  "description": "Hypha RPC client for connecting to Hypha server for data management and AI model serving.",
5
5
  "main": "index.js",
6
6
  "types": "index.d.ts",
package/src/rpc.js CHANGED
@@ -210,7 +210,7 @@ export class RPC extends MessageEmitter {
210
210
  this._emit_message = connection.emit_message.bind(connection);
211
211
  connection.on_message(this._on_message.bind(this));
212
212
  this._connection = connection;
213
- const updateServices = async () => {
213
+ const onConnected = async (connectionInfo) => {
214
214
  if (!this._silent && this._connection.manager_id) {
215
215
  console.log("Connection established, reporting services...");
216
216
  for (let service of Object.values(this._services)) {
@@ -223,12 +223,13 @@ export class RPC extends MessageEmitter {
223
223
  }
224
224
  } else {
225
225
  console.log(
226
- "Connection established, no manager id to report services",
226
+ "Connection established", connectionInfo
227
227
  );
228
228
  }
229
+ this._fire("connected", connectionInfo);
229
230
  };
230
- connection.on_connect(updateServices);
231
- updateServices();
231
+ connection.on_connected(onConnected);
232
+ onConnected();
232
233
  } else {
233
234
  this._emit_message = function () {
234
235
  console.log("No connection to emit message");
@@ -366,7 +367,11 @@ export class RPC extends MessageEmitter {
366
367
  Object.assign(main, extra.value);
367
368
  }
368
369
  this._fire(main["type"], main);
369
- } else {
370
+ }
371
+ else if (typeof message === "object") {
372
+ this._fire(message["type"], message);
373
+ }
374
+ else {
370
375
  throw new Error("Invalid message format");
371
376
  }
372
377
  }
@@ -377,7 +382,7 @@ export class RPC extends MessageEmitter {
377
382
  }
378
383
 
379
384
  async disconnect() {
380
- this._fire("disconnect");
385
+ this._fire("disconnected");
381
386
  await this._connection.disconnect();
382
387
  }
383
388
 
@@ -457,7 +462,7 @@ export class RPC extends MessageEmitter {
457
462
  svc.id = `${provider}:${service_id}`;
458
463
  return svc;
459
464
  } catch (e) {
460
- console.error("Failed to get remote service: " + service_uri, e);
465
+ console.warn("Failed to get remote service: " + service_uri, e);
461
466
  throw e;
462
467
  }
463
468
  }
@@ -769,8 +774,12 @@ export class RPC extends MessageEmitter {
769
774
  emit(main_message, extra_data) {
770
775
  assert(
771
776
  typeof main_message === "object" && main_message.type,
772
- "Invalid message, must be an object with a type field.",
777
+ "Invalid message, must be an object with a `type` fields.",
773
778
  );
779
+ if(!main_message.to) {
780
+ this._fire(main_message.type, main_message);
781
+ return
782
+ }
774
783
  let message_package = msgpack_packb(main_message);
775
784
  if (extra_data) {
776
785
  const extra = msgpack_packb(extra_data);
@@ -6,11 +6,11 @@ class WebRTCConnection {
6
6
  this._data_channel = channel;
7
7
  this._handle_message = null;
8
8
  this._reconnection_token = null;
9
- this._disconnect_handler = null;
10
- this._handle_connect = () => {};
9
+ this._handle_disconnected = null;
10
+ this._handle_connected = () => {};
11
11
  this.manager_id = null;
12
12
  this._data_channel.onopen = async () => {
13
- this._handle_connect && this._handle_connect();
13
+ this._handle_connected && this._handle_connected({channel: this._data_channel});
14
14
  };
15
15
  this._data_channel.onmessage = async (event) => {
16
16
  let data = event.data;
@@ -21,18 +21,18 @@ class WebRTCConnection {
21
21
  };
22
22
  const self = this;
23
23
  this._data_channel.onclose = function () {
24
- if (this._disconnect_handler) this._disconnect_handler("closed");
24
+ if (this._handle_disconnected) this._handle_disconnected("closed");
25
25
  console.log("websocket closed");
26
26
  self._data_channel = null;
27
27
  };
28
28
  }
29
29
 
30
30
  on_disconnected(handler) {
31
- this._disconnect_handler = handler;
31
+ this._handle_disconnected = handler;
32
32
  }
33
33
 
34
- on_connect(handler) {
35
- this._handle_connect = handler;
34
+ on_connected(handler) {
35
+ this._handle_connected = handler;
36
36
  }
37
37
 
38
38
  on_message(handler) {
@@ -14,6 +14,7 @@ class WebsocketRPCConnection {
14
14
  client_id,
15
15
  workspace,
16
16
  token,
17
+ reconnection_token = null,
17
18
  timeout = 60,
18
19
  WebSocketClass = null,
19
20
  ) {
@@ -22,11 +23,11 @@ class WebsocketRPCConnection {
22
23
  this._client_id = client_id;
23
24
  this._workspace = workspace;
24
25
  this._token = token;
25
- this._reconnection_token = null;
26
+ this._reconnection_token = reconnection_token;
26
27
  this._websocket = null;
27
28
  this._handle_message = null;
28
- this._handle_connect = null; // Connection open event handler
29
- this._disconnect_handler = null; // Disconnection event handler
29
+ this._handle_connected = null; // Connection open event handler
30
+ this._handle_disconnected = null; // Disconnection event handler
30
31
  this._timeout = timeout;
31
32
  this._WebSocketClass = WebSocketClass || WebSocket; // Allow overriding the WebSocket class
32
33
  this._closed = false;
@@ -41,12 +42,12 @@ class WebsocketRPCConnection {
41
42
  this._handle_message = handler;
42
43
  }
43
44
 
44
- on_connect(handler) {
45
- this._handle_connect = handler;
45
+ on_connected(handler) {
46
+ this._handle_connected = handler;
46
47
  }
47
48
 
48
49
  on_disconnected(handler) {
49
- this._disconnect_handler = handler;
50
+ this._handle_disconnected = handler;
50
51
  }
51
52
 
52
53
  async _attempt_connection(server_url, attempt_fallback = true) {
@@ -74,8 +75,8 @@ class WebsocketRPCConnection {
74
75
  this._attempt_connection_with_query_params(server_url)
75
76
  .then(resolve)
76
77
  .catch(reject);
77
- } else if (this._disconnect_handler) {
78
- this._disconnect_handler(event.reason);
78
+ } else if (this._handle_disconnected) {
79
+ this._handle_disconnected(event.reason);
79
80
  }
80
81
  };
81
82
  });
@@ -127,15 +128,18 @@ class WebsocketRPCConnection {
127
128
  console.log(
128
129
  `Successfully connected to the server, workspace: ${this.connection_info.workspace}, manager_id: ${this.manager_id}`,
129
130
  );
131
+ if(this.connection_info.announcement){
132
+ console.log(`${this.connection_info.announcement}`);
133
+ }
130
134
  resolve(this.connection_info);
131
135
  } else if (first_message.type == "error") {
132
- const error = first_message.error || "Unknown error";
136
+ const error = "ConnectionAbortedError: " + first_message.message;
133
137
  console.error("Failed to connect, " + error);
134
138
  reject(new Error(error));
135
139
  return;
136
140
  } else {
137
- console.error("Unexpected message received from the server:", data);
138
- reject(new Error("Unexpected message received from the server"));
141
+ console.error("ConnectionAbortedError: Unexpected message received from the server:", data);
142
+ reject(new Error("ConnectionAbortedError: Unexpected message received from the server"));
139
143
  return;
140
144
  }
141
145
  };
@@ -177,8 +181,8 @@ class WebsocketRPCConnection {
177
181
 
178
182
  this._websocket.onclose = this._handle_close.bind(this);
179
183
 
180
- if (this._handle_connect) {
181
- this._handle_connect(this);
184
+ if (this._handle_connected) {
185
+ this._handle_connected(this.connection_info);
182
186
  }
183
187
  return this.connection_info;
184
188
  } catch (error) {
@@ -197,14 +201,12 @@ class WebsocketRPCConnection {
197
201
  this._websocket &&
198
202
  this._websocket.readyState === WebSocket.CLOSED
199
203
  ) {
200
- if ([1000].includes(event.code)) {
204
+ if ([1000, 1001].includes(event.code)) {
201
205
  console.info(
202
- "Websocket connection closed (code: %s): %s",
203
- event.code,
204
- event.reason,
206
+ `Websocket connection closed (code: ${event.code}): ${event.reason}`
205
207
  );
206
- if (this._disconnect_handler) {
207
- this._disconnect_handler(event.reason);
208
+ if (this._handle_disconnected) {
209
+ this._handle_disconnected(event.reason);
208
210
  }
209
211
  this._closed = true;
210
212
  } else if (this._enable_reconnect) {
@@ -216,10 +218,11 @@ class WebsocketRPCConnection {
216
218
  let retry = 0;
217
219
  const reconnect = async () => {
218
220
  try {
219
- console.info(
221
+ console.warn(
220
222
  `Reconnecting to ${this._server_url.split("?")[0]} (attempt #${retry})`,
221
223
  );
222
224
  await this.open();
225
+ console.warn(`Successfully reconnected to server ${this._server_url}`);
223
226
  } catch (e) {
224
227
  if (`${e}`.includes("ConnectionAbortedError")) {
225
228
  console.warn("Failed to reconnect, connection aborted:", e);
@@ -228,7 +231,6 @@ class WebsocketRPCConnection {
228
231
  console.warn("Failed to reconnect, connection aborted:", e);
229
232
  return;
230
233
  }
231
- console.warn("Failed to reconnect:", e);
232
234
  await new Promise((resolve) => setTimeout(resolve, 1000));
233
235
  if (
234
236
  this._websocket &&
@@ -247,8 +249,8 @@ class WebsocketRPCConnection {
247
249
  reconnect();
248
250
  }
249
251
  } else {
250
- if (this._disconnect_handler) {
251
- this._disconnect_handler(event.reason);
252
+ if (this._handle_disconnected) {
253
+ this._handle_disconnected(event.reason);
252
254
  }
253
255
  }
254
256
  }
@@ -293,6 +295,7 @@ export async function login(config) {
293
295
  const service_id = config.login_service_id || "public/*:hypha-login";
294
296
  const timeout = config.login_timeout || 60;
295
297
  const callback = config.login_callback;
298
+ const profile = config.profile;
296
299
 
297
300
  const server = await connectToServer({
298
301
  name: "initial login client",
@@ -300,13 +303,14 @@ export async function login(config) {
300
303
  });
301
304
  try {
302
305
  const svc = await server.get_service(service_id);
306
+ assert(svc, `Failed to get the login service: ${service_id}`);
303
307
  const context = await svc.start();
304
308
  if (callback) {
305
309
  await callback(context);
306
310
  } else {
307
311
  console.log(`Please open your browser and login at ${context.login_url}`);
308
312
  }
309
- return await svc.check(context.key, timeout);
313
+ return await svc.check(context.key, timeout, profile);
310
314
  } catch (error) {
311
315
  throw error;
312
316
  } finally {
@@ -333,6 +337,7 @@ export async function connectToServer(config) {
333
337
  clientId,
334
338
  config.workspace,
335
339
  config.token,
340
+ config.reconnection_token,
336
341
  config.method_timeout || 60,
337
342
  config.WebSocketClass,
338
343
  );
@@ -369,17 +374,13 @@ export async function connectToServer(config) {
369
374
  return await wm.get_service(query + ":default");
370
375
  }
371
376
 
372
- async function disconnect() {
373
- await rpc.disconnect();
374
- await connection.disconnect();
375
- }
376
377
  if (connection_info) {
377
378
  wm.config = Object.assign(wm.config, connection_info);
378
379
  }
379
380
  wm.export = _export;
380
381
  wm.getPlugin = getPlugin;
381
382
  wm.listPlugins = wm.listServices;
382
- wm.disconnect = disconnect;
383
+ wm.disconnect = rpc.disconnect.bind(rpc);
383
384
  wm.registerCodec = rpc.register_codec.bind(rpc);
384
385
  wm.emit = rpc.emit;
385
386
  wm.on = rpc.on;
@@ -387,7 +388,7 @@ export async function connectToServer(config) {
387
388
  rpc.on("force-exit", async (message) => {
388
389
  if (message.from === "*/" + connection.manager_id) {
389
390
  console.log("Disconnecting from server, reason:", message.reason);
390
- await disconnect();
391
+ await rpc.disconnect();
391
392
  }
392
393
  });
393
394
  }
@@ -401,7 +402,9 @@ export async function connectToServer(config) {
401
402
  [undefined, true, false, "auto"].includes(webrtc),
402
403
  "webrtc must be true, false or 'auto'",
403
404
  );
404
- const svc = await _get_service(query);
405
+ // pass other arguments to get_service
406
+ const otherArgs = Array.prototype.slice.call(arguments, 3);
407
+ const svc = await _get_service(query, ...otherArgs);
405
408
  if (webrtc === true || webrtc === "auto") {
406
409
  if (svc.id.includes(":") && svc.id.includes("/")) {
407
410
  const client = svc.id.split(":")[0];