doover-js 0.4.0 → 0.4.1

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.
@@ -243,7 +243,7 @@ class GatewayClient {
243
243
  this.emit("messageCreate", (0, snowflake_1.addTimestampToMessage)(message.d));
244
244
  break;
245
245
  case "MessageUpdate":
246
- this.emit("messageUpdate", (0, snowflake_1.addTimestampToMessage)(message.d));
246
+ this.emit("messageUpdate", (0, snowflake_1.addTimestampToMessage)(message.d.message), message.d.request_data);
247
247
  break;
248
248
  case "AggregateUpdate":
249
249
  this.emit("aggregateUpdate", message.d);
@@ -38,10 +38,20 @@ export interface GatewayMessageCreate extends GatewayMessageBase {
38
38
  t: "MessageCreate";
39
39
  d: Omit<MessageStructure, "timestamp">;
40
40
  }
41
+ /**
42
+ * `message` is the full post-update MessageStructure; `request_data` is the
43
+ * diff of just-changed fields. Consumers should read `message` for the
44
+ * current state and only touch `request_data` if they specifically need to
45
+ * know what changed in this update.
46
+ */
41
47
  export interface GatewayMessageUpdate extends GatewayMessageBase {
42
48
  op: 0;
43
49
  t: "MessageUpdate";
44
- d: Omit<MessageStructure, "timestamp"> & {
50
+ d: {
51
+ channel: ChannelRef;
52
+ author_id: string;
53
+ organisation_id?: string;
54
+ message: Omit<MessageStructure, "timestamp">;
45
55
  request_data: JSONValue;
46
56
  };
47
57
  }
@@ -119,9 +129,7 @@ export interface GatewayListenerMap {
119
129
  ready: (event: GatewayReady["d"]) => void;
120
130
  channelSync: (event: GatewayChannelSync["d"]) => void;
121
131
  messageCreate: (event: MessageStructure) => void;
122
- messageUpdate: (event: GatewayMessageUpdate["d"] & {
123
- timestamp: number;
124
- }) => void;
132
+ messageUpdate: (message: MessageStructure, request_data: JSONValue | undefined) => void;
125
133
  aggregateUpdate: (event: GatewayAggregateUpdate["d"]) => void;
126
134
  alarmTrigger: (event: GatewayAlarmTrigger["d"]) => void;
127
135
  oneShotMessage: (event: GatewayOneShotMessage["d"]) => void;
@@ -1,8 +1,13 @@
1
- import type { Aggregate, MessageStructure } from "../types/common";
1
+ import type { Aggregate, JSONValue, MessageStructure } from "../types/common";
2
2
  import type { ChannelIdentifier } from "../types/viewer";
3
3
  export interface ChannelSubscriptionHandlers {
4
4
  onMessage?: (message: MessageStructure) => void;
5
- onMessageUpdate?: (message: MessageStructure) => void;
5
+ /**
6
+ * Fires on server-side MessageUpdate events. `message` is the full updated
7
+ * MessageStructure; `request_data` (optional) is the diff of what changed
8
+ * in this specific update. Most consumers only need `message`.
9
+ */
10
+ onMessageUpdate?: (message: MessageStructure, request_data?: JSONValue) => void;
6
11
  onAggregate?: (aggregate: Aggregate) => void;
7
12
  }
8
13
  /**
@@ -24,8 +24,8 @@ function useChannelSubscription(identifier, handlers) {
24
24
  const aggregateCallback = (_id, aggregate) => {
25
25
  handlersRef.current.onAggregate?.(aggregate);
26
26
  };
27
- const messageUpdateCallback = (_id, message) => {
28
- handlersRef.current.onMessageUpdate?.(message);
27
+ const messageUpdateCallback = (_id, message, request_data) => {
28
+ handlersRef.current.onMessageUpdate?.(message, request_data);
29
29
  };
30
30
  void client.viewer.subscribeToChannel(identifier, messageCallback, aggregateCallback, messageUpdateCallback);
31
31
  return () => {
@@ -289,36 +289,44 @@ const helpers_1 = require("./helpers");
289
289
  op: 0,
290
290
  t: "MessageUpdate",
291
291
  d: {
292
- id: rpcId,
293
- author_id: "u1",
294
292
  channel: { agent_id: "a1", name: "c1" },
295
- data: {
296
- type: "rpc",
297
- method: "ping",
298
- request: {},
299
- status: { code: "acknowledged", message: { timestamp: 1 } },
300
- response: {},
293
+ author_id: "u1",
294
+ message: {
295
+ id: rpcId,
296
+ author_id: "u1",
297
+ channel: { agent_id: "a1", name: "c1" },
298
+ data: {
299
+ type: "rpc",
300
+ method: "ping",
301
+ request: {},
302
+ status: { code: "acknowledged", message: { timestamp: 1 } },
303
+ response: {},
304
+ },
305
+ attachments: [],
301
306
  },
302
- attachments: [],
303
- request_data: {},
307
+ request_data: { status: { code: "acknowledged", message: { timestamp: 1 } } },
304
308
  },
305
309
  });
306
310
  ws.receive({
307
311
  op: 0,
308
312
  t: "MessageUpdate",
309
313
  d: {
310
- id: rpcId,
311
- author_id: "u1",
312
314
  channel: { agent_id: "a1", name: "c1" },
313
- data: {
314
- type: "rpc",
315
- method: "ping",
316
- request: {},
317
- status: { code: "success" },
318
- response: { pong: true },
315
+ author_id: "u1",
316
+ message: {
317
+ id: rpcId,
318
+ author_id: "u1",
319
+ channel: { agent_id: "a1", name: "c1" },
320
+ data: {
321
+ type: "rpc",
322
+ method: "ping",
323
+ request: {},
324
+ status: { code: "success" },
325
+ response: { pong: true },
326
+ },
327
+ attachments: [],
319
328
  },
320
- attachments: [],
321
- request_data: {},
329
+ request_data: { status: { code: "success" }, response: { pong: true } },
322
330
  },
323
331
  });
324
332
  await (0, chai_1.expect)(promise).to.eventually.deep.equal({ pong: true });
@@ -366,18 +374,22 @@ const helpers_1 = require("./helpers");
366
374
  op: 0,
367
375
  t: "MessageUpdate",
368
376
  d: {
369
- id: rpcId,
370
- author_id: "u1",
371
377
  channel: { agent_id: "a1", name: "c1" },
372
- data: {
373
- type: "rpc",
374
- method: "ping",
375
- request: {},
376
- status: { code: "error", message: "boom" },
377
- response: {},
378
+ author_id: "u1",
379
+ message: {
380
+ id: rpcId,
381
+ author_id: "u1",
382
+ channel: { agent_id: "a1", name: "c1" },
383
+ data: {
384
+ type: "rpc",
385
+ method: "ping",
386
+ request: {},
387
+ status: { code: "error", message: "boom" },
388
+ response: {},
389
+ },
390
+ attachments: [],
378
391
  },
379
- attachments: [],
380
- request_data: {},
392
+ request_data: { status: { code: "error", message: "boom" } },
381
393
  },
382
394
  });
383
395
  await (0, chai_1.expect)(promise).to.eventually.be.rejectedWith("boom");
@@ -115,12 +115,16 @@ const helpers_1 = require("./helpers");
115
115
  op: 0,
116
116
  t: "MessageUpdate",
117
117
  d: {
118
- id,
119
- author_id: "u1",
120
118
  channel: { agent_id: "a1", name: "c1" },
121
- data: {},
122
- attachments: [],
123
- request_data: {},
119
+ author_id: "u1",
120
+ message: {
121
+ id,
122
+ author_id: "u1",
123
+ channel: { agent_id: "a1", name: "c1" },
124
+ data: { full: true },
125
+ attachments: [],
126
+ },
127
+ request_data: { diff: true },
124
128
  },
125
129
  });
126
130
  ws.receive({
@@ -195,7 +199,7 @@ const helpers_1 = require("./helpers");
195
199
  });
196
200
  (0, chai_1.expect)(channelSync.calledOnce).to.equal(true);
197
201
  (0, chai_1.expect)(messageCreate.calledWithMatch(sinon_1.default.match({ id, timestamp: sinon_1.default.match.number }))).to.equal(true);
198
- (0, chai_1.expect)(messageUpdate.calledWithMatch(sinon_1.default.match({ id, timestamp: sinon_1.default.match.number }))).to.equal(true);
202
+ (0, chai_1.expect)(messageUpdate.calledWithMatch(sinon_1.default.match({ id, data: { full: true }, timestamp: sinon_1.default.match.number }), sinon_1.default.match({ diff: true }))).to.equal(true);
199
203
  (0, chai_1.expect)(aggregateUpdate.calledOnce).to.equal(true);
200
204
  (0, chai_1.expect)(alarmTrigger.calledOnce).to.equal(true);
201
205
  (0, chai_1.expect)(oneShot.calledOnce).to.equal(true);
@@ -328,18 +328,22 @@ function wrapper(client) {
328
328
  op: 0,
329
329
  t: "MessageUpdate",
330
330
  d: {
331
- id: rpcId,
332
- author_id: "u1",
333
331
  channel: { agent_id: "a1", name: "ui_cmds" },
334
- data: {
335
- type: "rpc",
336
- method: "ping",
337
- request: {},
338
- status: { code: "success" },
339
- response: { pong: true },
332
+ author_id: "u1",
333
+ message: {
334
+ id: rpcId,
335
+ author_id: "u1",
336
+ channel: { agent_id: "a1", name: "ui_cmds" },
337
+ data: {
338
+ type: "rpc",
339
+ method: "ping",
340
+ request: {},
341
+ status: { code: "success" },
342
+ response: { pong: true },
343
+ },
344
+ attachments: [],
340
345
  },
341
- attachments: [],
342
- request_data: {},
346
+ request_data: { status: { code: "success" }, response: { pong: true } },
343
347
  },
344
348
  });
345
349
  return promise;
@@ -6,12 +6,17 @@ import { MessagesApi, type ListMessagesParams } from "../apis/messages-api";
6
6
  import type { DooverAuth } from "../auth/doover-auth";
7
7
  import { GatewayClient } from "../gateway/gateway-client";
8
8
  import { RestClient, type DooverClientConfig } from "../http/rest-client";
9
- import type { Aggregate, Channel, ConnectionDetails, MessageStructure, RpcRequest, RpcStatus } from "../types/common";
9
+ import type { Aggregate, Channel, ConnectionDetails, JSONValue, MessageStructure, RpcRequest, RpcStatus } from "../types/common";
10
10
  import type { Agent, AgentsResponse, ChannelIdentifier, ChannelsDataProvider, SubscriptionDetails, User } from "../types/viewer";
11
11
  interface SubscriptionEntry {
12
12
  messageCallback: (identifier: ChannelIdentifier, message: MessageStructure) => void;
13
13
  aggregateCallback: (identifier: ChannelIdentifier, aggregate: Aggregate) => void;
14
- messageUpdateCallback?: (identifier: ChannelIdentifier, message: MessageStructure) => void;
14
+ /**
15
+ * `message` is the full post-update MessageStructure (server-side `.message`
16
+ * field). `request_data` is the diff of just-changed fields, or undefined
17
+ * if the server didn't provide one. Most consumers only need `message`.
18
+ */
19
+ messageUpdateCallback?: (identifier: ChannelIdentifier, message: MessageStructure, request_data?: JSONValue) => void;
15
20
  }
16
21
  export declare class DooverDataProvider implements ChannelsDataProvider<ChannelIdentifier> {
17
22
  private readonly config;
@@ -34,10 +34,10 @@ class DooverDataProvider {
34
34
  const identifier = this.toIdentifier(message.channel.agent_id, message.channel.name);
35
35
  this.subscriptions.get(key)?.forEach((entry) => entry.messageCallback(identifier, message));
36
36
  });
37
- this.gateway.on("messageUpdate", (message) => {
37
+ this.gateway.on("messageUpdate", (message, request_data) => {
38
38
  const key = this.channelKey(message.channel.agent_id, message.channel.name);
39
39
  const identifier = this.toIdentifier(message.channel.agent_id, message.channel.name);
40
- this.subscriptions.get(key)?.forEach((entry) => entry.messageUpdateCallback?.(identifier, message));
40
+ this.subscriptions.get(key)?.forEach((entry) => entry.messageUpdateCallback?.(identifier, message, request_data));
41
41
  });
42
42
  this.gateway.on("channelSync", (event) => {
43
43
  const key = this.channelKey(event.channel.agent_id, event.channel.name);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "doover-js",
3
- "version": "0.4.0",
3
+ "version": "0.4.1",
4
4
  "description": "TypeScript client for Doover.",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",