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.
- package/dist/gateway/gateway-client.js +1 -1
- package/dist/gateway/types.d.ts +12 -4
- package/dist/react/useChannelSubscription.d.ts +7 -2
- package/dist/react/useChannelSubscription.js +2 -2
- package/dist/test/doover-data-provider.test.js +42 -30
- package/dist/test/gateway-client.test.js +10 -6
- package/dist/test/react.test.js +14 -10
- package/dist/viewer/doover-data-provider.d.ts +7 -2
- package/dist/viewer/doover-data-provider.js +2 -2
- package/package.json +1 -1
|
@@ -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);
|
package/dist/gateway/types.d.ts
CHANGED
|
@@ -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:
|
|
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: (
|
|
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
|
-
|
|
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
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
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
|
-
|
|
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
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
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
|
-
|
|
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
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
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
|
-
|
|
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
|
-
|
|
122
|
-
|
|
123
|
-
|
|
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);
|
package/dist/test/react.test.js
CHANGED
|
@@ -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
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
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
|
-
|
|
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
|
-
|
|
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);
|