clarion-shared-types 1.0.113 → 1.0.115
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/cjs/modules/chat/index.js +1 -0
- package/dist/cjs/modules/chat/index.js.map +1 -1
- package/dist/cjs/modules/chat/interfaces/chat-analytics.js +35 -0
- package/dist/cjs/modules/chat/interfaces/chat-analytics.js.map +1 -0
- package/dist/cjs/modules/notification/index.js +2 -0
- package/dist/cjs/modules/notification/index.js.map +1 -1
- package/dist/cjs/modules/notification/interfaces/notification-analytics.js +27 -0
- package/dist/cjs/modules/notification/interfaces/notification-analytics.js.map +1 -0
- package/dist/cjs/modules/permission/enums/permission-actions.enum.js +6 -0
- package/dist/cjs/modules/permission/enums/permission-actions.enum.js.map +1 -1
- package/dist/esm/modules/chat/index.js +1 -0
- package/dist/esm/modules/chat/index.js.map +1 -1
- package/dist/esm/modules/chat/interfaces/chat-analytics.js +34 -0
- package/dist/esm/modules/chat/interfaces/chat-analytics.js.map +1 -0
- package/dist/esm/modules/notification/index.js +2 -0
- package/dist/esm/modules/notification/index.js.map +1 -1
- package/dist/esm/modules/notification/interfaces/notification-analytics.js +26 -0
- package/dist/esm/modules/notification/interfaces/notification-analytics.js.map +1 -0
- package/dist/esm/modules/permission/enums/permission-actions.enum.js +6 -0
- package/dist/esm/modules/permission/enums/permission-actions.enum.js.map +1 -1
- package/dist/types/modules/chat/index.d.ts +1 -0
- package/dist/types/modules/chat/interfaces/chat-analytics.d.ts +275 -0
- package/dist/types/modules/notification/index.d.ts +1 -0
- package/dist/types/modules/notification/interfaces/notification-analytics.d.ts +273 -0
- package/dist/types/modules/permission/enums/permission-actions.enum.d.ts +2 -0
- package/package.json +45 -45
|
@@ -25,6 +25,7 @@ __exportStar(require("./interfaces/chat-conversation-with-participants"), export
|
|
|
25
25
|
__exportStar(require("./interfaces/chat-message"), exports);
|
|
26
26
|
__exportStar(require("./interfaces/chat-participant"), exports);
|
|
27
27
|
__exportStar(require("./interfaces/chat-presence-info"), exports);
|
|
28
|
+
__exportStar(require("./interfaces/chat-analytics"), exports);
|
|
28
29
|
// constants
|
|
29
30
|
__exportStar(require("./constants/chat-ws-events"), exports);
|
|
30
31
|
__exportStar(require("./constants/chat-room-names"), exports);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/modules/chat/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,QAAQ;AACR,wEAAsD;AACtD,sEAAoD;AACpD,iEAA+C;AAC/C,qEAAmD;AAEnD,aAAa;AACb,iEAA+C;AAC/C,mFAAiE;AACjE,4DAA0C;AAC1C,gEAA8C;AAC9C,kEAAgD;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/modules/chat/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,QAAQ;AACR,wEAAsD;AACtD,sEAAoD;AACpD,iEAA+C;AAC/C,qEAAmD;AAEnD,aAAa;AACb,iEAA+C;AAC/C,mFAAiE;AACjE,4DAA0C;AAC1C,gEAA8C;AAC9C,kEAAgD;AAChD,8DAA4C;AAE5C,YAAY;AACZ,6DAA2C;AAC3C,8DAA4C"}
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Chat analytics (the admin's Chat Analytics): how the conversations on Clarion went over
|
|
4
|
+
* a period - incident chats, Follow Me chats and direct chats - how much was written and
|
|
5
|
+
* by whom, and above all how quickly a member who wrote was answered.
|
|
6
|
+
*
|
|
7
|
+
* One read, computed by clarion-chat from one consistent snapshot, with who each person
|
|
8
|
+
* is from clarion-authentication. Counts, rates and durations only: never a message, a
|
|
9
|
+
* member's name or a trip's label. The only people named are STAFF - the control room,
|
|
10
|
+
* responders and administrators - as agents are on the support analytics.
|
|
11
|
+
*
|
|
12
|
+
* DURATIONS ARE IN SECONDS, like every analytics contract.
|
|
13
|
+
*
|
|
14
|
+
* How it is counted:
|
|
15
|
+
* - A conversation belongs to the organization, control centre and country of the
|
|
16
|
+
* person who STARTED it: the member who raised the SOS, the traveller on a Follow Me
|
|
17
|
+
* trip, the administrator who opened a direct chat. clarion-chat keeps no organization
|
|
18
|
+
* of its own. Everything written in a conversation is its organization's, whoever
|
|
19
|
+
* wrote it - a guardian, or a responder from another organization.
|
|
20
|
+
* - What a conversation is for (`ChatAnalyticsContext`): INCIDENT is an incident's chat,
|
|
21
|
+
* including a Follow Me chat that an SOS adopted; FOLLOW_ME a trip's; DIRECT one person
|
|
22
|
+
* to another; GROUP any other group.
|
|
23
|
+
* - Who writes (`ChatAnalyticsSenderKind`), from the roles a person holds NOW: anybody
|
|
24
|
+
* with a control-centre role is the CONTROL_ROOM, then RESPONDER, then ADMINISTRATOR
|
|
25
|
+
* (organization roles, Super-Admin) - together, STAFF. Everybody else is a MEMBER: the
|
|
26
|
+
* people the service is for, their guardians included. UNKNOWN is an account that no
|
|
27
|
+
* longer exists. Whoever started an incident's or a Follow Me chat from the app is its
|
|
28
|
+
* MEMBER there, whatever else they hold - staff raise SOSes too.
|
|
29
|
+
* - A member's TURN starts with a member's message that opens a conversation or follows
|
|
30
|
+
* a staff message. It is ANSWERED by the first staff message after it, and the wait is
|
|
31
|
+
* the time between. Turns started in the period, answered whenever.
|
|
32
|
+
* - System messages are counted on their own and never take part in a turn.
|
|
33
|
+
*/
|
|
34
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
35
|
+
//# sourceMappingURL=chat-analytics.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chat-analytics.js","sourceRoot":"","sources":["../../../../../src/modules/chat/interfaces/chat-analytics.ts"],"names":[],"mappings":";AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG"}
|
|
@@ -31,4 +31,6 @@ __exportStar(require("./interfaces/notification-dispatch-result"), exports);
|
|
|
31
31
|
__exportStar(require("./interfaces/organization-notification-settings.dto"), exports);
|
|
32
32
|
// Utilities
|
|
33
33
|
__exportStar(require("./utils/notification-sender.util"), exports);
|
|
34
|
+
// Notification Analytics (GET /notifications/admin/analytics)
|
|
35
|
+
__exportStar(require("./interfaces/notification-analytics"), exports);
|
|
34
36
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/modules/notification/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,QAAQ;AACR,oEAAkD;AAClD,iEAA+C;AAC/C,mEAAiD;AACjD,2EAAyD;AACzD,uEAAqD;AACrD,sEAAoD;AAEpD,4CAA4C;AAC5C,gEAA8C;AAC9C,kEAAgD;AAChD,+DAA6C;AAC7C,iEAA+C;AAC/C,4EAA0D;AAE1D,kEAAkE;AAClE,sFAAoE;AAEpE,YAAY;AACZ,mEAAiD"}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/modules/notification/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,QAAQ;AACR,oEAAkD;AAClD,iEAA+C;AAC/C,mEAAiD;AACjD,2EAAyD;AACzD,uEAAqD;AACrD,sEAAoD;AAEpD,4CAA4C;AAC5C,gEAA8C;AAC9C,kEAAgD;AAChD,+DAA6C;AAC7C,iEAA+C;AAC/C,4EAA0D;AAE1D,kEAAkE;AAClE,sFAAoE;AAEpE,YAAY;AACZ,mEAAiD;AAEjD,8DAA8D;AAC9D,sEAAoD"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Notification analytics (the admin's Notification Analytics): what Clarion sent people
|
|
4
|
+
* over a period, on every channel - push to the app, the console's in-app notifications,
|
|
5
|
+
* SMS and email - whether it got through, whether it was opened, and how many people a
|
|
6
|
+
* push can reach at all.
|
|
7
|
+
*
|
|
8
|
+
* One read, computed by clarion-notification from one consistent snapshot, with who each
|
|
9
|
+
* recipient is from clarion-authentication. Counts, rates and durations only: never a
|
|
10
|
+
* title, a message, a phone number or an address.
|
|
11
|
+
*
|
|
12
|
+
* DURATIONS ARE IN SECONDS, like every analytics contract.
|
|
13
|
+
*
|
|
14
|
+
* How it is counted:
|
|
15
|
+
* - Everything by when it was CREATED - the moment Clarion decided to tell somebody.
|
|
16
|
+
* - Whose it is: the organization recorded on it; for a push, the organization of the
|
|
17
|
+
* post it announces, then the recipient's; for an SMS, the recipient's. Older SMS and
|
|
18
|
+
* email (before 21 September 2026) recorded no organization and often no recipient:
|
|
19
|
+
* those are counted only in the platform view (`unattributed`).
|
|
20
|
+
* - Got through: accepted by the provider - Firebase for a push, the SMS gateway, the
|
|
21
|
+
* mail service - or, in the console, delivered. Nothing reports whether an SMS or an
|
|
22
|
+
* email was read, so only push (tapped) and in-app (read) have an open rate.
|
|
23
|
+
* - A country narrows push, in-app and devices by the recipient's country and SMS by
|
|
24
|
+
* the number's; email has no country and is never narrowed.
|
|
25
|
+
*/
|
|
26
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
27
|
+
//# sourceMappingURL=notification-analytics.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"notification-analytics.js","sourceRoot":"","sources":["../../../../../src/modules/notification/interfaces/notification-analytics.ts"],"names":[],"mappings":";AAAA;;;;;;;;;;;;;;;;;;;;;;;GAuBG"}
|
|
@@ -54,6 +54,9 @@ var PermissionActions;
|
|
|
54
54
|
PermissionActions["READ_INCIDENT"] = "read:incident";
|
|
55
55
|
PermissionActions["UPDATE_INCIDENT"] = "update:incident";
|
|
56
56
|
PermissionActions["DELETE_INCIDENT"] = "delete:incident";
|
|
57
|
+
// Chat Analytics: how the chats went and how quickly members were answered - totals
|
|
58
|
+
// only. Held by exactly the roles that read the user analytics.
|
|
59
|
+
PermissionActions["READ_CHAT_ANALYTICS"] = "read:chat-analytics";
|
|
57
60
|
PermissionActions["CREATE_INCIDENT_CATEGORY_TYPE"] = "create:incident-category-type";
|
|
58
61
|
PermissionActions["READ_INCIDENT_CATEGORY_TYPE"] = "read:incident-category-type";
|
|
59
62
|
PermissionActions["UPDATE_INCIDENT_CATEGORY_TYPE"] = "update:incident-category-type";
|
|
@@ -125,6 +128,9 @@ var PermissionActions;
|
|
|
125
128
|
// emails are branded, the address they are sent from, and the sender ID its
|
|
126
129
|
// SMS arrive under - one family per thing configured. Mirrors grm-shared-library.
|
|
127
130
|
PermissionActions["READ_NOTIFICATION_BRANDING"] = "read:notification-branding";
|
|
131
|
+
// Notification Analytics: what went out on every channel and whether it got
|
|
132
|
+
// through - totals only. Held by exactly the roles that read the notification settings.
|
|
133
|
+
PermissionActions["READ_NOTIFICATION_ANALYTICS"] = "read:notification-analytics";
|
|
128
134
|
PermissionActions["UPDATE_NOTIFICATION_BRANDING"] = "update:notification-branding";
|
|
129
135
|
PermissionActions["CREATE_NOTIFICATION_EMAIL_SENDER"] = "create:notification-email-sender";
|
|
130
136
|
PermissionActions["READ_NOTIFICATION_EMAIL_SENDER"] = "read:notification-email-sender";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"permission-actions.enum.js","sourceRoot":"","sources":["../../../../../src/modules/permission/enums/permission-actions.enum.ts"],"names":[],"mappings":";;;AAAA,IAAY,
|
|
1
|
+
{"version":3,"file":"permission-actions.enum.js","sourceRoot":"","sources":["../../../../../src/modules/permission/enums/permission-actions.enum.ts"],"names":[],"mappings":"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"}
|
|
@@ -9,6 +9,7 @@ export * from './interfaces/chat-conversation-with-participants';
|
|
|
9
9
|
export * from './interfaces/chat-message';
|
|
10
10
|
export * from './interfaces/chat-participant';
|
|
11
11
|
export * from './interfaces/chat-presence-info';
|
|
12
|
+
export * from './interfaces/chat-analytics';
|
|
12
13
|
// constants
|
|
13
14
|
export * from './constants/chat-ws-events';
|
|
14
15
|
export * from './constants/chat-room-names';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/modules/chat/index.ts"],"names":[],"mappings":"AAAA,QAAQ;AACR,cAAc,uCAAuC,CAAC;AACtD,cAAc,qCAAqC,CAAC;AACpD,cAAc,gCAAgC,CAAC;AAC/C,cAAc,oCAAoC,CAAC;AAEnD,aAAa;AACb,cAAc,gCAAgC,CAAC;AAC/C,cAAc,kDAAkD,CAAC;AACjE,cAAc,2BAA2B,CAAC;AAC1C,cAAc,+BAA+B,CAAC;AAC9C,cAAc,iCAAiC,CAAC;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/modules/chat/index.ts"],"names":[],"mappings":"AAAA,QAAQ;AACR,cAAc,uCAAuC,CAAC;AACtD,cAAc,qCAAqC,CAAC;AACpD,cAAc,gCAAgC,CAAC;AAC/C,cAAc,oCAAoC,CAAC;AAEnD,aAAa;AACb,cAAc,gCAAgC,CAAC;AAC/C,cAAc,kDAAkD,CAAC;AACjE,cAAc,2BAA2B,CAAC;AAC1C,cAAc,+BAA+B,CAAC;AAC9C,cAAc,iCAAiC,CAAC;AAChD,cAAc,6BAA6B,CAAC;AAE5C,YAAY;AACZ,cAAc,4BAA4B,CAAC;AAC3C,cAAc,6BAA6B,CAAC"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Chat analytics (the admin's Chat Analytics): how the conversations on Clarion went over
|
|
3
|
+
* a period - incident chats, Follow Me chats and direct chats - how much was written and
|
|
4
|
+
* by whom, and above all how quickly a member who wrote was answered.
|
|
5
|
+
*
|
|
6
|
+
* One read, computed by clarion-chat from one consistent snapshot, with who each person
|
|
7
|
+
* is from clarion-authentication. Counts, rates and durations only: never a message, a
|
|
8
|
+
* member's name or a trip's label. The only people named are STAFF - the control room,
|
|
9
|
+
* responders and administrators - as agents are on the support analytics.
|
|
10
|
+
*
|
|
11
|
+
* DURATIONS ARE IN SECONDS, like every analytics contract.
|
|
12
|
+
*
|
|
13
|
+
* How it is counted:
|
|
14
|
+
* - A conversation belongs to the organization, control centre and country of the
|
|
15
|
+
* person who STARTED it: the member who raised the SOS, the traveller on a Follow Me
|
|
16
|
+
* trip, the administrator who opened a direct chat. clarion-chat keeps no organization
|
|
17
|
+
* of its own. Everything written in a conversation is its organization's, whoever
|
|
18
|
+
* wrote it - a guardian, or a responder from another organization.
|
|
19
|
+
* - What a conversation is for (`ChatAnalyticsContext`): INCIDENT is an incident's chat,
|
|
20
|
+
* including a Follow Me chat that an SOS adopted; FOLLOW_ME a trip's; DIRECT one person
|
|
21
|
+
* to another; GROUP any other group.
|
|
22
|
+
* - Who writes (`ChatAnalyticsSenderKind`), from the roles a person holds NOW: anybody
|
|
23
|
+
* with a control-centre role is the CONTROL_ROOM, then RESPONDER, then ADMINISTRATOR
|
|
24
|
+
* (organization roles, Super-Admin) - together, STAFF. Everybody else is a MEMBER: the
|
|
25
|
+
* people the service is for, their guardians included. UNKNOWN is an account that no
|
|
26
|
+
* longer exists. Whoever started an incident's or a Follow Me chat from the app is its
|
|
27
|
+
* MEMBER there, whatever else they hold - staff raise SOSes too.
|
|
28
|
+
* - A member's TURN starts with a member's message that opens a conversation or follows
|
|
29
|
+
* a staff message. It is ANSWERED by the first staff message after it, and the wait is
|
|
30
|
+
* the time between. Turns started in the period, answered whenever.
|
|
31
|
+
* - System messages are counted on their own and never take part in a turn.
|
|
32
|
+
*/
|
|
33
|
+
export {};
|
|
34
|
+
//# sourceMappingURL=chat-analytics.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"chat-analytics.js","sourceRoot":"","sources":["../../../../../src/modules/chat/interfaces/chat-analytics.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG"}
|
|
@@ -15,4 +15,6 @@ export * from './interfaces/notification-dispatch-result';
|
|
|
15
15
|
export * from './interfaces/organization-notification-settings.dto';
|
|
16
16
|
// Utilities
|
|
17
17
|
export * from './utils/notification-sender.util';
|
|
18
|
+
// Notification Analytics (GET /notifications/admin/analytics)
|
|
19
|
+
export * from './interfaces/notification-analytics';
|
|
18
20
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/modules/notification/index.ts"],"names":[],"mappings":"AAAA,QAAQ;AACR,cAAc,mCAAmC,CAAC;AAClD,cAAc,gCAAgC,CAAC;AAC/C,cAAc,kCAAkC,CAAC;AACjD,cAAc,0CAA0C,CAAC;AACzD,cAAc,sCAAsC,CAAC;AACrD,cAAc,qCAAqC,CAAC;AAEpD,4CAA4C;AAC5C,cAAc,+BAA+B,CAAC;AAC9C,cAAc,iCAAiC,CAAC;AAChD,cAAc,8BAA8B,CAAC;AAC7C,cAAc,gCAAgC,CAAC;AAC/C,cAAc,2CAA2C,CAAC;AAE1D,kEAAkE;AAClE,cAAc,qDAAqD,CAAC;AAEpE,YAAY;AACZ,cAAc,kCAAkC,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/modules/notification/index.ts"],"names":[],"mappings":"AAAA,QAAQ;AACR,cAAc,mCAAmC,CAAC;AAClD,cAAc,gCAAgC,CAAC;AAC/C,cAAc,kCAAkC,CAAC;AACjD,cAAc,0CAA0C,CAAC;AACzD,cAAc,sCAAsC,CAAC;AACrD,cAAc,qCAAqC,CAAC;AAEpD,4CAA4C;AAC5C,cAAc,+BAA+B,CAAC;AAC9C,cAAc,iCAAiC,CAAC;AAChD,cAAc,8BAA8B,CAAC;AAC7C,cAAc,gCAAgC,CAAC;AAC/C,cAAc,2CAA2C,CAAC;AAE1D,kEAAkE;AAClE,cAAc,qDAAqD,CAAC;AAEpE,YAAY;AACZ,cAAc,kCAAkC,CAAC;AAEjD,8DAA8D;AAC9D,cAAc,qCAAqC,CAAC"}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Notification analytics (the admin's Notification Analytics): what Clarion sent people
|
|
3
|
+
* over a period, on every channel - push to the app, the console's in-app notifications,
|
|
4
|
+
* SMS and email - whether it got through, whether it was opened, and how many people a
|
|
5
|
+
* push can reach at all.
|
|
6
|
+
*
|
|
7
|
+
* One read, computed by clarion-notification from one consistent snapshot, with who each
|
|
8
|
+
* recipient is from clarion-authentication. Counts, rates and durations only: never a
|
|
9
|
+
* title, a message, a phone number or an address.
|
|
10
|
+
*
|
|
11
|
+
* DURATIONS ARE IN SECONDS, like every analytics contract.
|
|
12
|
+
*
|
|
13
|
+
* How it is counted:
|
|
14
|
+
* - Everything by when it was CREATED - the moment Clarion decided to tell somebody.
|
|
15
|
+
* - Whose it is: the organization recorded on it; for a push, the organization of the
|
|
16
|
+
* post it announces, then the recipient's; for an SMS, the recipient's. Older SMS and
|
|
17
|
+
* email (before 21 September 2026) recorded no organization and often no recipient:
|
|
18
|
+
* those are counted only in the platform view (`unattributed`).
|
|
19
|
+
* - Got through: accepted by the provider - Firebase for a push, the SMS gateway, the
|
|
20
|
+
* mail service - or, in the console, delivered. Nothing reports whether an SMS or an
|
|
21
|
+
* email was read, so only push (tapped) and in-app (read) have an open rate.
|
|
22
|
+
* - A country narrows push, in-app and devices by the recipient's country and SMS by
|
|
23
|
+
* the number's; email has no country and is never narrowed.
|
|
24
|
+
*/
|
|
25
|
+
export {};
|
|
26
|
+
//# sourceMappingURL=notification-analytics.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"notification-analytics.js","sourceRoot":"","sources":["../../../../../src/modules/notification/interfaces/notification-analytics.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;GAuBG"}
|
|
@@ -51,6 +51,9 @@ export var PermissionActions;
|
|
|
51
51
|
PermissionActions["READ_INCIDENT"] = "read:incident";
|
|
52
52
|
PermissionActions["UPDATE_INCIDENT"] = "update:incident";
|
|
53
53
|
PermissionActions["DELETE_INCIDENT"] = "delete:incident";
|
|
54
|
+
// Chat Analytics: how the chats went and how quickly members were answered - totals
|
|
55
|
+
// only. Held by exactly the roles that read the user analytics.
|
|
56
|
+
PermissionActions["READ_CHAT_ANALYTICS"] = "read:chat-analytics";
|
|
54
57
|
PermissionActions["CREATE_INCIDENT_CATEGORY_TYPE"] = "create:incident-category-type";
|
|
55
58
|
PermissionActions["READ_INCIDENT_CATEGORY_TYPE"] = "read:incident-category-type";
|
|
56
59
|
PermissionActions["UPDATE_INCIDENT_CATEGORY_TYPE"] = "update:incident-category-type";
|
|
@@ -122,6 +125,9 @@ export var PermissionActions;
|
|
|
122
125
|
// emails are branded, the address they are sent from, and the sender ID its
|
|
123
126
|
// SMS arrive under - one family per thing configured. Mirrors grm-shared-library.
|
|
124
127
|
PermissionActions["READ_NOTIFICATION_BRANDING"] = "read:notification-branding";
|
|
128
|
+
// Notification Analytics: what went out on every channel and whether it got
|
|
129
|
+
// through - totals only. Held by exactly the roles that read the notification settings.
|
|
130
|
+
PermissionActions["READ_NOTIFICATION_ANALYTICS"] = "read:notification-analytics";
|
|
125
131
|
PermissionActions["UPDATE_NOTIFICATION_BRANDING"] = "update:notification-branding";
|
|
126
132
|
PermissionActions["CREATE_NOTIFICATION_EMAIL_SENDER"] = "create:notification-email-sender";
|
|
127
133
|
PermissionActions["READ_NOTIFICATION_EMAIL_SENDER"] = "read:notification-email-sender";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"permission-actions.enum.js","sourceRoot":"","sources":["../../../../../src/modules/permission/enums/permission-actions.enum.ts"],"names":[],"mappings":"AAAA,MAAM,CAAN,IAAY,
|
|
1
|
+
{"version":3,"file":"permission-actions.enum.js","sourceRoot":"","sources":["../../../../../src/modules/permission/enums/permission-actions.enum.ts"],"names":[],"mappings":"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"}
|
|
@@ -7,5 +7,6 @@ export * from './interfaces/chat-conversation-with-participants';
|
|
|
7
7
|
export * from './interfaces/chat-message';
|
|
8
8
|
export * from './interfaces/chat-participant';
|
|
9
9
|
export * from './interfaces/chat-presence-info';
|
|
10
|
+
export * from './interfaces/chat-analytics';
|
|
10
11
|
export * from './constants/chat-ws-events';
|
|
11
12
|
export * from './constants/chat-room-names';
|
|
@@ -0,0 +1,275 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Chat analytics (the admin's Chat Analytics): how the conversations on Clarion went over
|
|
3
|
+
* a period - incident chats, Follow Me chats and direct chats - how much was written and
|
|
4
|
+
* by whom, and above all how quickly a member who wrote was answered.
|
|
5
|
+
*
|
|
6
|
+
* One read, computed by clarion-chat from one consistent snapshot, with who each person
|
|
7
|
+
* is from clarion-authentication. Counts, rates and durations only: never a message, a
|
|
8
|
+
* member's name or a trip's label. The only people named are STAFF - the control room,
|
|
9
|
+
* responders and administrators - as agents are on the support analytics.
|
|
10
|
+
*
|
|
11
|
+
* DURATIONS ARE IN SECONDS, like every analytics contract.
|
|
12
|
+
*
|
|
13
|
+
* How it is counted:
|
|
14
|
+
* - A conversation belongs to the organization, control centre and country of the
|
|
15
|
+
* person who STARTED it: the member who raised the SOS, the traveller on a Follow Me
|
|
16
|
+
* trip, the administrator who opened a direct chat. clarion-chat keeps no organization
|
|
17
|
+
* of its own. Everything written in a conversation is its organization's, whoever
|
|
18
|
+
* wrote it - a guardian, or a responder from another organization.
|
|
19
|
+
* - What a conversation is for (`ChatAnalyticsContext`): INCIDENT is an incident's chat,
|
|
20
|
+
* including a Follow Me chat that an SOS adopted; FOLLOW_ME a trip's; DIRECT one person
|
|
21
|
+
* to another; GROUP any other group.
|
|
22
|
+
* - Who writes (`ChatAnalyticsSenderKind`), from the roles a person holds NOW: anybody
|
|
23
|
+
* with a control-centre role is the CONTROL_ROOM, then RESPONDER, then ADMINISTRATOR
|
|
24
|
+
* (organization roles, Super-Admin) - together, STAFF. Everybody else is a MEMBER: the
|
|
25
|
+
* people the service is for, their guardians included. UNKNOWN is an account that no
|
|
26
|
+
* longer exists. Whoever started an incident's or a Follow Me chat from the app is its
|
|
27
|
+
* MEMBER there, whatever else they hold - staff raise SOSes too.
|
|
28
|
+
* - A member's TURN starts with a member's message that opens a conversation or follows
|
|
29
|
+
* a staff message. It is ANSWERED by the first staff message after it, and the wait is
|
|
30
|
+
* the time between. Turns started in the period, answered whenever.
|
|
31
|
+
* - System messages are counted on their own and never take part in a turn.
|
|
32
|
+
*/
|
|
33
|
+
/** How the period is cut into points for the charts. Chosen by the service from the length of the period. */
|
|
34
|
+
export type ChatAnalyticsBucket = 'hour' | 'day' | 'week' | 'month';
|
|
35
|
+
/** What a conversation is for. */
|
|
36
|
+
export type ChatAnalyticsContext = 'INCIDENT' | 'FOLLOW_ME' | 'DIRECT' | 'GROUP';
|
|
37
|
+
/** Who wrote a message: the three kinds of staff, a member, or an account that no longer exists. */
|
|
38
|
+
export type ChatAnalyticsSenderKind = 'CONTROL_ROOM' | 'RESPONDER' | 'ADMINISTRATOR' | 'MEMBER' | 'UNKNOWN';
|
|
39
|
+
export interface ChatAnalyticsRange {
|
|
40
|
+
/** Inclusive, ISO 8601. The first conversation when the period asked for was "forever". */
|
|
41
|
+
from: string;
|
|
42
|
+
/** Exclusive, ISO 8601. */
|
|
43
|
+
to: string;
|
|
44
|
+
bucket: ChatAnalyticsBucket;
|
|
45
|
+
/** IANA time zone the buckets and the hour-of-week grid are cut in. */
|
|
46
|
+
timeZone: string;
|
|
47
|
+
}
|
|
48
|
+
/** A count by a key (a context, a kind, a band), largest first unless the section says otherwise. */
|
|
49
|
+
export interface ChatAnalyticsCount<K extends string = string> {
|
|
50
|
+
key: K;
|
|
51
|
+
count: number;
|
|
52
|
+
}
|
|
53
|
+
/** Median and 90th percentile of one duration, in seconds; null when nothing was measured. */
|
|
54
|
+
export interface ChatAnalyticsDuration {
|
|
55
|
+
median: number | null;
|
|
56
|
+
p90: number | null;
|
|
57
|
+
/** How many were measured. */
|
|
58
|
+
count: number;
|
|
59
|
+
}
|
|
60
|
+
/** One kind of conversation and how it went in the period. */
|
|
61
|
+
export interface ChatAnalyticsContextRow {
|
|
62
|
+
context: ChatAnalyticsContext;
|
|
63
|
+
/** Started in the period. */
|
|
64
|
+
started: number;
|
|
65
|
+
/** Of those, written in at least once (whenever). */
|
|
66
|
+
used: number;
|
|
67
|
+
/** Written in during the period, whenever started. */
|
|
68
|
+
active: number;
|
|
69
|
+
/** Messages written in the period, not counting system messages. */
|
|
70
|
+
messages: number;
|
|
71
|
+
memberMessages: number;
|
|
72
|
+
staffMessages: number;
|
|
73
|
+
/** Members' turns started in the period, and of those answered. */
|
|
74
|
+
turns: number;
|
|
75
|
+
answered: number;
|
|
76
|
+
/** answered / turns, as a percentage. */
|
|
77
|
+
replyRate: number | null;
|
|
78
|
+
medianSecondsToReply: number | null;
|
|
79
|
+
}
|
|
80
|
+
/** The conversations: what was started, what was used, and who was in them. */
|
|
81
|
+
export interface ChatAnalyticsConversations {
|
|
82
|
+
/** Started in the period. */
|
|
83
|
+
started: number;
|
|
84
|
+
/** Of those, written in at least once (whenever) - and as a percentage. */
|
|
85
|
+
used: number;
|
|
86
|
+
usedRate: number | null;
|
|
87
|
+
/** Of those, a member AND staff both wrote in - a conversation rather than a notice. */
|
|
88
|
+
twoWay: number;
|
|
89
|
+
/** Written in during the period, whenever started. */
|
|
90
|
+
active: number;
|
|
91
|
+
/** People seated in the conversations started in the period, each counted once. */
|
|
92
|
+
people: number;
|
|
93
|
+
/** People per conversation started in the period. */
|
|
94
|
+
averageParticipants: number | null;
|
|
95
|
+
/**
|
|
96
|
+
* In the period, in any conversation in scope: people added AFTER it started (a
|
|
97
|
+
* responder assigned, a guardian added - not the people it started with), and seats
|
|
98
|
+
* given up (removed, or left).
|
|
99
|
+
*/
|
|
100
|
+
joined: number;
|
|
101
|
+
left: number;
|
|
102
|
+
/** Start to the first message - conversations started in the period that were used. */
|
|
103
|
+
toFirstMessage: ChatAnalyticsDuration;
|
|
104
|
+
/** Start to the first staff message - conversations started in the period that staff wrote in. */
|
|
105
|
+
toFirstStaffMessage: ChatAnalyticsDuration;
|
|
106
|
+
/** INCIDENT, FOLLOW_ME, DIRECT, GROUP - in that order, zeros included. */
|
|
107
|
+
byContext: ChatAnalyticsContextRow[];
|
|
108
|
+
/** Conversations started in the period by how many people are in them now: 1, 2, 3, 4, 5, 6+ - in that order. */
|
|
109
|
+
bySize: ChatAnalyticsCount[];
|
|
110
|
+
/** Conversations started in the period, by the country of whoever started them. */
|
|
111
|
+
byCountry: ChatAnalyticsCount[];
|
|
112
|
+
}
|
|
113
|
+
/** The messages written in the period. */
|
|
114
|
+
export interface ChatAnalyticsMessages {
|
|
115
|
+
/** Written by people (system messages are `system`). */
|
|
116
|
+
sent: number;
|
|
117
|
+
fromMembers: number;
|
|
118
|
+
fromStaff: number;
|
|
119
|
+
/** By accounts that no longer exist. */
|
|
120
|
+
fromUnknown: number;
|
|
121
|
+
system: number;
|
|
122
|
+
/** Removed in the period, whenever written. */
|
|
123
|
+
removed: number;
|
|
124
|
+
/** Different people who wrote. */
|
|
125
|
+
senders: number;
|
|
126
|
+
memberSenders: number;
|
|
127
|
+
staffSenders: number;
|
|
128
|
+
/** sent / active conversations. */
|
|
129
|
+
perActiveConversation: number | null;
|
|
130
|
+
/** CONTROL_ROOM, RESPONDER, ADMINISTRATOR, MEMBER, UNKNOWN - in that order, zeros included. */
|
|
131
|
+
bySenderKind: ChatAnalyticsCount<ChatAnalyticsSenderKind>[];
|
|
132
|
+
/** Characters, never the words. */
|
|
133
|
+
medianLength: number | null;
|
|
134
|
+
/** SHORT (under 20 characters), MEDIUM (20-79), LONG (80-279), VERY_LONG (280+) - in that order. */
|
|
135
|
+
byLength: ChatAnalyticsCount[];
|
|
136
|
+
}
|
|
137
|
+
/** How quickly members were answered. */
|
|
138
|
+
export interface ChatAnalyticsReplies {
|
|
139
|
+
/** Members' turns started in the period. */
|
|
140
|
+
turns: number;
|
|
141
|
+
answered: number;
|
|
142
|
+
/** Never answered - the last word in that conversation is still the member's. */
|
|
143
|
+
unanswered: number;
|
|
144
|
+
/** answered / turns, as a percentage. */
|
|
145
|
+
replyRate: number | null;
|
|
146
|
+
/** The member's message to the first staff message after it - turns answered. */
|
|
147
|
+
toReply: ChatAnalyticsDuration;
|
|
148
|
+
/** Answered within a minute, 5 minutes, 15 minutes, an hour, later: UNDER_1M, 1-5M, 5-15M, 15-60M, OVER_1H - in that order. */
|
|
149
|
+
byWait: ChatAnalyticsCount[];
|
|
150
|
+
/** Answered within 5 minutes, as a percentage of turns. */
|
|
151
|
+
withinFiveMinutes: number | null;
|
|
152
|
+
}
|
|
153
|
+
/** One member of staff who wrote in the period. Staff are named; members never are. */
|
|
154
|
+
export interface ChatAnalyticsStaffRow {
|
|
155
|
+
userId: number;
|
|
156
|
+
name: string | null;
|
|
157
|
+
kind: ChatAnalyticsSenderKind;
|
|
158
|
+
/** Messages they wrote in the period. */
|
|
159
|
+
messages: number;
|
|
160
|
+
/** Conversations they wrote in, in the period. */
|
|
161
|
+
conversations: number;
|
|
162
|
+
/** Members' turns started in the period that they were first to answer. */
|
|
163
|
+
replies: number;
|
|
164
|
+
medianSecondsToReply: number | null;
|
|
165
|
+
}
|
|
166
|
+
/** One conversation, for a table - never its messages, its members or its label. */
|
|
167
|
+
export interface ChatAnalyticsConversationRow {
|
|
168
|
+
id: string;
|
|
169
|
+
context: ChatAnalyticsContext;
|
|
170
|
+
/** The incident it belongs to, for an incident's chat. */
|
|
171
|
+
incidentId: number | null;
|
|
172
|
+
organizationId: number | null;
|
|
173
|
+
startedAt: string;
|
|
174
|
+
/** People in it now. */
|
|
175
|
+
participants: number;
|
|
176
|
+
/** Written in the period. */
|
|
177
|
+
messages: number;
|
|
178
|
+
memberMessages: number;
|
|
179
|
+
staffMessages: number;
|
|
180
|
+
/** Its latest message, whenever. */
|
|
181
|
+
lastMessageAt: string | null;
|
|
182
|
+
/** Its members' turns started in the period, answered. */
|
|
183
|
+
medianSecondsToReply: number | null;
|
|
184
|
+
/** The last word is a member's, and nobody from staff has answered it. */
|
|
185
|
+
awaitingReply: boolean;
|
|
186
|
+
/** When that unanswered member's turn began; null when nothing is waiting. */
|
|
187
|
+
waitingSince: string | null;
|
|
188
|
+
}
|
|
189
|
+
/** One point on the charts: a bucket of the period. */
|
|
190
|
+
export interface ChatAnalyticsPoint {
|
|
191
|
+
/** Local wall-clock start of the bucket, in `range.timeZone` (no offset). */
|
|
192
|
+
bucket: string;
|
|
193
|
+
/** Conversations started in the bucket, and of those incident chats. */
|
|
194
|
+
started: number;
|
|
195
|
+
incidentChats: number;
|
|
196
|
+
memberMessages: number;
|
|
197
|
+
staffMessages: number;
|
|
198
|
+
/** Conversations written in during the bucket. */
|
|
199
|
+
active: number;
|
|
200
|
+
/** Members' turns started in the bucket, and of those answered. */
|
|
201
|
+
turns: number;
|
|
202
|
+
answered: number;
|
|
203
|
+
medianSecondsToReply: number | null;
|
|
204
|
+
}
|
|
205
|
+
/** One hour of the week. Weekday 1 is Monday. */
|
|
206
|
+
export interface ChatAnalyticsHeatCell {
|
|
207
|
+
weekday: number;
|
|
208
|
+
hour: number;
|
|
209
|
+
/** When members write. */
|
|
210
|
+
memberMessages: number;
|
|
211
|
+
/** When staff write. */
|
|
212
|
+
staffMessages: number;
|
|
213
|
+
}
|
|
214
|
+
/** The previous period of the same length, for the change on each headline figure. */
|
|
215
|
+
export interface ChatAnalyticsPrevious {
|
|
216
|
+
from: string;
|
|
217
|
+
to: string;
|
|
218
|
+
started: number;
|
|
219
|
+
used: number;
|
|
220
|
+
active: number;
|
|
221
|
+
sent: number;
|
|
222
|
+
memberMessages: number;
|
|
223
|
+
staffMessages: number;
|
|
224
|
+
senders: number;
|
|
225
|
+
turns: number;
|
|
226
|
+
answered: number;
|
|
227
|
+
replyRate: number | null;
|
|
228
|
+
medianSecondsToReply: number | null;
|
|
229
|
+
}
|
|
230
|
+
/** A Super-Admin's view of every organization: one row each, busiest first. */
|
|
231
|
+
export interface ChatAnalyticsOrganizationRow {
|
|
232
|
+
organizationId: number;
|
|
233
|
+
started: number;
|
|
234
|
+
active: number;
|
|
235
|
+
sent: number;
|
|
236
|
+
memberMessages: number;
|
|
237
|
+
staffMessages: number;
|
|
238
|
+
turns: number;
|
|
239
|
+
replyRate: number | null;
|
|
240
|
+
medianSecondsToReply: number | null;
|
|
241
|
+
}
|
|
242
|
+
export interface ChatAnalytics {
|
|
243
|
+
/** Whose figures: one organization (and one control centre in it), or null for every organization. */
|
|
244
|
+
organizationId: number | null;
|
|
245
|
+
controlCentreId: number | null;
|
|
246
|
+
/** The one country the figures are narrowed to, or null for every country. */
|
|
247
|
+
countryCode: string | null;
|
|
248
|
+
range: ChatAnalyticsRange;
|
|
249
|
+
generatedAt: string;
|
|
250
|
+
previous: ChatAnalyticsPrevious | null;
|
|
251
|
+
/** Countries with conversations in scope, whatever country is chosen - for narrowing to one. */
|
|
252
|
+
countryOptions: ChatAnalyticsCount[];
|
|
253
|
+
conversations: ChatAnalyticsConversations;
|
|
254
|
+
messages: ChatAnalyticsMessages;
|
|
255
|
+
replies: ChatAnalyticsReplies;
|
|
256
|
+
/** Staff who wrote in the period, busiest first - at most 25. */
|
|
257
|
+
staff: ChatAnalyticsStaffRow[];
|
|
258
|
+
/** The 15 conversations most written in during the period. */
|
|
259
|
+
busiest: ChatAnalyticsConversationRow[];
|
|
260
|
+
/** Conversations written in during the period whose member is still waiting for an answer, latest first - at most 25. */
|
|
261
|
+
waiting: ChatAnalyticsConversationRow[];
|
|
262
|
+
timeline: ChatAnalyticsPoint[];
|
|
263
|
+
/** All 168 hours of the week, Monday first, zeros included. */
|
|
264
|
+
heatmap: ChatAnalyticsHeatCell[];
|
|
265
|
+
/** A Super-Admin looking at every organization only. */
|
|
266
|
+
byOrganization?: ChatAnalyticsOrganizationRow[];
|
|
267
|
+
}
|
|
268
|
+
/** What a dashboard asks: the period, one country - and, for a Super-Admin, whose figures. */
|
|
269
|
+
export interface ChatAnalyticsQuery {
|
|
270
|
+
from?: string;
|
|
271
|
+
to?: string;
|
|
272
|
+
timeZone?: string;
|
|
273
|
+
organizationId?: number;
|
|
274
|
+
countryCode?: string;
|
|
275
|
+
}
|
|
@@ -11,3 +11,4 @@ export * from './interfaces/email-send-result';
|
|
|
11
11
|
export * from './interfaces/notification-dispatch-result';
|
|
12
12
|
export * from './interfaces/organization-notification-settings.dto';
|
|
13
13
|
export * from './utils/notification-sender.util';
|
|
14
|
+
export * from './interfaces/notification-analytics';
|
|
@@ -0,0 +1,273 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Notification analytics (the admin's Notification Analytics): what Clarion sent people
|
|
3
|
+
* over a period, on every channel - push to the app, the console's in-app notifications,
|
|
4
|
+
* SMS and email - whether it got through, whether it was opened, and how many people a
|
|
5
|
+
* push can reach at all.
|
|
6
|
+
*
|
|
7
|
+
* One read, computed by clarion-notification from one consistent snapshot, with who each
|
|
8
|
+
* recipient is from clarion-authentication. Counts, rates and durations only: never a
|
|
9
|
+
* title, a message, a phone number or an address.
|
|
10
|
+
*
|
|
11
|
+
* DURATIONS ARE IN SECONDS, like every analytics contract.
|
|
12
|
+
*
|
|
13
|
+
* How it is counted:
|
|
14
|
+
* - Everything by when it was CREATED - the moment Clarion decided to tell somebody.
|
|
15
|
+
* - Whose it is: the organization recorded on it; for a push, the organization of the
|
|
16
|
+
* post it announces, then the recipient's; for an SMS, the recipient's. Older SMS and
|
|
17
|
+
* email (before 21 September 2026) recorded no organization and often no recipient:
|
|
18
|
+
* those are counted only in the platform view (`unattributed`).
|
|
19
|
+
* - Got through: accepted by the provider - Firebase for a push, the SMS gateway, the
|
|
20
|
+
* mail service - or, in the console, delivered. Nothing reports whether an SMS or an
|
|
21
|
+
* email was read, so only push (tapped) and in-app (read) have an open rate.
|
|
22
|
+
* - A country narrows push, in-app and devices by the recipient's country and SMS by
|
|
23
|
+
* the number's; email has no country and is never narrowed.
|
|
24
|
+
*/
|
|
25
|
+
/** How the period is cut into points for the charts. Chosen by the service from the length of the period. */
|
|
26
|
+
export type NotificationAnalyticsBucket = 'hour' | 'day' | 'week' | 'month';
|
|
27
|
+
/** The four ways Clarion tells somebody something. */
|
|
28
|
+
export type NotificationAnalyticsChannel = 'PUSH' | 'IN_APP' | 'SMS' | 'EMAIL';
|
|
29
|
+
export interface NotificationAnalyticsRange {
|
|
30
|
+
/** Inclusive, ISO 8601. The first notification when the period asked for was "forever". */
|
|
31
|
+
from: string;
|
|
32
|
+
/** Exclusive, ISO 8601. */
|
|
33
|
+
to: string;
|
|
34
|
+
bucket: NotificationAnalyticsBucket;
|
|
35
|
+
/** IANA time zone the buckets and the hour-of-week grid are cut in. */
|
|
36
|
+
timeZone: string;
|
|
37
|
+
}
|
|
38
|
+
/** A count by a key (a kind, a provider, a reason), largest first unless the section says otherwise. */
|
|
39
|
+
export interface NotificationAnalyticsCount<K extends string = string> {
|
|
40
|
+
key: K;
|
|
41
|
+
count: number;
|
|
42
|
+
}
|
|
43
|
+
/** Median and 90th percentile of one duration, in seconds; null when nothing was measured. */
|
|
44
|
+
export interface NotificationAnalyticsDuration {
|
|
45
|
+
median: number | null;
|
|
46
|
+
p90: number | null;
|
|
47
|
+
/** How many were measured. */
|
|
48
|
+
count: number;
|
|
49
|
+
}
|
|
50
|
+
/** One channel over the period. */
|
|
51
|
+
export interface NotificationAnalyticsChannelRow {
|
|
52
|
+
channel: NotificationAnalyticsChannel;
|
|
53
|
+
/** Created in the period. */
|
|
54
|
+
total: number;
|
|
55
|
+
/** Got through: accepted by the provider, or delivered to the console. */
|
|
56
|
+
succeeded: number;
|
|
57
|
+
failed: number;
|
|
58
|
+
/** No outcome yet: waiting, or cancelled before it was sent. */
|
|
59
|
+
pending: number;
|
|
60
|
+
/** succeeded / (succeeded + failed), as a percentage. */
|
|
61
|
+
successRate: number | null;
|
|
62
|
+
/** Push tapped, in-app read; null for SMS and email - nothing reports it. */
|
|
63
|
+
opened: number | null;
|
|
64
|
+
/** opened / succeeded, as a percentage. */
|
|
65
|
+
openRate: number | null;
|
|
66
|
+
}
|
|
67
|
+
/** One kind of push - what it announced - and how it went. */
|
|
68
|
+
export interface NotificationAnalyticsPushKindRow {
|
|
69
|
+
/** The event it announced (NEWSFEED_POST_PUBLISHED, GUARDIAN_INCIDENT_ALERT...), else its category (INCIDENT, ALERT...). */
|
|
70
|
+
kind: string;
|
|
71
|
+
total: number;
|
|
72
|
+
failed: number;
|
|
73
|
+
opened: number;
|
|
74
|
+
/** opened / those that got through, as a percentage. */
|
|
75
|
+
openRate: number | null;
|
|
76
|
+
medianSecondsToOpen: number | null;
|
|
77
|
+
}
|
|
78
|
+
/** Push notifications to the app. */
|
|
79
|
+
export interface NotificationAnalyticsPush {
|
|
80
|
+
/** One per device: a notification to somebody with two phones is two. */
|
|
81
|
+
total: number;
|
|
82
|
+
succeeded: number;
|
|
83
|
+
failed: number;
|
|
84
|
+
pending: number;
|
|
85
|
+
opened: number;
|
|
86
|
+
successRate: number | null;
|
|
87
|
+
openRate: number | null;
|
|
88
|
+
/** Different people pushed to. */
|
|
89
|
+
recipients: number;
|
|
90
|
+
/** Notifications as Clarion decided them, each fanned out to its recipients' devices. */
|
|
91
|
+
sends: number;
|
|
92
|
+
/** Created to accepted by Firebase - seconds, with decimals. */
|
|
93
|
+
toSend: NotificationAnalyticsDuration;
|
|
94
|
+
/** Created to tapped. */
|
|
95
|
+
toOpen: NotificationAnalyticsDuration;
|
|
96
|
+
byKind: NotificationAnalyticsPushKindRow[];
|
|
97
|
+
/** Critical, High, Normal, Low - in that order, zeros included. */
|
|
98
|
+
byPriority: NotificationAnalyticsCount[];
|
|
99
|
+
/** The Android channel it rang on (urgent, incidents...); DEFAULT when none. */
|
|
100
|
+
byChannel: NotificationAnalyticsCount[];
|
|
101
|
+
/** Why pushes failed, as the provider said it - ids, numbers and addresses masked. The eight commonest. */
|
|
102
|
+
failureReasons: NotificationAnalyticsCount[];
|
|
103
|
+
}
|
|
104
|
+
/** The phones and browsers a push can reach - NOW, whatever the period, apart from `registered`. */
|
|
105
|
+
export interface NotificationAnalyticsDevices {
|
|
106
|
+
activeNow: number;
|
|
107
|
+
/** Switched off: signed out, replaced by a newer registration, or refused by the provider. */
|
|
108
|
+
inactiveNow: number;
|
|
109
|
+
/** People with at least one active device: who a push can reach. */
|
|
110
|
+
reachableNow: number;
|
|
111
|
+
/** Registered in the period. */
|
|
112
|
+
registered: number;
|
|
113
|
+
/** Active devices by kind (android, ios, web). */
|
|
114
|
+
byType: NotificationAnalyticsCount[];
|
|
115
|
+
/** Active devices by app version; NONE when not recorded. */
|
|
116
|
+
byAppVersion: NotificationAnalyticsCount[];
|
|
117
|
+
byLanguage: NotificationAnalyticsCount[];
|
|
118
|
+
}
|
|
119
|
+
/** The console's own notifications, to the staff using it. */
|
|
120
|
+
export interface NotificationAnalyticsInApp {
|
|
121
|
+
total: number;
|
|
122
|
+
succeeded: number;
|
|
123
|
+
failed: number;
|
|
124
|
+
pending: number;
|
|
125
|
+
read: number;
|
|
126
|
+
/** read / total, as a percentage. */
|
|
127
|
+
readRate: number | null;
|
|
128
|
+
/** Different people notified. */
|
|
129
|
+
recipients: number;
|
|
130
|
+
/** INCIDENT, ALERT, MESSAGE... */
|
|
131
|
+
byType: NotificationAnalyticsCount[];
|
|
132
|
+
/** What happened (Created, Auto-Stopped, CHAT_MESSAGE...). */
|
|
133
|
+
byAction: NotificationAnalyticsCount[];
|
|
134
|
+
/** NOW: notifications nobody has read yet, whenever created. */
|
|
135
|
+
unreadNow: number;
|
|
136
|
+
}
|
|
137
|
+
/** Cost recorded on SMS, per currency. */
|
|
138
|
+
export interface NotificationAnalyticsSmsCost {
|
|
139
|
+
currency: string;
|
|
140
|
+
amount: number;
|
|
141
|
+
/** Messages with a cost recorded. */
|
|
142
|
+
messages: number;
|
|
143
|
+
}
|
|
144
|
+
/** SMS. */
|
|
145
|
+
export interface NotificationAnalyticsSms {
|
|
146
|
+
total: number;
|
|
147
|
+
succeeded: number;
|
|
148
|
+
failed: number;
|
|
149
|
+
pending: number;
|
|
150
|
+
successRate: number | null;
|
|
151
|
+
/** Created to accepted by the gateway. */
|
|
152
|
+
toSend: NotificationAnalyticsDuration;
|
|
153
|
+
/** What it was for: otp:verify_phone, otp:reset_password, guardian_incident_notification...; NOT_RECORDED for the oldest. */
|
|
154
|
+
byPurpose: NotificationAnalyticsCount[];
|
|
155
|
+
/** The gateway that took it (uwazii, twilio, africastalking); NOT_RECORDED for the oldest. */
|
|
156
|
+
byProvider: NotificationAnalyticsCount[];
|
|
157
|
+
/** Whose sender ID it went out under (PLATFORM_DEFAULT, ORGANIZATION); NOT_RECORDED for the oldest. */
|
|
158
|
+
bySenderSource: NotificationAnalyticsCount[];
|
|
159
|
+
/** The number's country; UNKNOWN when not recorded. */
|
|
160
|
+
byCountry: NotificationAnalyticsCount[];
|
|
161
|
+
/** Why messages failed - ids, numbers and addresses masked. The eight commonest. */
|
|
162
|
+
failureReasons: NotificationAnalyticsCount[];
|
|
163
|
+
cost: NotificationAnalyticsSmsCost[];
|
|
164
|
+
}
|
|
165
|
+
/** Email. */
|
|
166
|
+
export interface NotificationAnalyticsEmail {
|
|
167
|
+
total: number;
|
|
168
|
+
succeeded: number;
|
|
169
|
+
failed: number;
|
|
170
|
+
successRate: number | null;
|
|
171
|
+
/** Verification, Password Reset, Notification, Acknowledgement... */
|
|
172
|
+
byType: NotificationAnalyticsCount[];
|
|
173
|
+
/** The mail service that took it; NOT_RECORDED for the oldest. */
|
|
174
|
+
byProvider: NotificationAnalyticsCount[];
|
|
175
|
+
bySenderSource: NotificationAnalyticsCount[];
|
|
176
|
+
}
|
|
177
|
+
/** One point on the charts: a bucket of the period. */
|
|
178
|
+
export interface NotificationAnalyticsPoint {
|
|
179
|
+
/** Local wall-clock start of the bucket, in `range.timeZone` (no offset). */
|
|
180
|
+
bucket: string;
|
|
181
|
+
push: number;
|
|
182
|
+
pushFailed: number;
|
|
183
|
+
/** Of the pushes created in the bucket, those tapped (whenever). */
|
|
184
|
+
pushOpened: number;
|
|
185
|
+
inApp: number;
|
|
186
|
+
inAppRead: number;
|
|
187
|
+
sms: number;
|
|
188
|
+
smsFailed: number;
|
|
189
|
+
email: number;
|
|
190
|
+
emailFailed: number;
|
|
191
|
+
}
|
|
192
|
+
/** One hour of the week. Weekday 1 is Monday. */
|
|
193
|
+
export interface NotificationAnalyticsHeatCell {
|
|
194
|
+
weekday: number;
|
|
195
|
+
hour: number;
|
|
196
|
+
/** Notifications created in it, every channel. */
|
|
197
|
+
sent: number;
|
|
198
|
+
/** Pushes tapped in it - when people look. */
|
|
199
|
+
opened: number;
|
|
200
|
+
}
|
|
201
|
+
/** The previous period of the same length, for the change on each headline figure. */
|
|
202
|
+
export interface NotificationAnalyticsPrevious {
|
|
203
|
+
from: string;
|
|
204
|
+
to: string;
|
|
205
|
+
total: number;
|
|
206
|
+
push: number;
|
|
207
|
+
pushFailed: number;
|
|
208
|
+
pushOpened: number;
|
|
209
|
+
pushOpenRate: number | null;
|
|
210
|
+
pushSuccessRate: number | null;
|
|
211
|
+
inApp: number;
|
|
212
|
+
inAppRead: number;
|
|
213
|
+
sms: number;
|
|
214
|
+
smsFailed: number;
|
|
215
|
+
smsSuccessRate: number | null;
|
|
216
|
+
email: number;
|
|
217
|
+
emailFailed: number;
|
|
218
|
+
devicesRegistered: number;
|
|
219
|
+
}
|
|
220
|
+
/** A Super-Admin's view of every organization: one row each, busiest first. */
|
|
221
|
+
export interface NotificationAnalyticsOrganizationRow {
|
|
222
|
+
organizationId: number;
|
|
223
|
+
total: number;
|
|
224
|
+
push: number;
|
|
225
|
+
pushFailed: number;
|
|
226
|
+
pushOpenRate: number | null;
|
|
227
|
+
inApp: number;
|
|
228
|
+
inAppReadRate: number | null;
|
|
229
|
+
sms: number;
|
|
230
|
+
smsFailed: number;
|
|
231
|
+
email: number;
|
|
232
|
+
/** NOW. */
|
|
233
|
+
activeDevices: number;
|
|
234
|
+
}
|
|
235
|
+
/** Notifications of the period no organization could be found for - the platform view only. */
|
|
236
|
+
export interface NotificationAnalyticsUnattributed {
|
|
237
|
+
push: number;
|
|
238
|
+
sms: number;
|
|
239
|
+
email: number;
|
|
240
|
+
}
|
|
241
|
+
export interface NotificationAnalytics {
|
|
242
|
+
/** Whose figures: one organization, or null for every organization. */
|
|
243
|
+
organizationId: number | null;
|
|
244
|
+
/** The one country the figures are narrowed to, or null for every country. */
|
|
245
|
+
countryCode: string | null;
|
|
246
|
+
range: NotificationAnalyticsRange;
|
|
247
|
+
generatedAt: string;
|
|
248
|
+
previous: NotificationAnalyticsPrevious | null;
|
|
249
|
+
/** Countries with notifications or devices in scope, whatever country is chosen - for narrowing to one. */
|
|
250
|
+
countryOptions: NotificationAnalyticsCount[];
|
|
251
|
+
/** PUSH, IN_APP, SMS, EMAIL - in that order. */
|
|
252
|
+
channels: NotificationAnalyticsChannelRow[];
|
|
253
|
+
push: NotificationAnalyticsPush;
|
|
254
|
+
devices: NotificationAnalyticsDevices;
|
|
255
|
+
inApp: NotificationAnalyticsInApp;
|
|
256
|
+
sms: NotificationAnalyticsSms;
|
|
257
|
+
email: NotificationAnalyticsEmail;
|
|
258
|
+
timeline: NotificationAnalyticsPoint[];
|
|
259
|
+
/** All 168 hours of the week, Monday first, zeros included. */
|
|
260
|
+
heatmap: NotificationAnalyticsHeatCell[];
|
|
261
|
+
/** A Super-Admin looking at every organization only. */
|
|
262
|
+
byOrganization?: NotificationAnalyticsOrganizationRow[];
|
|
263
|
+
/** A Super-Admin looking at every organization only. */
|
|
264
|
+
unattributed?: NotificationAnalyticsUnattributed;
|
|
265
|
+
}
|
|
266
|
+
/** What a dashboard asks: the period, one country - and, for a Super-Admin, whose figures. */
|
|
267
|
+
export interface NotificationAnalyticsQuery {
|
|
268
|
+
from?: string;
|
|
269
|
+
to?: string;
|
|
270
|
+
timeZone?: string;
|
|
271
|
+
organizationId?: number;
|
|
272
|
+
countryCode?: string;
|
|
273
|
+
}
|
|
@@ -32,6 +32,7 @@ export declare enum PermissionActions {
|
|
|
32
32
|
READ_INCIDENT = "read:incident",
|
|
33
33
|
UPDATE_INCIDENT = "update:incident",
|
|
34
34
|
DELETE_INCIDENT = "delete:incident",
|
|
35
|
+
READ_CHAT_ANALYTICS = "read:chat-analytics",
|
|
35
36
|
CREATE_INCIDENT_CATEGORY_TYPE = "create:incident-category-type",
|
|
36
37
|
READ_INCIDENT_CATEGORY_TYPE = "read:incident-category-type",
|
|
37
38
|
UPDATE_INCIDENT_CATEGORY_TYPE = "update:incident-category-type",
|
|
@@ -86,6 +87,7 @@ export declare enum PermissionActions {
|
|
|
86
87
|
READ_SUPPORT_SYNC = "read:support-sync",
|
|
87
88
|
MANAGE_SUPPORT_SYNC = "manage:support-sync",
|
|
88
89
|
READ_NOTIFICATION_BRANDING = "read:notification-branding",
|
|
90
|
+
READ_NOTIFICATION_ANALYTICS = "read:notification-analytics",
|
|
89
91
|
UPDATE_NOTIFICATION_BRANDING = "update:notification-branding",
|
|
90
92
|
CREATE_NOTIFICATION_EMAIL_SENDER = "create:notification-email-sender",
|
|
91
93
|
READ_NOTIFICATION_EMAIL_SENDER = "read:notification-email-sender",
|
package/package.json
CHANGED
|
@@ -1,45 +1,45 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "clarion-shared-types",
|
|
3
|
-
"version": "1.0.
|
|
4
|
-
"main": "dist/cjs/index.js",
|
|
5
|
-
"module": "dist/esm/index.js",
|
|
6
|
-
"types": "dist/types/index.d.ts",
|
|
7
|
-
"exports": {
|
|
8
|
-
".": {
|
|
9
|
-
"types": "./dist/types/index.d.ts",
|
|
10
|
-
"import": "./dist/esm/index.js",
|
|
11
|
-
"require": "./dist/cjs/index.js"
|
|
12
|
-
},
|
|
13
|
-
"./dist/modules/*": {
|
|
14
|
-
"types": "./dist/types/modules/*.d.ts",
|
|
15
|
-
"import": "./dist/esm/modules/*.js",
|
|
16
|
-
"require": "./dist/cjs/modules/*.js"
|
|
17
|
-
}
|
|
18
|
-
},
|
|
19
|
-
"files": [
|
|
20
|
-
"dist/**/*"
|
|
21
|
-
],
|
|
22
|
-
"scripts": {
|
|
23
|
-
"clean": "rimraf dist dist-test",
|
|
24
|
-
"build:cjs": "tsc -p tsconfig.cjs.json",
|
|
25
|
-
"build:esm": "tsc -p tsconfig.esm.json",
|
|
26
|
-
"build:types": "tsc -p tsconfig.types.json",
|
|
27
|
-
"build": "npm run clean && npm run build:types && npm run build:cjs && npm run build:esm",
|
|
28
|
-
"prepublishOnly": "npm run build",
|
|
29
|
-
"pretest": "rimraf dist-test",
|
|
30
|
-
"test": "tsc -p tsconfig.spec.json && node --test \"dist-test/**/*.spec.js\""
|
|
31
|
-
},
|
|
32
|
-
"keywords": [],
|
|
33
|
-
"author": "vince_lawino",
|
|
34
|
-
"license": "ISC",
|
|
35
|
-
"description": "",
|
|
36
|
-
"publishConfig": {
|
|
37
|
-
"access": "public"
|
|
38
|
-
},
|
|
39
|
-
"devDependencies": {
|
|
40
|
-
"@types/geojson": "^7946.0.16",
|
|
41
|
-
"@types/node": "^20.11.2",
|
|
42
|
-
"rimraf": "^5.0.5",
|
|
43
|
-
"typescript": "^5.7.3"
|
|
44
|
-
}
|
|
45
|
-
}
|
|
1
|
+
{
|
|
2
|
+
"name": "clarion-shared-types",
|
|
3
|
+
"version": "1.0.115",
|
|
4
|
+
"main": "dist/cjs/index.js",
|
|
5
|
+
"module": "dist/esm/index.js",
|
|
6
|
+
"types": "dist/types/index.d.ts",
|
|
7
|
+
"exports": {
|
|
8
|
+
".": {
|
|
9
|
+
"types": "./dist/types/index.d.ts",
|
|
10
|
+
"import": "./dist/esm/index.js",
|
|
11
|
+
"require": "./dist/cjs/index.js"
|
|
12
|
+
},
|
|
13
|
+
"./dist/modules/*": {
|
|
14
|
+
"types": "./dist/types/modules/*.d.ts",
|
|
15
|
+
"import": "./dist/esm/modules/*.js",
|
|
16
|
+
"require": "./dist/cjs/modules/*.js"
|
|
17
|
+
}
|
|
18
|
+
},
|
|
19
|
+
"files": [
|
|
20
|
+
"dist/**/*"
|
|
21
|
+
],
|
|
22
|
+
"scripts": {
|
|
23
|
+
"clean": "rimraf dist dist-test",
|
|
24
|
+
"build:cjs": "tsc -p tsconfig.cjs.json",
|
|
25
|
+
"build:esm": "tsc -p tsconfig.esm.json",
|
|
26
|
+
"build:types": "tsc -p tsconfig.types.json",
|
|
27
|
+
"build": "npm run clean && npm run build:types && npm run build:cjs && npm run build:esm",
|
|
28
|
+
"prepublishOnly": "npm run build",
|
|
29
|
+
"pretest": "rimraf dist-test",
|
|
30
|
+
"test": "tsc -p tsconfig.spec.json && node --test \"dist-test/**/*.spec.js\""
|
|
31
|
+
},
|
|
32
|
+
"keywords": [],
|
|
33
|
+
"author": "vince_lawino",
|
|
34
|
+
"license": "ISC",
|
|
35
|
+
"description": "",
|
|
36
|
+
"publishConfig": {
|
|
37
|
+
"access": "public"
|
|
38
|
+
},
|
|
39
|
+
"devDependencies": {
|
|
40
|
+
"@types/geojson": "^7946.0.16",
|
|
41
|
+
"@types/node": "^20.11.2",
|
|
42
|
+
"rimraf": "^5.0.5",
|
|
43
|
+
"typescript": "^5.7.3"
|
|
44
|
+
}
|
|
45
|
+
}
|