@onereach/step-voice 7.0.21 → 7.0.22-deskphones.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.
- package/dst/Initiate Call.d.ts +1 -0
- package/dst/Initiate Call.js +14 -3
- package/dst/Wait For Call.js +2 -0
- package/dst/uui.d.ts +5 -0
- package/dst/uui.js +102 -0
- package/dst/voice.d.ts +1 -0
- package/package.json +1 -1
package/dst/Initiate Call.d.ts
CHANGED
package/dst/Initiate Call.js
CHANGED
|
@@ -7,6 +7,7 @@
|
|
|
7
7
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
8
8
|
const tslib_1 = require("tslib");
|
|
9
9
|
const voice_1 = tslib_1.__importDefault(require("./voice"));
|
|
10
|
+
const uui_1 = require("./uui");
|
|
10
11
|
const lodash_1 = tslib_1.__importDefault(require("lodash"));
|
|
11
12
|
const timestring_1 = tslib_1.__importDefault(require("timestring"));
|
|
12
13
|
const uuid = tslib_1.__importStar(require("uuid"));
|
|
@@ -47,7 +48,7 @@ class InitiateCall extends voice_1.default {
|
|
|
47
48
|
this.exitStep('cancel');
|
|
48
49
|
}
|
|
49
50
|
async waitForCall() {
|
|
50
|
-
const { asr, tts, from: botNumber, endUserNumber, gatewaySettingsMode, sipHost, sipUser, sipPassword, sipProfile, timeout, headers, enableSpoofCallerId, spoofCallerId, isAMD, otherCallRef, otherCallRefThread, handleCancel, } = this.data;
|
|
51
|
+
const { asr, tts, from: botNumber, endUserNumber, gatewaySettingsMode, sipHost, sipUser, sipPassword, sipProfile, timeout, headers, uui, enableSpoofCallerId, spoofCallerId, isAMD, otherCallRef, otherCallRefThread, handleCancel, } = this.data;
|
|
51
52
|
const call = await this.fetchData();
|
|
52
53
|
this.triggers.once(`in/voice/${call.id}/event`, async (event) => {
|
|
53
54
|
switch (event.params.type) {
|
|
@@ -69,6 +70,7 @@ class InitiateCall extends voice_1.default {
|
|
|
69
70
|
const newCall = {
|
|
70
71
|
headers: event.params.headers,
|
|
71
72
|
...event.params.channel,
|
|
73
|
+
uui: (0, uui_1.decodeUui)(event.params.headers),
|
|
72
74
|
asr: asr.getSettings(),
|
|
73
75
|
tts: tts.getVoice(),
|
|
74
76
|
botNumber: event.params.channel.to ?? 'unknown',
|
|
@@ -157,10 +159,19 @@ class InitiateCall extends voice_1.default {
|
|
|
157
159
|
this.triggers.otherwise(async () => {
|
|
158
160
|
await this.triggers.flush();
|
|
159
161
|
const originateTimeout = (0, timestring_1.default)(`${timeout ?? 30} sec`, 'ms'); // timeout or 30 seconds
|
|
160
|
-
const customHeaders = lodash_1.default.reduce(headers, (memo, header) => {
|
|
162
|
+
const customHeaders = (0, uui_1.headersWithoutUui)(lodash_1.default.reduce(headers, (memo, header) => {
|
|
161
163
|
memo[header.name] = `${header.value}`;
|
|
162
164
|
return memo;
|
|
163
|
-
}, {});
|
|
165
|
+
}, {}));
|
|
166
|
+
try {
|
|
167
|
+
(0, uui_1.assertUuiFits)(uui);
|
|
168
|
+
const encoded = (0, uui_1.encodeUui)(uui);
|
|
169
|
+
if (encoded != null)
|
|
170
|
+
customHeaders['User-to-User'] = encoded;
|
|
171
|
+
}
|
|
172
|
+
catch (error) {
|
|
173
|
+
this.throwError(error);
|
|
174
|
+
}
|
|
164
175
|
// GET SIP PROFILE SETTINGS
|
|
165
176
|
let gateway;
|
|
166
177
|
const profile = sipProfile !== "default" /* SIP_PROFILE.DEFAULT */ ? sipProfile : undefined;
|
package/dst/Wait For Call.js
CHANGED
|
@@ -7,6 +7,7 @@
|
|
|
7
7
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
8
8
|
const tslib_1 = require("tslib");
|
|
9
9
|
const voice_1 = tslib_1.__importDefault(require("./voice"));
|
|
10
|
+
const uui_1 = require("./uui");
|
|
10
11
|
const lodash_1 = tslib_1.__importDefault(require("lodash"));
|
|
11
12
|
const defaultSessionTimeout = 5 * 60 * 1000;
|
|
12
13
|
class WaitForCall extends voice_1.default {
|
|
@@ -30,6 +31,7 @@ class WaitForCall extends voice_1.default {
|
|
|
30
31
|
// @ts-expect-error
|
|
31
32
|
endUserNumber: event.params.channel?.from ?? 'unknown',
|
|
32
33
|
...event.params.channel,
|
|
34
|
+
uui: (0, uui_1.decodeUui)(event.params.headers),
|
|
33
35
|
asr: asr.getSettings(),
|
|
34
36
|
tts: tts.getVoice()
|
|
35
37
|
};
|
package/dst/uui.d.ts
ADDED
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
export declare function encodeUui(uui: unknown): string | undefined;
|
|
2
|
+
export declare function encodedUuiLength(uui: unknown): number;
|
|
3
|
+
export declare function assertUuiFits(uui: unknown): void;
|
|
4
|
+
export declare function decodeUui(headers?: Record<string, string>): Record<string, unknown>;
|
|
5
|
+
export declare function headersWithoutUui(headers?: Record<string, string>): Record<string, string>;
|
package/dst/uui.js
ADDED
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.headersWithoutUui = exports.decodeUui = exports.assertUuiFits = exports.encodedUuiLength = exports.encodeUui = void 0;
|
|
4
|
+
const tslib_1 = require("tslib");
|
|
5
|
+
const lodash_1 = tslib_1.__importDefault(require("lodash"));
|
|
6
|
+
function uuiTypeName(uui) {
|
|
7
|
+
if (Array.isArray(uui))
|
|
8
|
+
return 'array';
|
|
9
|
+
if (uui === null)
|
|
10
|
+
return 'null';
|
|
11
|
+
return typeof uui;
|
|
12
|
+
}
|
|
13
|
+
function encodeUui(uui) {
|
|
14
|
+
if (uui === undefined || uui === null)
|
|
15
|
+
return undefined;
|
|
16
|
+
if (typeof uui === 'string')
|
|
17
|
+
return uui === '' ? undefined : uui;
|
|
18
|
+
if (Array.isArray(uui) || typeof uui === 'number' || typeof uui === 'boolean') {
|
|
19
|
+
throw new Error(`uui must be an object or a string, got ${uuiTypeName(uui)}`);
|
|
20
|
+
}
|
|
21
|
+
if (lodash_1.default.isPlainObject(uui)) {
|
|
22
|
+
if (lodash_1.default.isEmpty(uui))
|
|
23
|
+
return undefined;
|
|
24
|
+
const json = JSON.stringify(uui);
|
|
25
|
+
if (json === '{}')
|
|
26
|
+
return undefined;
|
|
27
|
+
const payload = Buffer.from(json, 'utf8').toString('base64');
|
|
28
|
+
return `${payload};encoding=base64`;
|
|
29
|
+
}
|
|
30
|
+
throw new Error(`uui must be an object or a string, got ${uuiTypeName(uui)}`);
|
|
31
|
+
}
|
|
32
|
+
exports.encodeUui = encodeUui;
|
|
33
|
+
function encodedUuiLength(uui) {
|
|
34
|
+
const encoded = encodeUui(uui);
|
|
35
|
+
return encoded == null ? 0 : encoded.length;
|
|
36
|
+
}
|
|
37
|
+
exports.encodedUuiLength = encodedUuiLength;
|
|
38
|
+
function assertUuiFits(uui) {
|
|
39
|
+
const length = encodedUuiLength(uui);
|
|
40
|
+
if (length > 256) {
|
|
41
|
+
throw new Error(`User-to-User final header value exceeds 256 characters (${length}). The cap is the final header value (object path includes ;encoding=base64).`);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
exports.assertUuiFits = assertUuiFits;
|
|
45
|
+
function headerValue(headers, name) {
|
|
46
|
+
if (headers == null)
|
|
47
|
+
return undefined;
|
|
48
|
+
const found = Object.keys(headers).find(key => key.toLowerCase() === name.toLowerCase());
|
|
49
|
+
if (found == null)
|
|
50
|
+
return undefined;
|
|
51
|
+
const value = headers[found];
|
|
52
|
+
if (typeof value !== 'string' || value === '')
|
|
53
|
+
return undefined;
|
|
54
|
+
return value;
|
|
55
|
+
}
|
|
56
|
+
function parseEncoding(header) {
|
|
57
|
+
const parts = header.split(';').map(part => part.trim());
|
|
58
|
+
const payload = parts[0] ?? '';
|
|
59
|
+
let encoding;
|
|
60
|
+
for (const part of parts.slice(1)) {
|
|
61
|
+
const eq = part.indexOf('=');
|
|
62
|
+
if (eq === -1)
|
|
63
|
+
continue;
|
|
64
|
+
const key = part.slice(0, eq).trim().toLowerCase();
|
|
65
|
+
const val = part.slice(eq + 1).trim();
|
|
66
|
+
if (key === 'encoding')
|
|
67
|
+
encoding = val;
|
|
68
|
+
}
|
|
69
|
+
return { payload, encoding };
|
|
70
|
+
}
|
|
71
|
+
function asJsonObjectOrRaw(text) {
|
|
72
|
+
try {
|
|
73
|
+
const parsed = JSON.parse(text);
|
|
74
|
+
if (lodash_1.default.isPlainObject(parsed))
|
|
75
|
+
return parsed;
|
|
76
|
+
}
|
|
77
|
+
catch { }
|
|
78
|
+
return { raw: text };
|
|
79
|
+
}
|
|
80
|
+
function decodeUui(headers) {
|
|
81
|
+
const header = headerValue(headers, 'User-to-User') ?? headerValue(headers, 'X-User-to-User');
|
|
82
|
+
if (header == null)
|
|
83
|
+
return {};
|
|
84
|
+
const { payload, encoding } = parseEncoding(header);
|
|
85
|
+
if (encoding != null && encoding.toLowerCase() !== 'base64') {
|
|
86
|
+
return { raw: header };
|
|
87
|
+
}
|
|
88
|
+
const utf8 = Buffer.from(payload, 'base64').toString('utf8');
|
|
89
|
+
return asJsonObjectOrRaw(utf8);
|
|
90
|
+
}
|
|
91
|
+
exports.decodeUui = decodeUui;
|
|
92
|
+
function headersWithoutUui(headers) {
|
|
93
|
+
const next = {};
|
|
94
|
+
for (const [key, value] of Object.entries(headers ?? {})) {
|
|
95
|
+
const lower = key.toLowerCase();
|
|
96
|
+
if (lower === 'user-to-user' || lower === 'x-user-to-user')
|
|
97
|
+
continue;
|
|
98
|
+
next[key] = value;
|
|
99
|
+
}
|
|
100
|
+
return next;
|
|
101
|
+
}
|
|
102
|
+
exports.headersWithoutUui = headersWithoutUui;
|
package/dst/voice.d.ts
CHANGED