dual streams (#467)

* dual streams

* dual streams

* dual streams

* dual streams

* use sdp transform
This commit is contained in:
Hoan Luu Huu
2023-09-21 18:57:30 +07:00
committed by GitHub
parent 76cf4e527f
commit 991fff3386
4 changed files with 57 additions and 12 deletions

View File

@@ -10,6 +10,7 @@ const HttpRequestor = require('../../utils/http-requestor');
const WsRequestor = require('../../utils/ws-requestor'); const WsRequestor = require('../../utils/ws-requestor');
const RootSpan = require('../../utils/call-tracer'); const RootSpan = require('../../utils/call-tracer');
const dbUtils = require('../../utils/db-utils'); const dbUtils = require('../../utils/db-utils');
const { mergeSdpMedia, extractSdpMedia } = require('../../utils/sdp-utils');
router.post('/', async(req, res) => { router.post('/', async(req, res) => {
const {logger} = req.app.locals; const {logger} = req.app.locals;
@@ -127,16 +128,35 @@ router.post('/', async(req, res) => {
/* launch outdial */ /* launch outdial */
let sdp, sipLogger; let sdp, sipLogger;
let dualEp;
let localSdp = ep.local.sdp;
if (req.body.dual_streams) {
dualEp = await ms.createEndpoint();
localSdp = mergeSdpMedia(localSdp, dualEp.local.sdp);
ep.on('destroy', () => {
dualEp.destroy();
});
}
const connectStream = async(remoteSdp) => { const connectStream = async(remoteSdp) => {
if (remoteSdp !== sdp) { if (remoteSdp !== sdp) {
ep.modify(sdp = remoteSdp); sdp = remoteSdp;
if (req.body.dual_streams) {
const [sdpLegA, sdpLebB] = extractSdpMedia(remoteSdp);
await Promise.all([ep.modify(sdpLegA), dualEp.modify(sdpLebB)]);
await ep.bridge(dualEp);
} else {
ep.modify(sdp);
}
return true; return true;
} }
return false; return false;
}; };
Object.assign(opts, { Object.assign(opts, {
proxy: `sip:${sbcAddress}`, proxy: `sip:${sbcAddress}`,
localSdp: ep.local.sdp localSdp
}); });
if (target.auth) opts.auth = target.auth; if (target.auth) opts.auth = target.auth;

View File

@@ -1,7 +1,32 @@
const sdpTransform = require('sdp-transform');
const isOnhold = (sdp) => { const isOnhold = (sdp) => {
return sdp && (sdp.includes('a=sendonly') || sdp.includes('a=inactive')); return sdp && (sdp.includes('a=sendonly') || sdp.includes('a=inactive'));
}; };
module.exports = { const mergeSdpMedia = (sdp1, sdp2) => {
isOnhold const parsedSdp1 = sdpTransform.parse(sdp1);
const parsedSdp2 = sdpTransform.parse(sdp2);
parsedSdp1.media.push(...parsedSdp2.media);
return sdpTransform.write(parsedSdp1);
};
const extractSdpMedia = (sdp) => {
const parsedSdp1 = sdpTransform.parse(sdp);
if (parsedSdp1.media.length > 1) {
parsedSdp1.media = [parsedSdp1.media[0]];
const parsedSdp2 = sdpTransform.parse(sdp);
parsedSdp2.media = [parsedSdp2.media[1]];
return [sdpTransform.write(parsedSdp1), sdpTransform.write(parsedSdp2)];
} else {
return [sdp, sdp];
}
};
module.exports = {
isOnhold,
mergeSdpMedia,
extractSdpMedia
}; };

14
package-lock.json generated
View File

@@ -17,7 +17,7 @@
"@jambonz/speech-utils": "^0.0.21", "@jambonz/speech-utils": "^0.0.21",
"@jambonz/stats-collector": "^0.1.9", "@jambonz/stats-collector": "^0.1.9",
"@jambonz/time-series": "^0.2.8", "@jambonz/time-series": "^0.2.8",
"@jambonz/verb-specifications": "^0.0.34", "@jambonz/verb-specifications": "^0.0.35",
"@opentelemetry/api": "^1.4.0", "@opentelemetry/api": "^1.4.0",
"@opentelemetry/exporter-jaeger": "^1.9.0", "@opentelemetry/exporter-jaeger": "^1.9.0",
"@opentelemetry/exporter-trace-otlp-http": "^0.35.0", "@opentelemetry/exporter-trace-otlp-http": "^0.35.0",
@@ -3019,9 +3019,9 @@
} }
}, },
"node_modules/@jambonz/verb-specifications": { "node_modules/@jambonz/verb-specifications": {
"version": "0.0.34", "version": "0.0.35",
"resolved": "https://registry.npmjs.org/@jambonz/verb-specifications/-/verb-specifications-0.0.34.tgz", "resolved": "https://registry.npmjs.org/@jambonz/verb-specifications/-/verb-specifications-0.0.35.tgz",
"integrity": "sha512-6/oplhOMpxz6qbIdz0K3Y2+KXtnb/DLziYmnGUK8NALWD7rhDvp2RdTsuEjOOkOhwLyRJUhuIAM17GcpAq/lCw==", "integrity": "sha512-MTdK4zGxE6+lO4Ir0q/q3TjKPOvWIewH6woS2NmDSMqVOdBKmO5lDDDlwutEr689CnVQbSpwiob1Uv42IK12EA==",
"dependencies": { "dependencies": {
"debug": "^4.3.4", "debug": "^4.3.4",
"pino": "^8.8.0" "pino": "^8.8.0"
@@ -12985,9 +12985,9 @@
} }
}, },
"@jambonz/verb-specifications": { "@jambonz/verb-specifications": {
"version": "0.0.34", "version": "0.0.35",
"resolved": "https://registry.npmjs.org/@jambonz/verb-specifications/-/verb-specifications-0.0.34.tgz", "resolved": "https://registry.npmjs.org/@jambonz/verb-specifications/-/verb-specifications-0.0.35.tgz",
"integrity": "sha512-6/oplhOMpxz6qbIdz0K3Y2+KXtnb/DLziYmnGUK8NALWD7rhDvp2RdTsuEjOOkOhwLyRJUhuIAM17GcpAq/lCw==", "integrity": "sha512-MTdK4zGxE6+lO4Ir0q/q3TjKPOvWIewH6woS2NmDSMqVOdBKmO5lDDDlwutEr689CnVQbSpwiob1Uv42IK12EA==",
"requires": { "requires": {
"debug": "^4.3.4", "debug": "^4.3.4",
"pino": "^8.8.0" "pino": "^8.8.0"

View File

@@ -33,7 +33,7 @@
"@jambonz/speech-utils": "^0.0.21", "@jambonz/speech-utils": "^0.0.21",
"@jambonz/stats-collector": "^0.1.9", "@jambonz/stats-collector": "^0.1.9",
"@jambonz/time-series": "^0.2.8", "@jambonz/time-series": "^0.2.8",
"@jambonz/verb-specifications": "^0.0.34", "@jambonz/verb-specifications": "^0.0.35",
"@opentelemetry/api": "^1.4.0", "@opentelemetry/api": "^1.4.0",
"@opentelemetry/exporter-jaeger": "^1.9.0", "@opentelemetry/exporter-jaeger": "^1.9.0",
"@opentelemetry/exporter-trace-otlp-http": "^0.35.0", "@opentelemetry/exporter-trace-otlp-http": "^0.35.0",