Создание интерактивной голосовой почты для спортивных фанатов с помощью Twilio, MongoDB, Angular и Node.js (Часть первая)

Автор: | 28.07.2026

Летом прошлого года мы заметили действительно крутой интерактивный рекламный опыт на основе телефона, созданный для Nike и баскетбольной звезды Леброна Джеймса. В коротком рекламном ролике известные личности, такие как Спайк Ли, Уоррен Баффет и Dr. Dre, оставляют голосовые сообщения для MVP финала НБА, поздравляя его с победой в чемпионате. Если вы еще не видели, посмотрите видео ниже и краткий обзор ролика как «Креативный выбор дня» в Advertising Age:

Реклама заканчивается живым номером телефона, по которому фанаты могли позвонить и оставить сообщение для Леброна. Нам показалось, что это отличный способ позволить фанатам взаимодействовать с знаменитостью или брендом – и с Twilio это на самом деле довольно просто сделать.

В этом руководстве мы покажем, как можно создать интерактивный почтовый ящик для голосовых сообщений (и текстовых сообщений) в поддержку маркетинговой кампании вокруг бренда или знаменитости. Фанаты могут звонить или отправлять текстовые сообщения на настроенный вами номер, чтобы лично пообщаться со своими любимыми спортивными звездами или брендами. Такой способ взаимодействия может быть более значимым, чем комментарий на YouTube или лайк на Facebook – пользователи воспринимают текстовые сообщения и телефонные звонки как средства личного общения. С помощью инструмента, такого как голосовая почта или отправка сообщений, вы можете предоставить своей аудитории возможность для личного взаимодействия с объектом вашей маркетинговой кампании.

С началом бейсбольного сезона (заметили каламбур?) я подумал, что отличной демонстрацией этой техники будет настройка номера для голосовых и текстовых сообщений для моей любимой спортивной звезды: трехкратного чемпиона по отбиванию, шестикратного участника Матча всех звезд и обладателя награды MVP Американской лиги 2009 года Джо Мауэра из команды «Миннесота Твинс». Это включает в себя общедоступную веб-страницу, на которой отображаются все отправленные для Джо сообщения, а также административный интерфейс для модерации сообщений. Ведь это интернет, и мы хотим убедиться, что все отображаемые сообщения хотя бы соответствуют рейтингу PG-13.

Вы можете посмотреть работающий сайт (адаптивная верстка также работает в мобильных браузерах) по адресу http://www.leavejoeamessage.com. Полный исходный код приложения доступен на GitHub.

Технологии и инструменты, использованные в этом приложении:

— Twilio Voice и SMS (зарегистрируйтесь сейчас, если еще не сделали этого!)

— Node.js с следующими модулями:

— twilio (официальная клиентская библиотека для Node.js)

— express (популярный веб-фреймворк для Node.js)

— mongoose (ODM-обертка для MongoDB)

— Less CSS (препроцессор CSS)

— browserify (загрузка модулей в стиле Node.js для браузера)

— AngularJS (MVC на стороне клиента)

— Buzz (HTML5-аудио)

— Heroku (PaaS для Node.js)

— MongoHQ (MongoDB как услуга)

— Rev.com для высококачественной транскрипции голосовых сообщений

Мы разделим это руководство на три части. В этой части мы рассмотрим, как использовать Twilio для приема входящих текстовых сообщений и записи голосовых сообщений. В следующей части мы посмотрим, как мы создали административный и общедоступный интерфейсы для отображения текстовых сообщений и воспроизведения записей звонков Twilio. В третьей и заключительной части мы рассмотрим, как можно использовать API транскрипции Rev.com для добавления практически 100% точных транскрипций, выполненных людьми, к оставленным для Джо сообщениям.

Давайте начнем с понимания базовой архитектуры этого приложения.

Это приложение имеет два основных взаимодействия, через которые пользователь может оставить сообщение – одно происходит через голосовой звонок, а другое – через текстовое сообщение. Когда пользователь отправляет текстовое сообщение Джо, оно сохраняется в базе данных на модерацию для последующего отображения на сайте. Когда пользователь звонит, мы записываем его голосовое сообщение. По завершении записи Twilio отправляет нашему приложению на Node.js URL записанного сообщения, и мы сохраняем его в нашей базе данных MongoDB.

Для текстовых и голосовых сообщений у нас есть административный интерфейс для их модерации и общедоступный интерфейс для их отображения, но об этом мы расскажем в следующих частях этого руководства.

Вот базовая схема того, как выглядит это взаимодействие для текстового сообщения:

Для голосового сообщения это немного сложнее, но не намного:

Twilio передает события, такие как входящий звонок или текстовое сообщение, вашему веб-приложению через HTTP-запросы. Twilio ожидает, что HTTP-ответы на эти запросы будут содержать XML, написанный на диалекте, который мы называем TwiML. Этот тип HTTP-колбэка называется вебхуком – если вы не уверены, как Twilio использует вебхуки в сочетании с вашим программируемым номером телефона, или вы новичок в использовании Twilio с Node.js, возможно, стоит ознакомиться с этим вводным руководством. Давайте начнем с рассмотрения нашего кода вебхука в Node.js, написанного с использованием кастомизированной версии популярного веб-фреймворка Express.

В административном интерфейсе Twilio мы можем настроить URL для каждого из наших номеров Twilio, на который будет отправлен HTTP POST-запрос при входящем звонке или текстовом сообщении. Для обработки этих HTTP-запросов мы будем использовать Express, вероятно, самый популярный веб-фреймворк в сообществе Node.js. Чтобы узнать больше о том, как работает Express, ознакомьтесь с их официальной документацией и руководством.

В нашем приложении есть три маршрута, которые обрабатывают входящие запросы от Twilio – они настроены следующим образом:

Вы заметите, что у всех этих маршрутов есть второй аргумент после определения маршрута – это специальное промежуточное ПО Connect, предоставляемое в составе модуля Twilio для Node.js. Это промежуточное ПО помогает Express понимать, как рендерить объекты TwiML (такие, как те, которые мы будем создавать в наших обработчиках), а также проверять, что входящие HTTP-запросы действительно пришли от Twilio. Эта проверка запросов очень важна, особенно если запрос от Twilio создает или обновляет данные, или если ответ содержит конфиденциальную информацию. Для получения дополнительной информации о безопасности вебхуков ознакомьтесь с нашей документацией по безопасности.

Конфигурация промежуточного ПО находится в том же файле, что и все обработчики запросов:

Вы заметите, что проверка запросов включена только в том случае, если системная переменная окружения NODE_ENV установлена в значение «production», что является общепринятой практикой для многих приложений на Node.js, чтобы отличать разработку от продакшена.

Для обработки входящих текстовых сообщений нам нужен всего один маршрут:

В этом маршруте мы создаем новый объект под названием Message и сохраняем его в нашем хранилище данных MongoDB. Этот объект Message является объектом модели mongoose – mongoose это обертка для MongoDB, которая упрощает реализацию постоянных бизнес-объектов, предоставляя валидацию данных, методы классов/экземпляров и запросы.

Наше соединение с MongoDB, необходимое для инициализации mongoose, настроено в основном файле приложения JavaScript, app.js в корневом каталоге нашего проекта. Любой URL подключения к MongoDB может быть передан в метод «connect». Как для разработки, так и для продакшена я с удовольствием использовал размещенные экземпляры MongoDB, предоставляемые MongoHQ. Они предоставляют мгновенные базы данных MongoDB, которые легко интегрировать в ваше приложение на Node.js, а также удобные графические инструменты, которые можно использовать в браузере для просмотра и ручного редактирования данных. Вы можете прочитать больше о том, как настроить базу данных MongoHQ здесь.

Возвращаясь к нашему коду вебхука, мы видим, что свойства объекта Message считываются из POST-данных, отправленных в наше приложение Twilio. Мы сохраняем, среди прочего, номер телефона пользователя, уникальный идентификатор сообщения (SID) и текст сообщения:

Затем мы используем API модели, предоставляемый mongoose, для сохранения Message. После того как Message сохранен, мы создаем объект ответа TwiML и рендерим его как XML обратно в Twilio с помощью объекта ответа Express. Эти инструкции TwiML указывают Twilio отправить ответное текстовое сообщение пользователю, подтверждая получение его сообщения:

Для записи голосового сообщения мы создадим два маршрута – давайте начнем с рассмотрения первого маршрута, который будет использоваться Twilio при входящем звонке на наш номер:

Для начала записи голосового сообщения мы начинаем с краткого текстового сообщения, синтезированного из текста (TTS), которое предлагает пользователю оставить сообщение. Опять же, это достигается с помощью помощника по созданию TwiML из модуля Twilio для Node.js, объекта TwimlResponse. Это не что иное, как объект, позволяющий легко создавать XML-строку в JavaScript.

Объект TwimlResponse предоставляет цепочечный интерфейс, позволяющий добавлять несколько узлов TwiML в ответ с помощью одного оператора. После настройки TTS-сообщения в узле мы сразу используем тег , чтобы указать Twilio начать запись от пользователя. Мы ограничиваем запись двумя минутами и сообщаем Twilio, что после завершения записи он должен отправить POST-запрос на /recording с URL записи.

Twilio обработает начало записи и сохранение записанного аудиофайла (даже сделав его доступным в различных форматах, таких как mp3 и wav). После завершения записи Twilio продолжит выполнение звонка, отправив HTTP-запрос на URL, указанный в атрибуте action тега . В этом приложении этот URL соответствует нашему маршруту /recording:

HTTP-запрос, который Twilio отправляет нам на этом этапе, будет содержать POST-параметры с информацией о записи, в частности, ее публичный URL (доступ к которому осуществляется с помощью кода request.param(‘RecordingUrl’) в приведенном выше фрагменте). Как только у нас будет этот URL, мы готовы сохранить наше голосовое сообщение в базе данных:

Это приложение настроено на использование двух основных облачных сервисов для хостинга и хранения данных. Мы будем использовать Heroku в качестве PaaS для запуска приложения на Node.js и MongoHQ для хостинга и управления нашей базой данных MongoDB.

Чтобы создать базу данных MongoHQ, вам сначала нужно зарегистрироваться на MongoHQ. После регистрации вы можете создать базу данных нужного размера – есть бесплатная песочница, которая отлично подойдет для разработки и тестирования. Если вам нужна помощь в настройке, у них есть короткое и полезное видео-руководство здесь.

После создания базы данных вам понадобится строка подключения, чтобы предоставить ее нашему приложению на Node.js в качестве системной переменной окружения. Строка подключения находится в разделе «Admin» вашей новой базы данных:

Вам нужно заменить действительное имя пользователя и пароль базы данных в этой строке подключения на и . Чтобы получить имя пользователя и пароль базы данных, вам, вероятно, просто нужно создать нового пользователя. Также в разделе Admin есть вкладка «Users». Используйте предоставленную форму, чтобы добавить нового пользователя, но не забудьте записать имя пользователя и пароль!

Теперь у вас должна быть вся необходимая информация для строки подключения, которую мы установим как переменную окружения при развертывании нашего приложения на Heroku. Она должна выглядеть примерно так, исходя из значений на последнем скриншоте:

Чтобы развернуть это приложение на Heroku, шаги будут очень похожи на их руководство по развертыванию для Node.js. Репозиторий GitHub для leavejoeamessage.com включает Procfile, который запустит процесс веб-приложения на Node.js после развертывания вашего приложения.

Однако для работы нашего приложения нам нужно добавить конфиденциальную строку подключения к базе данных и учетные данные аккаунта Twilio в качестве системных переменных окружения. Используя утилиту командной строки Heroku Toolbelt, это довольно просто. Откройте окно терминала и выполните следующие команды:

heroku config:add TWILIO_ACCOUNT_SID=ваш twilio account sid

heroku config:add TWILIO_AUTH_TOKEN=ваш twilio auth token

heroku config:add MONGOHQ_URL=ваша строка подключения к MongoDB

Теперь наше приложение настроено для приема входящих звонков и текстовых сообщений от Twilio!

Теперь, когда наша серверная часть настроена, все, что нам нужно сделать, это подключить номер Twilio, на который фанаты будут звонить или отправлять сообщения. Перейдите к своим доступным телефонным номерам и выберите (или купите) номер, на который фанаты будут звонить. Затем щелкните по этому номеру и настройте оба колбэка для голоса и сообщений, чтобы они указывали на домен, где работает наше приложение:

Обратите внимание, что в нашем приложении проверка запросов Twilio включена. Нам нужно убедиться, что имя хоста и протокол, указанные здесь в наших вебхуках, совпадают со значениями, настроенными в нашем коде.

Теперь, когда вы нажмете «Сохранить», все входящие звонки и текстовые сообщения на этот номер должны сохраняться в нашей базе данных! По мере поступления звонков и сообщений вы можете просматривать их в административном интерфейсе MongoHQ для коллекции «messages»:

В этом руководстве мы рассмотрели код, необходимый для создания автоответчика на базе Twilio, с текстовыми и голосовыми сообщениями, сохраняемыми в базе данных MongoDB. В следующей части этого цикла мы посмотрим, как работать с сохраненными данными сообщений, чтобы создать адаптивный интерфейс на AngularJS, который позволит нам модерировать сообщения, оставленные пользователями, а также отображать и воспроизводить аудиозаписи. После этого мы покажем, как можно использовать API транскрипции Rev.com для добавления 100% точных транскрипций, выполненных людьми, к голосовым сообщениям.

Если у вас есть вопросы по поводу решений на поле и вы хотите оспорить судейство, не стесняйтесь обращаться ко мне в Twitter или в комментариях!