流媒体学习之路(mediasoup)——信令传输(3)
文章目录
一、Node.js部分
mediasoup——c++部分的信令交互主要通过Socket管道来进行的。Node.js部分与c++部分通过本机网络进行通话,实现交互。
前面两篇提到,Node.js部分worker建立后需要建立channel来进行通信,我们再来回顾一下channel.js部分通信的代码。下面是Worker的构造函数:
constructor({
logLevel, logTags, rtcMinPort, rtcMaxPort, dtlsCertificateFile, dtlsPrivateKeyFile, appData }) {
super();
// Closed flag.
this._closed = false;
// Routers set.
this._routers = new Set();
// Observer instance.
this._observer = new EnhancedEventEmitter_1.EnhancedEventEmitter();
logger.debug('constructor()');
let spawnBin = workerBin;
let spawnArgs = [];
if (process.env.MEDIASOUP_USE_VALGRIND === 'true') {
spawnBin = process.env.MEDIASOUP_VALGRIND_BIN || 'valgrind';
if (process.env.MEDIASOUP_VALGRIND_OPTIONS)
spawnArgs = spawnArgs.concat(process.env.MEDIASOUP_VALGRIND_OPTIONS.split(/\s+/));
spawnArgs.push(workerBin);
}
if (typeof logLevel === 'string' && logLevel)
spawnArgs.push(`--logLevel=${
logLevel}`);
for (const logTag of (Array.isArray(logTags) ? logTags : [])) {
if (typeof logTag === 'string' && logTag)
spawnArgs.push(`--logTag=${
logTag}`);
}
if (typeof rtcMinPort === 'number' && !Number.isNaN(rtcMinPort))
spawnArgs.push(`--rtcMinPort=${
rtcMinPort}`);
if (typeof rtcMaxPort === 'number' && !Number.isNaN(rtcMaxPort))
spawnArgs.push(`--rtcMaxPort=${
rtcMaxPort}`);
if (typeof dtlsCertificateFile === 'string' && dtlsCertificateFile)
spawnArgs.push(`--dtlsCertificateFile=${
dtlsCertificateFile}`);
if (typeof dtlsPrivateKeyFile === 'string' && dtlsPrivateKeyFile)
spawnArgs.push(`--dtlsPrivateKeyFile=${
dtlsPrivateKeyFile}`);
logger.debug('spawning worker process: %s %s', spawnBin, spawnArgs.join(' '));
this._child = child_process_1.spawn(
// command
spawnBin,
// args
spawnArgs,
// options
{
env: {
MEDIASOUP_VERSION: '3.6.13'
},
detached: false,
// fd 0 (stdin) : Just ignore it.
// fd 1 (stdout) : Pipe it for 3rd libraries that log their own stuff.
// fd 2 (stderr) : Same as stdout.
// fd 3 (channel) : Producer Channel fd.
// fd 4 (channel) : Consumer Channel fd.
// fd 5 (channel) : Producer PayloadChannel fd.
// fd 6 (channel) : Consumer PayloadChannel fd.
stdio: ['ignore', 'pipe', 'pipe', 'pipe', 'pipe', 'pipe', 'pipe'],
windowsHide: true
});
this._pid = this._child.pid;
this._channel = new Channel_1.Channel({
producerSocket: this._child.stdio[3],
consumerSocket: this._child.stdio[4],
pid: this._pid
});
this._payloadChannel = new PayloadChannel_1.PayloadChannel({
// NOTE: TypeScript does not like more than 5 fds.
// @ts-ignore
producerSocket: this._child.stdio[5],
// @ts-ignore
consumerSocket: this._child.stdio[6]
});
this._appData = appData;
let spawnDone = false;
// Listen for 'running' notification.
this._channel.once(String(this._pid), (event) => {
if (!spawnDone && event === 'running') {
spawnDone = true;
logger.debug('worker process running [pid:%s]', this._pid);
this.emit('@success');
}
});
this._child.on('exit', (code, signal) => {
this._child = undefined;
this.close();
if (!spawnDone) {
spawnDone = true;
if (code === 42) {
logger.error('worker process failed due to wrong settings [pid:%s]', this._pid);
this.emit('@failure', new TypeError('wrong settings'));
}
else {
logger.error('worker process failed unexpectedly [pid:%s, code:%s, signal:%s]', this._pid, code, signal);
this.emit('@failure', new Error(`[pid:${
this._pid}, code:${
code}, signal:${
signal

本文详细剖析了mediasoup项目中的信令传输过程,包括Node.js与C++部分的交互方式,重点介绍了如何通过Socket管道实现信令的传递与处理。
最低0.47元/天 解锁文章
2026

被折叠的 条评论
为什么被折叠?



