mirror of
https://github.com/donl/plivo-node.git
synced 2026-06-30 06:12:08 -06:00
Merge branch 'master' into 10dlc-api
This commit is contained in:
commit
744488e2d8
7 changed files with 207 additions and 14 deletions
10
.travis.yml
10
.travis.yml
|
|
@ -1,10 +0,0 @@
|
|||
service_name: travis-ci
|
||||
language: node_js
|
||||
node_js:
|
||||
# - "node" commenting this as we have to find out a solution for node12 & gulp3
|
||||
- "lts/*"
|
||||
- "8"
|
||||
- "7"
|
||||
- "6"
|
||||
- "5"
|
||||
- "4"
|
||||
10
CHANGELOG.md
10
CHANGELOG.md
|
|
@ -1,7 +1,13 @@
|
|||
# Change Log
|
||||
|
||||
## [v4.24.0](https://github.com/plivo/plivo-node/tree/v4.24.0) (2021-12-02)
|
||||
-- 10dlc Api support.
|
||||
## [v4.25.0](https://github.com/plivo/plivo-node/tree/v4.25.0) (2021-12-02)
|
||||
**Features - SMS: 10dlc Api support**
|
||||
- Brand and Campaign API.
|
||||
|
||||
## [v4.24.0](https://github.com/plivo/plivo-node/tree/v4.24.0) (2021-11-30)
|
||||
**Features - Voice: Multiparty calls**
|
||||
- The [Add Multiparty Call API](https://www.plivo.com/docs/voice/api/multiparty-call/participants#add-a-participant) allows for greater functionality by accepting options like `start recording audio`, `stop recording audio`, and their HTTP methods.
|
||||
- [Multiparty Calls](https://www.plivo.com/docs/voice/api/multiparty-call/) now has new APIs to `stop` and `play` audio.
|
||||
|
||||
## [v4.23.1](https://github.com/plivo/plivo-node/tree/v4.23.1) (2021-10-13)
|
||||
**Bug Fix**
|
||||
|
|
|
|||
|
|
@ -15,6 +15,7 @@ const clientKey = Symbol();
|
|||
const action = 'MultiPartyCall/';
|
||||
const idField = 'mpcUuid';
|
||||
const secondaryAction = 'Participant/';
|
||||
const secondaryMemberAction = 'Member/';
|
||||
const secondaryIdField = 'participantUuid';
|
||||
|
||||
export class MPCError extends Error { }
|
||||
|
|
@ -306,6 +307,29 @@ export class MultiPartyCall extends PlivoResource{
|
|||
else {
|
||||
params.exitSoundMethod = 'GET'
|
||||
}
|
||||
|
||||
if(params.startRecordingAudio){
|
||||
validUrl('startRecordingAudio', params.startRecordingAudio, false)
|
||||
}
|
||||
|
||||
if(params.startRecordingAudioMethod){
|
||||
validParam('startRecordingAudioMethod', params.startRecordingAudioMethod.toUpperCase(), [String], false, ['GET', 'POST'])
|
||||
}
|
||||
else {
|
||||
params.startRecordingAudioMethod = 'GET'
|
||||
}
|
||||
|
||||
if(params.stopRecordingAudio){
|
||||
validUrl('stopRecordingAudio', params.stopRecordingAudio, false)
|
||||
}
|
||||
|
||||
if(params.stopRecordingAudioMethod){
|
||||
validParam('stopRecordingAudioMethod', params.stopRecordingAudioMethod.toUpperCase(), [String], false, ['GET', 'POST'])
|
||||
}
|
||||
else {
|
||||
params.stopRecordingAudioMethod = 'GET'
|
||||
}
|
||||
|
||||
if(params.to && (String(params.ringTimeout).split('<').length > params.to.split('<').length)){
|
||||
throw new MPCError("RingTimeout:number of ring_timeout(s) should be same as number of destination(s)")
|
||||
}
|
||||
|
|
@ -449,6 +473,32 @@ export class MultiPartyCallParticipant extends PlivoSecondaryResource{
|
|||
|
||||
}
|
||||
|
||||
export class MultiPartyCallMember extends PlivoSecondaryResource{
|
||||
constructor(client, data= {}) {
|
||||
super(action, MultiPartyCall, idField, secondaryMemberAction, MultiPartyCallMember, secondaryIdField, client);
|
||||
|
||||
if (idField in data) {
|
||||
this.id = data[idField];
|
||||
}
|
||||
|
||||
if(secondaryIdField in data){
|
||||
this.secondaryId = data[secondaryIdField];
|
||||
}
|
||||
|
||||
extend(this, data);
|
||||
this[clientKey] = client;
|
||||
}
|
||||
|
||||
startPlayAudio(params){
|
||||
params.isVoiceRequest = 'true';
|
||||
return super.executeAction(this.id, this.secondaryId + '/Play', 'POST', params)
|
||||
}
|
||||
|
||||
stopPlayAudio(){
|
||||
return super.executeAction(this.id, this.secondaryId +'/Play', 'DELETE',{'isVoiceRequest' : 'true'})
|
||||
}
|
||||
}
|
||||
|
||||
export class MultiPartyCallInterface extends PlivoResourceInterface{
|
||||
constructor(client, data = {}) {
|
||||
super(action, MultiPartyCall, idField, client);
|
||||
|
|
@ -737,4 +787,33 @@ export class MultiPartyCallInterface extends PlivoResourceInterface{
|
|||
return new MultiPartyCallParticipant(this[clientKey], {id: mpcId[0] + mpcId[1], secondaryId: participantId}).getParticipant()
|
||||
}
|
||||
|
||||
startPlayAudio(participantId, url, params = {}){
|
||||
validParam('participantId', participantId, [String, Number], true)
|
||||
validUrl('url', url, true)
|
||||
if(params.uuid){
|
||||
validParam('uuid', params.uuid, [String], false)
|
||||
}
|
||||
if(params.friendlyName){
|
||||
validParam('friendlyName', params.friendlyName, [String], false)
|
||||
}
|
||||
let mpcId = this.makeMpcId(params.uuid, params.friendlyName)
|
||||
delete params.uuid
|
||||
delete params.friendlyName
|
||||
params.url = url
|
||||
return new MultiPartyCallMember(this[clientKey], {id: mpcId[0] + mpcId[1], secondaryId: participantId}).startPlayAudio(params)
|
||||
}
|
||||
|
||||
stopPlayAudio(participantId, params = {}){
|
||||
validParam('participantId', participantId, [String, Number], true)
|
||||
if(params.uuid){
|
||||
validParam('uuid', params.uuid, [String], false)
|
||||
}
|
||||
if(params.friendlyName){
|
||||
validParam('friendlyName', params.friendlyName, [String], false)
|
||||
}
|
||||
let mpcId = this.makeMpcId(params.uuid, params.friendlyName)
|
||||
delete params.uuid
|
||||
delete params.friendlyName
|
||||
return new MultiPartyCallMember(this[clientKey], {id: mpcId[0] + mpcId[1], secondaryId: participantId}).stopPlayAudio(params)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -883,6 +883,60 @@ export function Request(config) {
|
|||
});
|
||||
}
|
||||
|
||||
else if (method === 'POST' && action === 'MultiPartyCall/name_TestMPC/Participant/10/Record/'){
|
||||
resolve({
|
||||
response: {},
|
||||
body: {
|
||||
"api_id": "036c80f3-3721-11ec-a678-0242ac110002",
|
||||
"message": "MPC: TestMPC participant record started",
|
||||
"recording_id": "24670db8-c723-4ba2-8521-f10ec41ddf8b",
|
||||
"recording_url": "https://media-qa.voice.plivodev.com/v1/Account/MAXXXXXXXXXXXX/Recording/XXXXX-XXXX-XXXX-XXXXX.mp3"
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
else if (method === 'DELETE' && action === 'MultiPartyCall/name_TestMPC/Participant/10/Record/'){
|
||||
resolve({
|
||||
response: {},
|
||||
body: {}
|
||||
});
|
||||
}
|
||||
|
||||
else if (method === 'POST' && action === 'MultiPartyCall/name_TestMPC/Participant/10/Record/Pause/'){
|
||||
resolve({
|
||||
response: {},
|
||||
body: {}
|
||||
});
|
||||
}
|
||||
|
||||
else if (method === 'POST' && action === 'MultiPartyCall/name_TestMPC/Participant/10/Record/Resume/'){
|
||||
resolve({
|
||||
response: {},
|
||||
body: {}
|
||||
});
|
||||
}
|
||||
|
||||
else if (method === 'POST' && action === 'MultiPartyCall/name_TestMPC/Member/10/Play/'){
|
||||
resolve({
|
||||
response: {},
|
||||
body: {
|
||||
"api_id": "c07db813-3721-11ec-8bcd-0242ac110008",
|
||||
"message": "play queued into MPC",
|
||||
"mpcMemberId": [
|
||||
"1003"
|
||||
],
|
||||
"mpcName": "TestMPC"
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
else if (method === 'DELETE' && action === 'MultiPartyCall/name_TestMPC/Member/10/Play/'){
|
||||
resolve({
|
||||
response: {},
|
||||
body: {}
|
||||
});
|
||||
}
|
||||
|
||||
// ============= Numbers ===================
|
||||
else if (method == 'GET' && action == 'Number/+919999999990/') {
|
||||
resolve({
|
||||
|
|
|
|||
|
|
@ -473,6 +473,10 @@ Response.prototype = {
|
|||
* @param {string} [attributes.recordingCallbackUrl]
|
||||
* @param {string} [attributes.statusCallbackUrl]
|
||||
* @param {string} [attributes.customerHoldMusicUrl]
|
||||
* @param {string} [attributes.startRecordingAudio]
|
||||
* @param {string} [attributes.stopRecordingAudio]
|
||||
* @param {string} [attributes.startRecordingAudioMethod]
|
||||
* @param {string} [attributes.stopRecordingAudioMethod]
|
||||
*/
|
||||
addMultiPartyCall: function (body, attributes){
|
||||
const VALID_ROLE_VALUES = ['agent', 'supervisor', 'customer']
|
||||
|
|
@ -664,6 +668,28 @@ Response.prototype = {
|
|||
if(attributes.customerHoldMusicUrl && !plivoUtils.validUrl('customerHoldMusicUrl', attributes.customerHoldMusicUrl, false)){
|
||||
throw new PlivoXMLError('Invalid attribute value ' + attributes.customerHoldMusicUrl + ' for customerHoldMusicUrl')
|
||||
}
|
||||
|
||||
if(attributes.startRecordingAudio && !plivoUtils.validUrl('startRecordingAudio', attributes.startRecordingAudio, false)){
|
||||
throw new PlivoXMLError('Invalid attribute value ' + attributes.startRecordingAudio + ' for startRecordingAudio')
|
||||
}
|
||||
|
||||
if(attributes.stopRecordingAudio && !plivoUtils.validUrl('stopRecordingAudio', attributes.stopRecordingAudio, false)){
|
||||
throw new PlivoXMLError('Invalid attribute value ' + attributes.stopRecordingAudio + ' for stopRecordingAudio')
|
||||
}
|
||||
|
||||
if(attributes.startRecordingAudioMethod && VALID_METHOD_VALUES.indexOf(attributes.startRecordingAudioMethod.toUpperCase())===-1){
|
||||
throw new PlivoXMLError('Invalid attribute value ' + attributes.startRecordingAudioMethod + ' for startRecordingAudioMethod')
|
||||
}
|
||||
else if (!attributes.startRecordingAudioMethod){
|
||||
attributes.startRecordingAudioMethod = 'GET'
|
||||
}
|
||||
|
||||
if(attributes.stopRecordingAudioMethod && VALID_METHOD_VALUES.indexOf(attributes.stopRecordingAudioMethod.toUpperCase())===-1){
|
||||
throw new PlivoXMLError('Invalid attribute value ' + attributes.stopRecordingAudioMethod + ' for stopRecordingAudioMethod')
|
||||
}
|
||||
else if (!attributes.stopRecordingAudioMethod){
|
||||
attributes.stopRecordingAudioMethod = 'GET'
|
||||
}
|
||||
return this.add(new MultiPartyCall(Response), body, attributes);
|
||||
},
|
||||
|
||||
|
|
@ -984,6 +1010,7 @@ function MultiPartyCall(Response){
|
|||
'statusCallbackEvents', 'statusCallbackUrl', 'statusCallbackMethod',
|
||||
'stayAlone', 'coachMode', 'mute', 'hold', 'startMpcOnEnter', 'endMpcOnExit',
|
||||
'enterSound', 'enterSoundMethod', 'exitSound', 'exitSoundMethod',
|
||||
'onExitActionUrl', 'onExitActionMethod', 'relayDTMFInputs'];
|
||||
'onExitActionUrl', 'onExitActionMethod', 'relayDTMFInputs',
|
||||
'startRecordingAudio', 'startRecordingAudioMethod', 'stopRecordingAudio', 'stopRecordingAudioMethod'];
|
||||
}
|
||||
util.inherits(MultiPartyCall, Response);
|
||||
|
|
|
|||
|
|
@ -92,4 +92,41 @@ describe('multiPartyCalls', function (){
|
|||
assert.equal(response.resourceUri, '/v1/Account/MAMDJMMTEZOWY0ZMQWM2/MultiPartyCall/uuid_7503f05f-2d6e-4ab3-b9e6-3b0d81ae9087/Participant/2132/')
|
||||
})
|
||||
});
|
||||
|
||||
it('should start MPC Participant Recording', function (){
|
||||
return client.multiPartyCalls.startParticipantRecording(10, {friendlyName: 'TestMPC'}).then(function (response){
|
||||
assert(response.message, "MPC: TestMPC participant record started")
|
||||
})
|
||||
});
|
||||
|
||||
it('should stop MPC Participant Recording', function (){
|
||||
return client.multiPartyCalls.stopParticipantRecording(10,{friendlyName: 'TestMPC'}).then(function (response){
|
||||
assert(response instanceof PlivoGenericResponse)
|
||||
})
|
||||
});
|
||||
|
||||
it('should pause MPC Participant Recording', function (){
|
||||
return client.multiPartyCalls.pauseParticipantRecording(10,{friendlyName: 'TestMPC'}).then(function (response){
|
||||
assert(response instanceof PlivoGenericResponse)
|
||||
})
|
||||
});
|
||||
|
||||
it('should resume MPC Participant Recording', function (){
|
||||
return client.multiPartyCalls.resumeParticipantRecording(10,{friendlyName: 'TestMPC'}).then(function (response){
|
||||
assert(response instanceof PlivoGenericResponse)
|
||||
})
|
||||
});
|
||||
|
||||
it('should start MPC Play Audio Member', function (){
|
||||
return client.multiPartyCalls.startPlayAudio(10,'https://s3.amazonaws.com/XXX/XXX.mp3',
|
||||
{friendlyName: 'TestMPC'}).then(function (response){
|
||||
assert(response.message, "play queued into MPC")
|
||||
})
|
||||
});
|
||||
|
||||
it('should stop MPC Play Audio Member', function (){
|
||||
return client.multiPartyCalls.stopPlayAudio(10,{friendlyName: 'TestMPC'}).then(function (response){
|
||||
assert(response instanceof PlivoGenericResponse)
|
||||
})
|
||||
});
|
||||
})
|
||||
|
|
|
|||
|
|
@ -35,7 +35,7 @@ describe('PlivoXML', function () {
|
|||
maxDuration: 1000,
|
||||
statusCallbackEvents: 'participant-speak-events, participant-digit-input-events, add-participant-api-events, participant-state-changes, mpc-state-changes'
|
||||
});
|
||||
assert.equal('<Response><MultiPartyCall role="Agent" maxDuration="1000" statusCallbackEvents="participant-speak-events, participant-digit-input-events, add-participant-api-events, participant-state-changes, mpc-state-changes" maxParticipants="10" waitMusicMethod="GET" agentHoldMusicMethod="GET" customerHoldMusicMethod="GET" record="false" recordFileFormat="mp3" recordingCallbackMethod="GET" statusCallbackMethod="POST" stayAlone="false" coachMode="true" mute="false" hold="false" startMpcOnEnter="true" endMpcOnExit="false" enterSound="beep:1" enterSoundMethod="GET" exitSound="beep:2" exitSoundMethod="GET" onExitActionMethod="POST" relayDTMFInputs="false">Nairobi</MultiPartyCall></Response>',mpcResponse.toXML());
|
||||
assert.equal('<Response><MultiPartyCall role="Agent" maxDuration="1000" statusCallbackEvents="participant-speak-events, participant-digit-input-events, add-participant-api-events, participant-state-changes, mpc-state-changes" maxParticipants="10" waitMusicMethod="GET" agentHoldMusicMethod="GET" customerHoldMusicMethod="GET" record="false" recordFileFormat="mp3" recordingCallbackMethod="GET" statusCallbackMethod="POST" stayAlone="false" coachMode="true" mute="false" hold="false" startMpcOnEnter="true" endMpcOnExit="false" enterSound="beep:1" enterSoundMethod="GET" exitSound="beep:2" exitSoundMethod="GET" onExitActionMethod="POST" relayDTMFInputs="false" startRecordingAudioMethod="GET" stopRecordingAudioMethod="GET">Nairobi</MultiPartyCall></Response>',mpcResponse.toXML());
|
||||
done();
|
||||
});
|
||||
});
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue