@onereach/step-voice 7.0.2-VOIC1438.11 → 7.0.2-VOIC1438.13
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/MeetOps.d.ts +11 -1
- package/dst/MeetOps.js +148 -8
- package/dst/Send DTMF.js +1 -1
- package/package.json +1 -1
package/dst/MeetOps.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import VoiceStep, { CallStartEvent, IVoiceCall } from './voice';
|
|
1
|
+
import VoiceStep, { CallStartEvent, IVoiceCall, TODO } from './voice';
|
|
2
2
|
interface MeetOpsInput {
|
|
3
3
|
callId?: string;
|
|
4
4
|
sessionTimeout?: number | string;
|
|
@@ -17,13 +17,23 @@ interface MeetOpsInput {
|
|
|
17
17
|
enableSpoofCallerId?: boolean;
|
|
18
18
|
spoofCallerId?: string;
|
|
19
19
|
isAMD?: boolean;
|
|
20
|
+
asr: TODO;
|
|
21
|
+
meetOps: {
|
|
22
|
+
dtmfPin: string;
|
|
23
|
+
durationMs: number;
|
|
24
|
+
idleTimeoutMs: number;
|
|
25
|
+
};
|
|
20
26
|
}
|
|
21
27
|
interface MeetOpsOutput {
|
|
22
28
|
}
|
|
23
29
|
export default class MeetOps extends VoiceStep<MeetOpsInput, MeetOpsOutput, CallStartEvent> {
|
|
24
30
|
get conversation(): string | import("@onereach/flow-sdk/dst/types").IMergeField;
|
|
25
31
|
runStep(): Promise<void>;
|
|
32
|
+
onAwake(): Promise<void>;
|
|
26
33
|
waitForJoin(): Promise<void>;
|
|
34
|
+
private onHangup;
|
|
35
|
+
private onError;
|
|
36
|
+
private onCall;
|
|
27
37
|
originate(call: IVoiceCall): Promise<void>;
|
|
28
38
|
}
|
|
29
39
|
export {};
|
package/dst/MeetOps.js
CHANGED
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
const tslib_1 = require("tslib");
|
|
4
4
|
const uuid = tslib_1.__importStar(require("uuid"));
|
|
5
|
+
const timestring_1 = tslib_1.__importDefault(require("timestring"));
|
|
5
6
|
const voice_1 = tslib_1.__importDefault(require("./voice"));
|
|
6
7
|
class MeetOps extends voice_1.default {
|
|
7
8
|
get conversation() {
|
|
@@ -14,27 +15,160 @@ class MeetOps extends voice_1.default {
|
|
|
14
15
|
if (!this.session.key) {
|
|
15
16
|
await this.session.start({
|
|
16
17
|
key: callId,
|
|
17
|
-
timeout:
|
|
18
|
+
timeout: (0, timestring_1.default)('120 min'),
|
|
18
19
|
reporting: {
|
|
19
20
|
settingsKey: 'session',
|
|
20
21
|
startedBy: 'Bot',
|
|
21
|
-
sessionType: 'Phone'
|
|
22
|
-
}
|
|
22
|
+
sessionType: 'Phone',
|
|
23
|
+
},
|
|
23
24
|
});
|
|
24
25
|
}
|
|
25
26
|
const convData = { id: callId, type: 'voicer', vv: 0 };
|
|
26
27
|
await this.startConversation(convData);
|
|
27
28
|
this.gotoState('waitForJoin');
|
|
28
29
|
}
|
|
30
|
+
async onAwake() {
|
|
31
|
+
const { handleCancel } = this.data;
|
|
32
|
+
await super.onAwake();
|
|
33
|
+
const call = await this.fetchData();
|
|
34
|
+
if (!call.ended)
|
|
35
|
+
throw new Error('unpexpected awake');
|
|
36
|
+
if (handleCancel !== true)
|
|
37
|
+
throw new Error('hangup cancel');
|
|
38
|
+
this.exitStep('cancel');
|
|
39
|
+
}
|
|
29
40
|
async waitForJoin() {
|
|
30
41
|
const call = await this.fetchData();
|
|
31
|
-
|
|
32
|
-
|
|
42
|
+
this.triggers.once(`in/voice/${call.id}/event`, async (event) => {
|
|
43
|
+
this.log.debug('call event type:', event.params.type);
|
|
44
|
+
this.log.debug('call event:', event);
|
|
45
|
+
switch (event.params.type) {
|
|
46
|
+
case 'is_flow_ready':
|
|
47
|
+
return this.exitFlow({ is_ready: true });
|
|
48
|
+
case 'call':
|
|
49
|
+
return await this.onCall(event, call);
|
|
50
|
+
case 'hangup':
|
|
51
|
+
return await this.onHangup(event, call);
|
|
52
|
+
case 'error':
|
|
53
|
+
return await this.onError(event);
|
|
54
|
+
default:
|
|
55
|
+
return this.exitFlow();
|
|
56
|
+
}
|
|
57
|
+
});
|
|
33
58
|
this.triggers.otherwise(async () => {
|
|
34
59
|
await this.triggers.flush();
|
|
35
60
|
await this.originate(call);
|
|
36
61
|
});
|
|
37
62
|
}
|
|
63
|
+
async onHangup(event, call) {
|
|
64
|
+
const { handleCancel } = this.data;
|
|
65
|
+
await this.handleHangup(call);
|
|
66
|
+
if (handleCancel && event.params.error?.name === 'CancelError') {
|
|
67
|
+
return this.exitStep('cancel');
|
|
68
|
+
}
|
|
69
|
+
return this.throwError(event.params.error ?? {
|
|
70
|
+
name: 'HangupError',
|
|
71
|
+
message: 'unpexpected hangup during init call'
|
|
72
|
+
});
|
|
73
|
+
}
|
|
74
|
+
async onError(event) {
|
|
75
|
+
const { from: botNumber, endUserNumber } = this.data;
|
|
76
|
+
const error = event.params.error;
|
|
77
|
+
const errorStatus = error?.originateStatus ?? 'UNKNOWN';
|
|
78
|
+
const errorCall = {
|
|
79
|
+
botNumber,
|
|
80
|
+
endUserNumber
|
|
81
|
+
};
|
|
82
|
+
switch (errorStatus) {
|
|
83
|
+
case 'USER_BUSY':
|
|
84
|
+
await this.transcript(errorCall, {
|
|
85
|
+
action: 'Call Busy',
|
|
86
|
+
actionFromBot: true
|
|
87
|
+
});
|
|
88
|
+
await this.updateData();
|
|
89
|
+
return this.exitStep('busy', errorCall);
|
|
90
|
+
case 'NO_ANSWER':
|
|
91
|
+
case 'NO_USER_RESPONSE':
|
|
92
|
+
await this.transcript(errorCall, {
|
|
93
|
+
action: 'Call No Answer',
|
|
94
|
+
actionFromBot: true
|
|
95
|
+
});
|
|
96
|
+
await this.updateData();
|
|
97
|
+
return this.exitStep('no answer', errorCall);
|
|
98
|
+
default:
|
|
99
|
+
break;
|
|
100
|
+
}
|
|
101
|
+
await this.transcript(errorCall, {
|
|
102
|
+
action: 'Call Error',
|
|
103
|
+
actionFromBot: true
|
|
104
|
+
});
|
|
105
|
+
return this.throwError({
|
|
106
|
+
name: error?.name ?? 'VoiceError',
|
|
107
|
+
message: `${String(error?.date)}: ${errorStatus}`
|
|
108
|
+
});
|
|
109
|
+
}
|
|
110
|
+
async onCall(event, call) {
|
|
111
|
+
const { endUserNumber,
|
|
112
|
+
// isAMD
|
|
113
|
+
asr } = this.data;
|
|
114
|
+
const newCall = {
|
|
115
|
+
headers: event.params.headers,
|
|
116
|
+
...event.params.channel,
|
|
117
|
+
asr: asr.getSettings(),
|
|
118
|
+
// tts: tts.getVoice(),
|
|
119
|
+
botNumber: event.params.channel.to ?? 'unknown',
|
|
120
|
+
endUserNumber
|
|
121
|
+
};
|
|
122
|
+
delete newCall.from;
|
|
123
|
+
delete newCall.to;
|
|
124
|
+
newCall._conv = call._conv;
|
|
125
|
+
await this.startConversation(newCall);
|
|
126
|
+
await this.transcript(newCall, {
|
|
127
|
+
action: 'Call Start',
|
|
128
|
+
reportingSettingsKey: 'transcript',
|
|
129
|
+
actionFromBot: true
|
|
130
|
+
});
|
|
131
|
+
const commands = [
|
|
132
|
+
/* {
|
|
133
|
+
name: 'send-dtmf',
|
|
134
|
+
params: {
|
|
135
|
+
dtmf: '#',
|
|
136
|
+
afterDelay: 250,
|
|
137
|
+
beforeDelay: 250,
|
|
138
|
+
tonesDuration: 100,
|
|
139
|
+
}
|
|
140
|
+
},
|
|
141
|
+
{
|
|
142
|
+
name: 'record-session'
|
|
143
|
+
},
|
|
144
|
+
{
|
|
145
|
+
name: 'start-avmd',
|
|
146
|
+
params: {
|
|
147
|
+
type: 'avmd_detect'
|
|
148
|
+
}
|
|
149
|
+
} */
|
|
150
|
+
{
|
|
151
|
+
name: 'meet-ops',
|
|
152
|
+
params: {
|
|
153
|
+
meetOps: {
|
|
154
|
+
dtmfPin: '506 433 169 5884#'.replace(/ /g, ''),
|
|
155
|
+
durationMs: 10 * 60 * 1000,
|
|
156
|
+
idleTimeoutMs: 60 * 1000,
|
|
157
|
+
},
|
|
158
|
+
}
|
|
159
|
+
}
|
|
160
|
+
];
|
|
161
|
+
/* if (asr.serverSettings.enabled) {
|
|
162
|
+
commands.push({
|
|
163
|
+
name: 'start-recognition',
|
|
164
|
+
params: {
|
|
165
|
+
type: asr.serverSettings.engine
|
|
166
|
+
}
|
|
167
|
+
})
|
|
168
|
+
} */
|
|
169
|
+
await this.sendCommands(newCall, commands);
|
|
170
|
+
return this.exitStep('success');
|
|
171
|
+
}
|
|
38
172
|
async originate(call) {
|
|
39
173
|
const { id: callId } = call;
|
|
40
174
|
const {
|
|
@@ -42,7 +176,7 @@ class MeetOps extends voice_1.default {
|
|
|
42
176
|
// tts,
|
|
43
177
|
from: botNumber, endUserNumber: dianInNumber, sipHost, sipUser, sipPassword, timeout, headers, enableSpoofCallerId, spoofCallerId,
|
|
44
178
|
// isAMD,
|
|
45
|
-
otherCallRef, otherCallRefThread,
|
|
179
|
+
otherCallRef, otherCallRefThread, meetOps,
|
|
46
180
|
// handleCancel
|
|
47
181
|
} = this.data;
|
|
48
182
|
const customHeadersEntities = headers?.map(({ name, value }) => [name, `${value}`]) || [];
|
|
@@ -51,12 +185,12 @@ class MeetOps extends voice_1.default {
|
|
|
51
185
|
? {
|
|
52
186
|
host: sipHost,
|
|
53
187
|
username: sipUser,
|
|
54
|
-
password: sipPassword
|
|
188
|
+
password: sipPassword,
|
|
55
189
|
}
|
|
56
190
|
: undefined;
|
|
57
191
|
const spoofCallerIdConfig = {
|
|
58
192
|
enableSpoofCallerId,
|
|
59
|
-
spoofCallerId
|
|
193
|
+
spoofCallerId,
|
|
60
194
|
};
|
|
61
195
|
const params = {
|
|
62
196
|
id: callId,
|
|
@@ -68,8 +202,14 @@ class MeetOps extends voice_1.default {
|
|
|
68
202
|
version: 2,
|
|
69
203
|
gateway,
|
|
70
204
|
timeout,
|
|
205
|
+
meetOps,
|
|
71
206
|
};
|
|
72
207
|
console.log(otherCallRef, otherCallRefThread, params);
|
|
208
|
+
await this.thread.emitAsync({
|
|
209
|
+
target: 'provider',
|
|
210
|
+
name: 'out/voice/originate/v2',
|
|
211
|
+
params,
|
|
212
|
+
});
|
|
73
213
|
// const otherThread = this.process.getSafeThread(otherCallRefThread || this.thread.id)
|
|
74
214
|
// const otherCall: IVoiceCall | undefined = await otherThread.get(otherCallRef)
|
|
75
215
|
// if (otherCall == null) throw new Error(`otherCall not found: ${otherCallRef}`)
|
package/dst/Send DTMF.js
CHANGED