Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

Table of Contents

Пример доставки видеопотока с SIP на RTMP-сервер с добавлением звуковой дорожки к потоку

Данный пример показывает, как можно сделать вызов на SIP, получить от SIP стороны аудио и видео трафик, добавить к потоку звуковую дорожку и затем перенаправить полученный видеопоток на RTMP-сервер

Image RemovedImage Added

Код примера

Пример представляет собой простого REST-клиента, написанного на JavaScript и находится по следующему пути:

...

Здесь host - адрес WCS-сервера.

Работа с кодом примера

Для разбора кода возьмем версию файла sip-as-rtmp-2.js с хешем c306c1bbf49bfcbd8e24be927ae95f63b7dbaaba ecbadc3, которая находится здесь и доступна для
скачивания в соответствующей сборке 2.0.5212.28.2747.

1. Загрузка тестового RTMP-плеера на страницу для дальнейшего тестирования воспроизведения RTMP потока.

код

...

languagejs
themeRDark

...

.

...

2. Отправка REST / HTTP - запросов.

кодcode

Отправка происходит методом POST с ContentType application/json AJAX запросом с использованием фреймворка jquery.

Code Block
languagejs
themeRDark
function sendREST(url, data, successHandler, errorHandler) {
    console.info("url: " + url);
    console.info("data: " + data);
    $.ajax({
        url: url,
        beforeSend: function ( xhr ) {
            xhr.overrideMimeType( "text/plain;" );
        },
        type: 'POST',
        contentType: 'application/json',
        data: data,
        success: (successHandler === undefined) ? handleAjaxSuccess : successHandler,
        error: (errorHandler === undefined) ? handleAjaxError : errorHandler
    });
}

32. Создание исходящего звонка при помощи REST-запроса /call/startup

кодcode

Из текстовых форм собираются данные для установки соединения и звонка (RESTCall)

Code Block
languagejs
themeRDark
    var url = field("restUrl") + "/call/startup";
    callId = generateCallID();

    var connection = {};
    connection.sipLogin = field("sipLogin");
    connection.sipAuthenticationName = field("sipAuthenticationName");
    connection.sipPassword = field("sipPassword");
    connection.sipPort = field("sipPort");
    connection.sipDomain = field("sipDomain");
    connection.sipOutboundProxy = field("sipOutboundProxy");
    connection.appKey = field("appKey");
    connection.sipRegisterRequired = field("sipRegisterRequired");
    for (var key in connection) {
        setCookie(key, connection[key]);
    }

    var RESTCall = {};
    RESTCall.toStream = field("rtmpStream");
    RESTCall.hasAudio = field("hasAudio");
    RESTCall.hasVideo = field("hasVideo");
    RESTCall.callId = callId;
    RESTCall.sipLogin = field("sipLogin");
    RESTCall.sipAuthenticationName = field("sipAuthenticationName");
    RESTCall.sipPassword = field("sipPassword");
    RESTCall.sipPort = field("sipPort");
    RESTCall.sipDomain = field("sipDomain");
    RESTCall.sipOutboundProxy = field("sipOutboundProxy");
    RESTCall.appKey = field("appKey");
    RESTCall.sipRegisterRequired = field("sipRegisterRequired");

    for (var key in RESTCall) {
        setCookie(key, RESTCall[key]);
    }

    RESTCall.callee = field("callee");

    var data = JSON.stringify(RESTCall);

    sendREST(url, data);
    startCheckCallStatus();

43. Получение статуса звонка запросом /call/find.

кодcode

Code Block
languagejs
themeRDark
function getStatus() {
    var url = field("restUrl") + "/call/find";
    currentCallId = { callId: callId };
    $("#callTrace").text(callId + " >>> " + field("rtmpUrl"));
    var data = JSON.stringify(currentCallId);
    sendREST(url, data);
}

54. Отправка DTMF сигнала запросом /call/send_dtmf.

кодcode

Code Block
languagejs
themeRDark
function sendDTMF(value) {
    var url = field("restUrl") + "/call/send_dtmf";
    var data = {};
    data.callId = callId;
    data.dtmf = value;
    data.type = "RFC2833";
    data = JSON.stringify(data);
    sendREST(url, data);
}

65. Ретрансляция звонка на RTMP-сервер с добавлением звукового файла в поток запросом /push/startup

кодcode

Code Block
languagejs
themeRDark
function startRtmpStream() {
    if (!rtmpStreamStarted) {
        rtmpStreamStarted = true;
        var url = field("restUrl") + "/push/startup";
        var RESTObj = {};
        var options = {};
        if ($("#mute").is(':checked')) {
            options.action = "mute";
        } else if ($("#music").is(':checked')) {
            options.action = "sound_on";
            options.soundFile = "sample.wav";
        }
        RESTObj.streamName = field("rtmpStream");
        RESTObj.rtmpUrl = field("rtmpUrl");
        RESTObj.options = options;
        sendREST(url, JSON.stringify(RESTObj), startupRtmpSuccessHandler, startupRtmpErrorHandler);
        sendDataToPlayer();
        startCheckTransponderStatus();
    }
}

76. Получение статуса RTMP-потока запросом /push/find.

кодcode

Code Block
languagejs
themeRDark
function getTransponderStatus() {
    var url = field("restUrl") + "/push/find";
    var RESTObj = {};
    // By default transponder's stream name will contain prefix "rtmp_"
    RESTObj.streamName = "rtmp_" + field("rtmpStream");
    RESTObj.rtmpUrl = field("rtmpUrl");
    sendREST(url, JSON.stringify(RESTObj), transponderStatusSuccessHandler, transponderStatusErrorHandler);
}

87. Включение/отключение звука RTMP-потока.

Отключение звука /push/mute код code

Code Block
languagejs
themeRDark
function mute() {
    if (rtmpStreamStarted) {
        $("#mute").prop('disabled', true);
        var RESTObj = {};
        RESTObj.mediaSessionId = rtmpMediaSessionId;
        var url = field("restUrl") + "/push/mute";
        sendREST(url, JSON.stringify(RESTObj), muteSuccessHandler, muteErrorHandler);
    }
}

Включение звука /push/unmute код code

Code Block
languagejs
themeRDark
function unmute() {
    if (rtmpStreamStarted) {
        $("#mute").prop('disabled', true);
        var RESTObj = {};
        RESTObj.mediaSessionId = rtmpMediaSessionId;
        var url = field("restUrl") + "/push/unmute";
        sendREST(url, JSON.stringify(RESTObj), muteSuccessHandler, muteErrorHandler);
    }
}

98. Включение/отключение дополнительной звуковой дорожки RTMP-потока.

Включение звуковой дорожки из файла /push/sound_on код code

Code Block
languagejs
themeRDark
function soundOn() {
    if (rtmpStreamStarted) {
        $("#music").prop('disabled', true);
        var RESTObj = {};
        RESTObj.mediaSessionId = rtmpMediaSessionId;
        RESTObj.soundFile = "sample.wav";
        RESTObj.loop = false;
        var url = field("restUrl") + "/push/sound_on";
        sendREST(url, JSON.stringify(RESTObj), injectSoundSuccessHandler, injectSoundErrorHandler);
    }
}

Отключение звуковой дорожки /push/sound_off код code

Code Block
languagejs
themeRDark
function soundOff() {
    if (rtmpStreamStarted) {
        $("#music").prop('disabled', true);
        var RESTObj = {};
        RESTObj.mediaSessionId = rtmpMediaSessionId;
        var url = field("restUrl") + "/push/sound_off";
        sendREST(url, JSON.stringify(RESTObj), injectSoundSuccessHandler, injectSoundErrorHandler);
    }
}

109. Завершение звонка запросом /call/terminate.

кодcode

Code Block
languagejs
themeRDark
function hangup() {
    var url = field("restUrl") + "/call/terminate";
    var currentCallId = { callId: callId };
    var data = JSON.stringify(currentCallId);
    sendREST(url, data);
}

10. Отображение RTMP URL на странице для копирования в сторонний плеер

code

Code Block
languagejs
themeRDark
function sendDataToPlayer() {
    var host = field("rtmpUrl")
        .replace("localhost", window.location.hostname)
        .replace("127.0.0.1", window.location.hostname);

    var rtmpStreamPrefix = "rtmp_";
    var url = host + "/" + rtmpStreamPrefix + field("rtmpStream");
    $("#player").text(url);
}