@jambonz/node-red-contrib-jambonz 2.4.30 → 2.4.32
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/package.json +2 -2
- package/src/nodes/create_call.html +9 -2
- package/src/nodes/create_call.js +3 -2
- package/src/nodes/dial.html +48 -3
- package/src/nodes/dial.js +15 -2
- package/src/nodes/generic-verb.html +35 -14
- package/src/nodes/generic-verb.js +16 -6
- package/src/nodes/lcc.html +3 -2
- package/src/nodes/lcc.js +3 -0
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jambonz/node-red-contrib-jambonz",
|
|
3
|
-
"version": "2.4.
|
|
3
|
+
"version": "2.4.32",
|
|
4
4
|
"description": "Node-RED nodes for jambonz platform",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"node-red"
|
|
@@ -64,7 +64,7 @@
|
|
|
64
64
|
"hash-sum": "^2.0.0",
|
|
65
65
|
"is-utf8": "^0.2.1",
|
|
66
66
|
"media-typer": "^1.1.0",
|
|
67
|
-
"multer": "^
|
|
67
|
+
"multer": "^2.0.1",
|
|
68
68
|
"mustache": "^4.2.0",
|
|
69
69
|
"on-headers": "^1.0.2",
|
|
70
70
|
"raw-body": "^2.5.2",
|
|
@@ -20,8 +20,9 @@
|
|
|
20
20
|
trunk: {value: ''},
|
|
21
21
|
trunkType: {value: 'str'},
|
|
22
22
|
dest: {value: 'phone', required: true},
|
|
23
|
-
timeout: {
|
|
24
|
-
|
|
23
|
+
timeout: {value: '' },
|
|
24
|
+
timeoutType: {value: 'num'},
|
|
25
|
+
tag: {value: '{}'},
|
|
25
26
|
tagType: {value: 'json'},
|
|
26
27
|
application: {value: ''},
|
|
27
28
|
appName: {},
|
|
@@ -113,6 +114,11 @@
|
|
|
113
114
|
default: $('#node-input-trunkType').val(),
|
|
114
115
|
types: ['str', 'msg', 'flow', 'global', 'jsonata', 'env', mustacheType],
|
|
115
116
|
typeField: $('#node-input-trunkType')
|
|
117
|
+
});
|
|
118
|
+
$('#node-input-timeout').typedInput({
|
|
119
|
+
default: $('#node-input-timeoutType').val(),
|
|
120
|
+
types: ['num', 'msg', 'flow', 'global', 'jsonata', 'env'],
|
|
121
|
+
typeField: $('#node-input-timeoutType')
|
|
116
122
|
});
|
|
117
123
|
var populateApplications = function() {
|
|
118
124
|
var serverId = $('#node-input-server option:selected').val();
|
|
@@ -256,6 +262,7 @@
|
|
|
256
262
|
<div class="form-row">
|
|
257
263
|
<label for="node-input-timeout">Ring timeout</label>
|
|
258
264
|
<input type="text" id="node-input-timeout" placeholder="ring no answer timeout in secs (default: 60)">
|
|
265
|
+
<input type="hidden" id="node-input-timeoutType">
|
|
259
266
|
</div>
|
|
260
267
|
<div class="form-row">
|
|
261
268
|
<label for="node-input-tag">Tag data</label>
|
package/src/nodes/create_call.js
CHANGED
|
@@ -22,6 +22,7 @@ module.exports = function(RED) {
|
|
|
22
22
|
var from = await new_resolve(RED, config.from, config.fromType, node, msg);
|
|
23
23
|
var to = await new_resolve(RED, config.to, config.toType, node, msg);
|
|
24
24
|
var tag = await new_resolve(RED, config.tag, config.tagType, node, msg);
|
|
25
|
+
var timeout = await new_resolve(RED, config.timeout, config.timeoutType, node, msg);
|
|
25
26
|
|
|
26
27
|
const opts = {
|
|
27
28
|
from,
|
|
@@ -64,8 +65,8 @@ module.exports = function(RED) {
|
|
|
64
65
|
break;
|
|
65
66
|
}
|
|
66
67
|
|
|
67
|
-
if (
|
|
68
|
-
|
|
68
|
+
if (timeout) {
|
|
69
|
+
timeout = parseInt(timeout);
|
|
69
70
|
if (timeout > 0) opts.timeout = timeout;
|
|
70
71
|
}
|
|
71
72
|
|
package/src/nodes/dial.html
CHANGED
|
@@ -17,6 +17,7 @@
|
|
|
17
17
|
actionhookType: {value: 'str'},
|
|
18
18
|
answeronbridge: {value: false},
|
|
19
19
|
anchormedia: {value: false},
|
|
20
|
+
exitmediapath: {value: false},
|
|
20
21
|
callerid: {value: ''},
|
|
21
22
|
calleridType: {value: ''},
|
|
22
23
|
callername: {value: ''},
|
|
@@ -33,8 +34,14 @@
|
|
|
33
34
|
dtmfhookType: {value: 'str'},
|
|
34
35
|
onholdhook: {value: ''},
|
|
35
36
|
onholdhookType: {value: 'str'},
|
|
36
|
-
timelimit: {
|
|
37
|
-
|
|
37
|
+
timelimit: {},
|
|
38
|
+
timelimitType: {value: 'num'},
|
|
39
|
+
timeout: {},
|
|
40
|
+
timeoutType: {value: 'num'},
|
|
41
|
+
boostaudiosignal: { value: "" },
|
|
42
|
+
boostaudiosignalType: { value: "str" },
|
|
43
|
+
tag: {value: '{}'},
|
|
44
|
+
tagType: {value: 'json'},
|
|
38
45
|
listenurl: {value: ''},
|
|
39
46
|
listenurlType: {value: 'str'},
|
|
40
47
|
transcriptionhook: {},
|
|
@@ -74,7 +81,8 @@
|
|
|
74
81
|
amd_timers_decisionTimeoutMs: {},
|
|
75
82
|
amd_timers_greetingCompletionTimeoutMs:{},
|
|
76
83
|
amd_timers_noSpeechTimeoutMs: {},
|
|
77
|
-
amd_timers_toneTimeoutMs: {}
|
|
84
|
+
amd_timers_toneTimeoutMs: {},
|
|
85
|
+
amd_digitCount: {},
|
|
78
86
|
},
|
|
79
87
|
inputs:1,
|
|
80
88
|
outputs:1,
|
|
@@ -122,6 +130,15 @@
|
|
|
122
130
|
types: ['str', 'msg', 'flow', 'global', 'jsonata', 'env', mustacheType],
|
|
123
131
|
typeField: $('#node-input-onholdhookType')
|
|
124
132
|
});
|
|
133
|
+
$('#node-input-boostaudiosignal').typedInput({
|
|
134
|
+
types: ['str', 'msg', 'flow', 'global', 'jsonata', 'env', mustacheType],
|
|
135
|
+
typeField: $('#node-input-boostaudiosignalType')
|
|
136
|
+
});
|
|
137
|
+
$('#node-input-tag').typedInput({
|
|
138
|
+
default: $('#node-input-tagType').val(),
|
|
139
|
+
types: ['json', 'msg', 'flow', 'global', 'jsonata', 'env', mustacheType],
|
|
140
|
+
typeField: $('#node-input-tagType')
|
|
141
|
+
});
|
|
125
142
|
$('#node-input-transcribeurl').typedInput({
|
|
126
143
|
types: ['str', 'msg', 'flow', 'global', 'jsonata', 'env', mustacheType],
|
|
127
144
|
typeField: $('#node-input-transcribeurlType')
|
|
@@ -154,6 +171,14 @@
|
|
|
154
171
|
types: ['num', 'msg', 'flow', 'global', 'jsonata', 'env', mustacheType],
|
|
155
172
|
typeField: $('#node-input-naicsType')
|
|
156
173
|
});
|
|
174
|
+
$('#node-input-timeout').typedInput({
|
|
175
|
+
types: ['num', 'msg', 'flow', 'global', 'jsonata', 'env'],
|
|
176
|
+
typeField: $('#node-input-timeoutType')
|
|
177
|
+
});
|
|
178
|
+
$('#node-input-timelimit').typedInput({
|
|
179
|
+
types: ['num', 'msg', 'flow', 'global', 'jsonata', 'env'],
|
|
180
|
+
typeField: $('#node-input-timelimitType')
|
|
181
|
+
});
|
|
157
182
|
|
|
158
183
|
prepareSttControls(node);
|
|
159
184
|
prepareSttControls(node, '#node-input-amd_recognizer_vendor', '#node-input-amd_recognizer_lang');
|
|
@@ -474,6 +499,10 @@
|
|
|
474
499
|
<label for="node-input-anchormedia">Anchor media</label>
|
|
475
500
|
<input type="checkbox" id="node-input-anchormedia">
|
|
476
501
|
</div>
|
|
502
|
+
<div class="form-row">
|
|
503
|
+
<label for="node-input-exitmediapath">Exit media path</label>
|
|
504
|
+
<input type="checkbox" id="node-input-exitmediapath">
|
|
505
|
+
</div>
|
|
477
506
|
<div class="form-row">
|
|
478
507
|
<label for="node-input-callerid">Caller ID</label>
|
|
479
508
|
<input type="text" id="node-input-callerid" placeholder="caller id to place on outbound call">
|
|
@@ -517,10 +546,22 @@
|
|
|
517
546
|
<div class="form-row">
|
|
518
547
|
<label for="node-input-timelimit">Time limit</label>
|
|
519
548
|
<input type="text" id="node-input-timelimit" placeholder="max duration of call in secs">
|
|
549
|
+
<input type="hidden" id="node-input-timelimitType">
|
|
520
550
|
</div>
|
|
521
551
|
<div class="form-row">
|
|
522
552
|
<label for="node-input-timeout"><i class="icon-tag"></i> Timeout</label>
|
|
523
553
|
<input type="text" id="node-input-timeout" placeholder="ring no answer timeout in secs (default: 60)">
|
|
554
|
+
<input type="hidden" id="node-input-timeoutType">
|
|
555
|
+
</div>
|
|
556
|
+
<div class="form-row">
|
|
557
|
+
<label for="node-input-boostaudiosignal">Boost audio signal</label>
|
|
558
|
+
<input type="text" id="node-input-boostaudiosignal" placeholder="boost audio volume in decibels">
|
|
559
|
+
<input type="hidden" id="node-input-boostaudiosignalType">
|
|
560
|
+
</div>
|
|
561
|
+
<div class="form-row">
|
|
562
|
+
<label for="node-input-tag">Tag data</label>
|
|
563
|
+
<input type="text" id="node-input-tag" placeholder="tag object">
|
|
564
|
+
<input type="hidden" id="node-input-tagType">
|
|
524
565
|
</div>
|
|
525
566
|
<fieldset>
|
|
526
567
|
<legend>Live audio</legend>
|
|
@@ -690,6 +731,10 @@
|
|
|
690
731
|
<label for="node-input-amd_thresholdWordCount">Threshold Word Count</label>
|
|
691
732
|
<input type="text" id="node-input-amd_thresholdWordCount">
|
|
692
733
|
</div>
|
|
734
|
+
<div class="form-row">
|
|
735
|
+
<label for="node-input-amd_digitCount">Digit Count</label>
|
|
736
|
+
<input type="text" id="node-input-amd_digitCount">
|
|
737
|
+
</div>
|
|
693
738
|
<div class="form-row">
|
|
694
739
|
<label for="node-input-amd_timers_decisionTimeoutMs">Decision Timeout</label>
|
|
695
740
|
<input type="text" id="node-input-amd_timers_decisionTimeoutMs">
|
package/src/nodes/dial.js
CHANGED
|
@@ -41,8 +41,8 @@ module.exports = function(RED) {
|
|
|
41
41
|
verb: 'dial',
|
|
42
42
|
target,
|
|
43
43
|
answerOnBridge: config.answeronbridge,
|
|
44
|
-
timeLimit: config.timelimit
|
|
45
|
-
timeout: config.timeout
|
|
44
|
+
timeLimit: await new_resolve(RED, config.timelimit, config.timelimitType, node, msg),
|
|
45
|
+
timeout: await new_resolve(RED, config.timeout, config.timeoutType, node, msg),
|
|
46
46
|
callerId: await new_resolve(RED, config.callerid, config.calleridType, node, msg),
|
|
47
47
|
callerName: await new_resolve(RED, config.callername, config.callernameType, node, msg),
|
|
48
48
|
actionHook: await new_resolve(RED, config.actionhook, config.actionhookType, node, msg),
|
|
@@ -56,10 +56,22 @@ module.exports = function(RED) {
|
|
|
56
56
|
data.anchorMedia = config.anchormedia;
|
|
57
57
|
}
|
|
58
58
|
|
|
59
|
+
if (config.hasOwnProperty('exitmediapath')) {
|
|
60
|
+
data.exitMediaPath = config.exitmediapath;
|
|
61
|
+
}
|
|
62
|
+
|
|
59
63
|
if (config.onholdhook) {
|
|
60
64
|
data.onHoldHook = await new_resolve(RED, config.onholdhook, config.onholdhookType, node, msg);
|
|
61
65
|
}
|
|
62
66
|
|
|
67
|
+
if (config.tag) {
|
|
68
|
+
data.tag = await new_resolve(RED, config.tag, config.tagType, node, msg);
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
if (config.boostaudiosignal) {
|
|
72
|
+
data.boostAudioSignal = await new_resolve(RED, config.boostaudiosignal, config.boostaudiosignalType, node, msg)
|
|
73
|
+
}
|
|
74
|
+
|
|
63
75
|
// headers
|
|
64
76
|
const headers = {};
|
|
65
77
|
config.headers.forEach(function(h) {
|
|
@@ -138,6 +150,7 @@ module.exports = function(RED) {
|
|
|
138
150
|
data.amd = {}
|
|
139
151
|
data.amd.actionHook = _amd_actionHook;
|
|
140
152
|
config.amd_thresholdWordCount && (data.amd.thresholdWordCount = Number(config.amd_thresholdWordCount))
|
|
153
|
+
config.amd_digitCount && (data.amd.digitCount = Number(config.amd_digitCount))
|
|
141
154
|
data.amd.timers = {
|
|
142
155
|
...(config.amd_timers_decisionTimeoutMs && {decisionTimeoutMs: Number(config.amd_timers_decisionTimeoutMs)}),
|
|
143
156
|
...(config.amd_timers_greetingCompletionTimeoutMs && {greetingCompletionTimeoutMs: Number(config.amd_timers_greetingCompletionTimeoutMs)}),
|
|
@@ -1,6 +1,14 @@
|
|
|
1
1
|
<!-- Javascript -->
|
|
2
2
|
<script type="text/javascript">
|
|
3
|
-
|
|
3
|
+
|
|
4
|
+
function formatjson(e) {
|
|
5
|
+
e.preventDefault();
|
|
6
|
+
e = s.getValue() || "";
|
|
7
|
+
try {
|
|
8
|
+
e = JSON.stringify(JSON.parse(e), null, 4)
|
|
9
|
+
} catch (e) {}
|
|
10
|
+
s.getSession().setValue(e || "", -1)
|
|
11
|
+
}
|
|
4
12
|
|
|
5
13
|
RED.nodes.registerType('generic',{
|
|
6
14
|
category: 'jambonz',
|
|
@@ -8,20 +16,32 @@
|
|
|
8
16
|
defaults: {
|
|
9
17
|
name: {value: ''},
|
|
10
18
|
verb: {required: true},
|
|
11
|
-
data: {value: '
|
|
12
|
-
|
|
19
|
+
data: { value: '',
|
|
20
|
+
validate: function(v) {
|
|
21
|
+
return (typeof(JSON.parse(v)) == 'object')
|
|
22
|
+
}
|
|
23
|
+
},
|
|
13
24
|
},
|
|
14
25
|
inputs:1,
|
|
15
26
|
outputs:1,
|
|
16
27
|
icon: "font-awesome/fa-cubes",
|
|
17
28
|
label: function() { return this.name || 'generic';},
|
|
18
29
|
oneditprepare: function() {
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
30
|
+
this.editor = RED.editor.createEditor({
|
|
31
|
+
id: 'node-input-data-editor',
|
|
32
|
+
mode: 'ace/mode/json',
|
|
33
|
+
value: this.data
|
|
34
|
+
});
|
|
35
|
+
},
|
|
36
|
+
oneditsave: function() {
|
|
37
|
+
this.data = this.editor.getValue();
|
|
38
|
+
this.editor.destroy();
|
|
39
|
+
delete this.editor;
|
|
40
|
+
},
|
|
41
|
+
oneditcancel: function() {
|
|
42
|
+
this.editor.destroy();
|
|
43
|
+
delete this.editor;
|
|
44
|
+
}
|
|
25
45
|
});
|
|
26
46
|
</script>
|
|
27
47
|
|
|
@@ -35,11 +55,12 @@
|
|
|
35
55
|
<label for="node-input-verb">Verb</label>
|
|
36
56
|
<input type="text" id="node-input-verb" placeholder="verb">
|
|
37
57
|
</div>
|
|
38
|
-
<div class="form-row">
|
|
39
|
-
<label for="node-input-data">Attributes</label>
|
|
40
|
-
<
|
|
41
|
-
|
|
42
|
-
|
|
58
|
+
<div class="form-row" style="position: relative; height: 250px;">
|
|
59
|
+
<label for="node-input-data"><i class="fa fa-code"></i> Attributes</label>
|
|
60
|
+
<div style="position: absolute; right: 0; bottom: 0; top: 0; left: 100px;">
|
|
61
|
+
<div id="node-input-data-editor" style="width: 100%; height: 100%;"></div>
|
|
62
|
+
</div>
|
|
63
|
+
</div>
|
|
43
64
|
</script>
|
|
44
65
|
|
|
45
66
|
<!-- Help Text -->
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
var {appendVerb, new_resolve} = require('./libs')
|
|
2
|
+
const assert = require('node:assert/strict');
|
|
2
3
|
|
|
3
4
|
module.exports = function(RED) {
|
|
4
5
|
function generic(config) {
|
|
@@ -6,12 +7,21 @@ module.exports = function(RED) {
|
|
|
6
7
|
var node = this;
|
|
7
8
|
node.verb = config.verb
|
|
8
9
|
node.on('input', async function(msg) {
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
10
|
+
if (config.data.length==0) config.data='{}';
|
|
11
|
+
const _data = await new_resolve(RED, config.data, 'mustache', node, msg);
|
|
12
|
+
try {
|
|
13
|
+
const data = JSON.parse(_data)
|
|
14
|
+
assert.ok(typeof(data)=='object')
|
|
15
|
+
appendVerb(msg, {
|
|
16
|
+
...{verb: node.verb},
|
|
17
|
+
...data
|
|
18
|
+
});
|
|
19
|
+
node.send(msg);
|
|
20
|
+
} catch (error) {
|
|
21
|
+
console.error(error)
|
|
22
|
+
node.error(`Invalid Attributes object: ${_data}`)
|
|
23
|
+
}
|
|
24
|
+
|
|
15
25
|
});
|
|
16
26
|
}
|
|
17
27
|
RED.nodes.registerType('generic', generic);
|
package/src/nodes/lcc.html
CHANGED
|
@@ -355,7 +355,8 @@
|
|
|
355
355
|
<div class="form-row">
|
|
356
356
|
<label for="node-input-action">Action</label>
|
|
357
357
|
<select id="node-input-action">
|
|
358
|
-
<option value="hangup">hangup call</option>
|
|
358
|
+
<option value="hangup">hangup answered call</option>
|
|
359
|
+
<option value="cancel">cancel call</option>
|
|
359
360
|
<option value="mute">mute caller</option>
|
|
360
361
|
<option value="unmute">unmute caller</option>
|
|
361
362
|
<option value="mute_conf">mute conference participants</option>
|
|
@@ -508,7 +509,7 @@
|
|
|
508
509
|
<div class="form-row">
|
|
509
510
|
<label for="node-input-dubSay">Say Text</label>
|
|
510
511
|
<input type="text" id="node-input-dubSay" placeholder="Text">
|
|
511
|
-
<input type="hidden" id="node-input-
|
|
512
|
+
<input type="hidden" id="node-input-dubSayType">
|
|
512
513
|
</div>
|
|
513
514
|
<div class="form-row">
|
|
514
515
|
<label for="node-input-dubLoop">Loop</label>
|