Если в каком-нибудь коммюнити спрашивают про аудио- или видеозвонки из браузера, как правило, получают ответ: «Попробуйте WebRTC». WebRTC, действительно, подходящая для этого технология и имеет ряд преимуществ над другими способами передачи аудио и видео в браузере.
Адепты WebRTC уже давно похоронили Flash, несмотря на то, что WebRTC местами имеет сырые реализации и доступна далеко не повсеместно. В настоящей статье представлены TOP 3 технологий звонков из браузера с описанием их преимуществ и недостатков.
Как известно, сам браузер «звонить» до последнего времени не умел. Не умел обрабатывать звук с микрофона, посылать, принимать и воспроизводить. Относительно недавно в некоторых браузерах появилась возможность захвата с микрофона и вебкамеры и дальнейшей отправки этих данных по защищенному SRTP протоколу, а так же воспроизведение потока с использованием адаптивного jitter buffer. Все эти новые возможности и есть не что иное, как WebRTC. Здесь стоит заметить, что браузерные звонки существовали за много лет до появления WebRTC, поэтому начнём с наиболее древних.
TOP3 – Java
Временем появления браузерных звонков можно считать момент, когда Java апплеты стали поддерживать захват аудио с микрофона. Java Runtime Environment (JRE), как правило, уже установлена в системе, будь-то Linux или Windows. JRE так же присутствует в виде плагина в большинстве известных браузеров. Например, если заглянуть во вкладку chrome://plugins браузера Google Chrome, можно найти там NPAPI Java плагин. Этот плагин и будет средой для выполнения Java апплета. Второй, более продвинутый способ запуска, это JNLP (Java Network Launch Protocol), который позволяет, к примеру, кустомизировать окно «Загрузка апплета…».
В итоге Java код выполняется десктопом или браузерным плагином, захватывает аудио с микрофона и отправляет его на сервер по стандартному RTP протоколу (для Java можно с легкостью отыскать несколько готовых RTP реализаций). С безопасностью здесь так же все в порядке. Понятно, что апплет должен быть подписан, и при запуске пользователя спросят, желает ли он запустить подписанный апплет от данного производителя, который может получить доступ к тем или иным функциям.
Плюсы решения на Java:
- простое;
- нет лишних звеньев, возможность прямого взаимодействия с сервером по RTP;
- широкая распространенность и доступность JRE для конечного пользователя.
Кажется, что все идеально? К сожалению, в Java есть проблемы с DSP для VoIP. А это весь «must have» набор:
- AEC (Acoustic Echo Cancellation);
- AGC (Automatic Gain Control);
- Adaptive Jitter Buffer;
- Noise suppression.
Теперь представим звонок с Java апплета без гарнитуры (наушников с микрофоном). Если провести этот эксперимент ночью, поставив колонки на полную громкость, можно напугать соседей до заикания. Всё из-за эхоподавления. Его нет. Отсутствие AGC заставит ваших пользователей крутить уровень громкости (нормальный AGC должен делать это за пользователя, чтобы не было слишком тихо или слишком громко). А отсутствие Adaptive Jitter Buffer выльется либо в большую задержку либо в «choppy audio» – прерывистый неразборчивый звук. В результате качество коммуникации будет далеким от оптимального.
Все недостающие алгоритмы можно теоретически реализовать на Java, но есть пара проблем. Во-первых, реализовать универсальные и производительные алгоритмы (например AEC) достаточно сложно: такая реализация потребует высоких трудозатрат и расходов на R&D. Во-вторых, реализация таких алгоритмов на Java может работать в несколько раз медленнее, чем на C/C++, что может повлечь серьезные проблемы с производительностью и перерасход ресурсов клиентского CPU.
Производители Java апплетов с функцией звонков реализуют собственные DSP процессоры или используют уже существующие решения на C/C++. Как правило, они подкладывают к апплету DLL библиотеки, которые берут на себя обработку вышеописанных DSP алгоритмов. В результате Java апплет имеет стандартные VoIP функции для обеспечения качественного звонка со всеми «must have» VoIP алгоритмами.
В конечном итоге остается два минуса Java:
- кроссплатформенность — придется снабжать апплеты DLL библиотеками под Win и SO библиотеками под Linux;
- сложность реализации этих DSP библиотек.
Довести DSP до отличного качества или купить соответствующие разработки может позволить себе не каждый вендор. То же касается поддержки различных аудио- и видеокодеков.
В итоге, Java можно назвать незаслуженно покинутой разработчиками платформой для браузерных звонков.
Незаслуженно покинута она по двум причинам:
- недостаток встроенных возможностей по работе с DSP;
- более распространенные для Web конкурирующие платформы, которые лишены такого недостатка.
О них далее.
TOP 2 – Flash
До некоторого времени Flash был технологией для красивых интерактивных баннеров.
В 2002 году появилась в релизе версия Flash Communication Server MX 1.0 — прародитель сегодняшнего Adobe Media Server. Flash Player 6, являясь тогда продуктом компании Macromedia, умел взаимодействовать с FCS MX 1.0 и обмениваться с сервером аудиопотоками. Это еще раз указывает на то, что WebRTC припозднился на 10 лет, а также то, что рынок начинает закрывать свои потребности за 10 лет до появления вменяемой технологии браузерного интерактива.
В это время Flash Player 6 уже умел захватывать аудио и жать его в NellyMoser и видео — в Sorenson Spark. Java в это время была слабо представлена в веб и Flash Player 6 в связке с сервером претендовали на мировое господство в области web-стриминга. Позже появились Red5, Wowza, но это немного другая история.
В качестве транспорта для аудио и видео в Flash Player 6 использовался протокол RTMP, который сегодня имеет открытую спецификацию, опубликованную Adobe.
Flash Player 6 в связке с сервером стал платформой для браузерных звонков, обладающей следующими функциями:
- NellyMoser, Sorenson spark;
- RTMP.
До полноценного браузерного VoIP тогда было еще очень далеко. AEC (Acoustic Echo Cancellation) в тот период, наверное, даже не было в планах. Но платформа делала свое дело и передавала звук и видео от одного плеера к другому через сервер.
Все, кто работают с VoIP, рано или поздно сталкиваются с задержкой. Когда разработчик впервые тестирует написанное им VoIP приложение, он не обращает внимания на задержку: звук есть, картинка есть — и хорошо. Первыми задержку замечают пользователи и пишут репорты типа: «I say «one» then Bob says «two» and it seems it takes about 5 seconds. Why?» Потом уже два разработчика начинают тестировать звук и не понимают, куда пропали эти 5 секунд, ведь у них сервер Xeon на 100500 ядер и он не может тормозить.
Задержка была в связке Flash Player 6 + Flash Communication Server MX 1.0, а также осталась в следующих версиях сервера, включая последнюю Adobe Media Server, с ней безуспешно боролись на Wowza и Red5. Причина, конечно, проста и известна каждому VoIP разработчику: RTMP протокол работает поверх TCP, а потому не приспособлен для полноценного VoIP. Сохранить пакеты любой ценой – это не тот случай, когда дело касается передачи звука либо видео. Но это главная задача TCP протокола: сохраняем пакеты и получаем задержку. Все просто.
Отсутствие полноценного UDP транспорта сделало невозможным развитие интерактивных сервисов. Например, если участник вебинара хочет пообщаться face-to-face с ведущим, у него не всегда получится это сделать нормально. Все в значительной степени зависит от качества сети и потерь. В результате на базе RTMP развивались, в основном, video on demand сервисы, или live video, или вебинары с одним ведущим, где задержка не так важна.
Кстати, здесь вопрос к Macromedia: почему они не сделали audio и video стриминг по UDP. Это бы значительно упростило жизнь всем разработчикам и конечным пользователям. Очевидно, что VoIP функция браузера была на переферии и над ней никто особо не задумывался, а для интерактива с данными (sharedobjects, callbacks итд) TCP подходит оптимально.
Ситуацию с UDP в Flash Player сдвинула компания Adobe, когда в версии плеера 10 ввели поддержку нового протокола RTMFP и эхоподавление. В 11 версии Flash Player добавили поддержку кодеков G.711 и H.264. В AS3 API так же имеются упоминания про Adaptive Jitter Buffer для G.711 и Speex.
VoIP возможности Flash Player 11:
- Nelly Moser, Speex, G.711, Sorenson Spark, H.264;
- RTMP, RTMFP;
- AEC;
- Adaptive Jitter Buffer;
- AES шифрование.
Благодаря этим нововведениям, Flash Player имеет практически все необходимое, чтобы стать VoIP платформой №1 для браузера: шифрование AES защищает трафик между браузером и сервером от посторонних; AEC и Jitter Buffer обеспечивают качество воспроизведения звука; новые кодеки совместимы с традиционным VoIP, а RTMFP протокол работает по UDP. Не хватает AGC (Automatic Gain Control). Его отсутствие не смертельно, но неприятно для тех, кто понимает пользу этой функции для VoIP и не понимает, почему её до сих пор нет. Помогает перенос AGC-фильтра на сторону сервера.
Еще одна маленькая неприятность от Adobe — невозможность во Flash Player нормально проиграть H.264 поток, закодированный для передачи по RTP. В багтрекере Adobe cуществует «by design» баг, который накладывает ограничение 1 NALU per video frame. Это ограничение отрубает все H.264 кодеры, которые дают поток, совместимый с RTP. В результате приходится применять транскодинг, что в свою очередь вызывает избыточное потребление ресурсов CPU, которого в принципе хотелось бы избежать.
Flash RTMFP основан на UDP и довольно прилично передает звук. Но и здесь не обошлось без сюрпризов. В доках Adobe AS3 сказано, что RTMFP для аудио и видео поддерживает три режима: надежная доставка (reliable), частично-надежная доставка (partially reliable), ненадежная доставка (unreliable). В этих же доках есть только два флага для audioReliable и videoReliable: true, false. False описывается как режим частичной доставки (partially reliable). В итоге, получается, что ненадежная доставка (unreliable) пропала, а для передачи звука она наиболее важна.
Частичная доставка – это TCP подобные ретрансмиты, которые происходят очень ограниченное время, но и этого хватает, чтобы испортить звук на нестабильной сети. Такие ретрансмиты вызывают джиттер, который портит поток. Jitter buffer на принимающей стороне в данном случае не помогает, т.к. идет очень большой разброс. Решением является переход к ненадежной доставке (unreliable) звука. В Flash Player API нет возможностей её включить, и приходится добавлять её на уровне протокола на серверной стороне.
Например, в WebRTC — Flash RTMFP SIP Gateway Flashphoner Web Call Server реализован хак на уровне протокола, который позволяет полностью исключить ретрансмиты в RTMFP и обеспечить unreliable доставку. Это в разы повышает устойчивость потока к потерям и лагам сети. Можно получить разборчивый Speex поток до 12% потерь в сети. Тот же поток заметно рвется в случае частичной доставки(partially reliable) причем рвется на тестах с Adobe Flash Media Gateway, несмотря на то что эта часть Adobe Media Server должна по задумке являться эталонной реализацией RTMFP протокола.
Плюсы Flash:
- самый широкий охват браузеров;
- привычная технология для разработчиков — Flex/AS3;
- качественная VoIP передача аудио и видео.
Минусы Flash:
- требует промежуточного сервера (не поддерживает открытые UDP протоколы, такие как RTP/SRTP);
- относительно медленное улучшение VoIP части разработчиком (Adobe): отсутствие AGC, H.264 1 NALU per frame problem.
Кстати, что мешает разработчикам Flash Player внедрить WebRTC стек?
TOP 1 – WebRTC
И наконец, любимец публики, зомбирующая разработчиков, кошмарящая телекомов и активно обсуждаемая технология WebRTC. Рынок живет ожиданиями, а в ожиданиях сегодня доминирует WebRTC.
На текущий момент WebRTC присутствует в трех распространенных браузерах в состоянии production:
- Google Chrome;
- Mozilla Firefox;
- Mozilla Firefox mobile.
А также в двух браузерах в состоянии beta:
- Google Chrome Beta Mobile;
- Яндекс Браузер.
Яндекс Браузер не проверяли, но по информации в сети, он не всегда корректно работает с WebRTC, поэтому мы поставили его в beta в нашем списке.
Даже в Chrome браузере WebRTC продолжает оставаться недоработанной, хотя уже прошло немало времени после релиза. Простые вещи работают, но когда дело доходит до смены состояния сессии по SDP (аналог re-INVITE в SIP) или при других нетривиальных действиях, появляются разные сюрпризы, которые сильно огорчают.
Однако это не мешает WebRTC завоевывать все новые умы и определять вектор развития VoIP и вообще интерактивных технологий в Web. И это не удивительно по двум причинам:
- WebRTC поддерживается гигантами индустрии;
- WebRTC имеет действительно удачную и продуманную архитектуру, избавленную от ошибок и недостатков, выявленных в браузерных плагинах, которые существовали до неё.
На технологической начинке WebRTC хотелось бы остановиться отдельно, это:
SRTP, DTLS, ICE, STUN, AEC, AGC, Adaptive Jitter Buffer, Opus, VP8
Выглядит так, как будто в браузер встроили софтфон. Не хватает только поддержки SIP.
Действительно, набор используемых в WebRTC технологий больше похож на VoIP SDK. SRTP и DTLS обеспечивает защиту трафика между WebRTC узлами. ICE и STUN помогают преодолеть NAT, выставив с обеих сторон кандидатов для созвона в виде простых пар host:port. AEC, AGC и Jitter Buffer работают для того чтобы сделать аудио и видео качественным – без лагов и задержек. Кодеки Opus и VP8 хорошо подходят для глобального Интернета, где битрейт до конечного пользователя может легко падать до очень низких значений вопреки обещаниям провайдеров про каналы в 100Mbps.
Несколько омрачает картину отсутствие поддержки WebRTC в других браузерах, таких как IE, Safari, Opera и т.д. К недостаткам еще можно отнести несовместимость с традиционным VoIP оборудованием. Например, производители SIP/VoIP продуктов, коих великое множество, были бы очень признательны поддержке обычных SIP/RTP протоколов и кодеков для совместимости с миллионами устройств.
Здесь стоит упомянуть, что WebRTC изначально задумана как peer-to-peer между браузерами и ориентирована на шифрованный SRTP трафик. Скорее всего, именно поэтому VoIP вендорам, которые обмениваются стандартными RTP потоками, придётся внедрять у себя WebRTC совместимый транспорт и кодеки.
Хотя и здесь не все так плохо. Существуют шлюзы для обеспечения такого рода совместимости. Например WebRTC SIP Gateway Flashphoner Web Call Server 3 является шлюзом, который может соединить WebRTC клиента и стандартное SIP/RTP устройство будь то VoIP свитч или GSM шлюз, работающий по SIP. Таким образом, данная проблема вполне решаема путем ввода промежуточного ПО.
Преимущества и недостатки WebRTC достаточно прозрачны:
Плюсы WebRTC:
- полноценное VoIP в браузере
Минусы WebRTC:
- недостаточно поддерживающих браузеров
- отсутствие RFC (Cпецификации находятся в draft-ах и меняются, хотя нужно признать, что по сравнению с тем, что было год назад, сейчас все более-менее стабильно).
- отсутствие совместимости с традиционным VoIP (by design).
Ожидания и ресурсы, стоящие за WebRTC, с лихвой перекрывают текущие минусы, поэтому смело отдаем ей законное первое место TOP1 в списке браузерных технологий для VoIP.
Если же вспомнить, что остальные описанные здесь браузерные технологии Java и Flash – это плагины (хоть и предустановленные в большинстве браузеров), то выходит, что WebRTC – это единственная чисто-браузерная технология, которой в этом отношении нет аналогов.
Итак, мы закончили разбор трех технологий для web звонков, обобщим все описанное выше в виде следующих таблиц:
VoIP фильтры
Сетевые протоколы и спецификации
Аудио кодеки
Видео кодеки
Поддерживаемые браузеры
Некоторые пояснения:
- Все возможности Java клиента отмечены символом \\*. Это означает, что все вышеописанное может быть теоретически реализовано на Java. Вопрос в том сколько времени это займет, как хорошо это будет работать и сколько будет весить исполняемый файл со всеми библиотеками.
- С символами «плюс», «минус» и «вопрос» все должно быть понятно.
- В последний столбец таблицы было решено добавить для сравнения один из продвинутых VoIP софтфонов «традиционной» VoIP телефонии — Bria.
Ну вот и пришло время заняться подсчетом.
Некоторые функции, конечно, могут быть даже близко не равны по весу, но если считать в попугаях получается следующая картина:
Первое место в этой гонке VoIP технологий и коммуникационных протоколов занимает VoIP софтфон — 54% (21 попугай из 39). На втором месте WebRTC — 44% (17 попугаев из 39) и Flash, который идет за WebRTC с 41% (16 попугаев из 39).
В окончании, хотелось бы поставить вопрос: если мы строим облако для web-звонков с выходом на SIP/VoIP/PSTN, на чем мы будем это облако строить, какие материалы использовать?
Отвечая на этот вопрос, придется затронуть еще пару моментов. Первый из них связан с мобильными устройствами, второй — с проходимостью через брандмауэры.
Не секрет, что сейчас важна поддержка Android, iOS SDK и кроссплатформенность. С мобильными устройствами все более или менее понятно. Есть несколько вариантов:
- Adobe Air – тот же Flash с поддержкой тех же RTMP/RTMFP протоколов. Серьезный недостаток – нет эхоподавления. Преимущество – кроссплатформенность. Разворачиваем один и тот же код на Android и IOS.
- Браузер с поддержкой WebRTC. Недостаток – не очень удобно. Нативное мобильное приложение будет лучше в look and feel терминах.
- Портировать WebRTC код под IOS и Android. Недостаток – не кроссплатформенно и нетривиально.
- Использовать стандартный VoIP SDK с поддержкой SIP/RTP и портировать на IOS и Android. Недостаток – не кроссплатформенно, несовместимо с WebRTC. Преимущества – совместимо с традиционным VoIP оборудованием.
Теперь про брандмауэры(firewalls). Как звук пройдет через брандмауэр, если UDP на нем отключен? Ответ: для этого потребуется переключение на TCP транспорт. Подойдет например Flash RTMP.
А если весь трафик организации идет через proxy, и админ закрыл весь не HTTP трафик? Тогда придется использовать HTTP туннелированные, например RTMPT, что, кстати, не лучшим образом скажется на задержке.
В итоге получаем супероблако для VoIP звонков такого вида: для передачи аудио и видео используем WebRTC, RTMFP, RTMP, RTMPT, Java Applet. Для интеграции со стандартным VoIP используем SIP, RTP. Для мобильных устройств: Adobe Air, WebRTC, SIP/RTP клиентов.
Перечисленные технологии покроют большинство браузеров и мобильных устройств, хотя схема определенно избыточна.
Что из нее убрать, чтобы облегчить – решать вам.
Материал подготовлен при участии специалистов компании Flashphoner