Читайте веб-страницы и выделяйте контент с помощью Amazon Polly PlatoBlockchain Data Intelligence. Вертикальный поиск. Ай.

Читайте веб-страницы и выделяйте контент с помощью Amazon Polly

В этом посте мы покажем, как использовать Amazon Polly— ведущая облачная служба, которая преобразует текст в реалистичную речь — для чтения содержимого веб-страницы и выделения содержимого по мере его чтения. Добавление воспроизведения звука на веб-страницу улучшает доступность и удобство для посетителей страницы. Контент, дополненный звуком, более впечатляющий и запоминающийся, привлекает больше трафика на страницу и увеличивает покупательную способность посетителей. Это также улучшает бренд компании или организации, которая публикует страницу. Технология преобразования текста в речь делает эти бизнес-преимущества достижимыми. Мы ускоряем этот путь, демонстрируя, как достичь этой цели с помощью Amazon Polly.

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

Обзор решения

PollyReadsThePage (PRTP) — как мы называем это решение — позволяет издателю веб-страницы перетаскивать элемент управления звуком на свою веб-страницу. Когда посетитель выбирает Играть на элементе управления элемент управления считывает страницу и выделяет содержимое. PRTP использует общие возможности Amazon Polly для синтеза речи из текста. Он вызывает Amazon Polly для создания двух артефактов для каждой страницы:

  • Аудиоконтент в формате, воспроизводимом браузером: MP3
  • Файл речевых меток, который указывает для каждого предложения текста:
    • Время во время воспроизведения, когда читается предложение
    • Место на странице, где появляется предложение

Когда посетитель выбирает Играть, браузер воспроизводит файл MP3. По мере чтения аудио браузер проверяет время, находит в файле меток, какое предложение читать в это время, находит его на странице и выделяет.

PRTP позволяет посетителю читать разными голосами и языками. Для каждого голоса требуется своя пара файлов. PRTP использует нейронные голоса. Список поддерживаемых нейронных голосов и языков см. Нейронные голоса. Полный список стандартных и нейронных голосов в Amazon Polly см. Голоса в Амазонке Полли.

Мы рассматриваем два типа веб-страниц: статические и динамические страницы. В статический страница, содержимое содержится на странице и изменяется только при публикации новой версии страницы. Компания может обновлять страницу ежедневно или еженедельно в рамках процесса веб-сборки. Для этого типа страницы можно предварительно сгенерировать аудиофайлы во время сборки и разместить их на веб-сервере для воспроизведения. Как показано на следующем рисунке, сценарий PRTP Pre-Gen вызывает Amazon Polly для создания звука. Он принимает в качестве входных данных саму HTML-страницу и, при необходимости, файл конфигурации, который указывает, какой текст со страницы следует извлечь (Text Extract Config). Если конфигурация извлечения не указана, сценарий предварительной генерации делает разумный выбор текста для извлечения из тела страницы. Amazon Polly выводит файлы в Простой сервис хранения Amazon (Amazon S3) ведро; скрипт копирует их на ваш веб-сервер. Когда посетитель воспроизводит аудио, браузер загружает MP3 прямо с веб-сервера. Для основных моментов встраиваемая библиотека, PRTP.js, использует файл меток для выделения читаемого текста.

Содержание динамический страница изменяется в ответ на взаимодействие с посетителем, поэтому звук не может быть сгенерирован заранее, а должен быть синтезирован динамически. Как показано на следующем рисунке, когда посетитель воспроизводит аудио, страница использует PRTP.js для создания звука в Amazon Polly, и он выделяет синтезированный звук, используя тот же подход, что и для статических страниц. Для доступа к сервисам AWS из браузера посетителю требуется удостоверение AWS. Мы показываем, как использовать Амазон Когнито Identity Pool, чтобы предоставить посетителю достаточный доступ к Amazon Polly и корзине S3 для рендеринга звука.

Динамический контент

Для создания звуковых и речевых меток MP3 требуется, чтобы служба Polly дважды синтезировала одни и те же входные данные. Обратитесь к Страница цен на Amazon Polly понять последствия затрат. Предварительная генерация снижает затраты, поскольку синтез выполняется во время сборки, а не по запросу для каждого взаимодействия с посетителем.

Код, сопровождающий этот пост, доступен в виде репозитория с открытым исходным кодом на GitHub.

Чтобы изучить решение, мы выполняем следующие шаги:

  1. Настройте ресурсы, включая сервер предварительной сборки, корзину S3, веб-сервер и удостоверение Amazon Cognito.
  2. Запустите статическую предварительную сборку и протестируйте статические страницы.
  3. Тестируйте динамические страницы.

Предпосылки

Для запуска этого примера вам понадобится Аккаунт AWS с разрешением на использование Amazon Polly, Amazon S3, Amazon Cognito и (в демонстрационных целях) Облако AWS9.

Предоставление ресурсов

Мы разделяем AWS CloudFormation шаблон для создания в вашей учетной записи автономной демонстрационной среды, которая поможет вам следить за публикацией. Если вы предпочитаете настроить PRTP в своей среде, обратитесь к инструкциям в README.md.

Чтобы подготовить демонстрационную среду с помощью CloudFormation, сначала загрузите копию Шаблон CloudFormation. Затем выполните следующие шаги:

  1. В консоли AWS CloudFormation выберите Создать стек.
  2. Выберите С новыми ресурсами (стандарт).
  3. Выберите Загрузите файл шаблона.
  4. Выберите Выберите файл чтобы загрузить локальную копию скачанного шаблона. Имя файла prtp.yml.
  5. Выберите Следующая.
  6. Введите имя стека по вашему выбору. Позже вы вводите это снова в качестве замены для .
  7. Вы можете оставить значения по умолчанию в параметры .
  8. Выберите Следующая.
  9. Продолжить через оставшиеся разделы.
  10. Прочтите и установите флажки в Возможности .
  11. Выберите Создать стек.
  12. Когда стек заполнен, найдите значение для BucketName в выходах стека.

Мы рекомендуем вам проверить стек вместе с вашей командой безопасности, прежде чем использовать его в производственной среде.

Настройте веб-сервер и предварительный сервер в AWS Cloud9 IDE.

Затем на консоли AWS Cloud9 найдите среду PRTPDemoCloud9 созданный стеком CloudFormation. Выбирать Открыть IDE чтобы открыть среду AWS Cloud9. Откройте окно терминала и выполните следующие команды, которые клонируют код PRTP, настраивают предварительные зависимости и запускают веб-сервер для тестирования:

#Obtain PRTP code
cd /home/ec2-user/environment
git clone https://github.com/aws-samples/amazon-polly-reads-the-page.git

# Navigate to that code
cd amazon-polly-reads-the-page/setup

# Install Saxon and html5 Python lib. For pre-gen.
sh ./setup.sh <StackName>

# Run Python simple HTTP server
cd ..
./runwebserver.sh <IngressCIDR> 

Что касается , используйте имя, которое вы дали стеку CloudFormation. За , укажите диапазон IP-адресов, которым разрешен доступ к веб-серверу. Чтобы ограничить доступ к браузеру на вашем локальном компьютере, найдите свой IP-адрес, используя https://whatismyipaddress.com/ и добавить /32 чтобы указать диапазон. Например, если ваш IP 10.2.3.4, use 10.2.3.4/32. Сервер прослушивает порт 8080. Общедоступный IP-адрес, который прослушивает сервер, указан в выходных данных. Например:

Public IP is

3.92.33.223

Тестировать статические страницы

В браузере перейдите к PRTPStaticDefault.html. (Если вы используете демо, URL-адрес http://<cloud9host>:8080/web/PRTPStaticDefault.html, Где общедоступный IP-адрес, который вы обнаружили при настройке IDE.) Выберите Играть на панели управления звуком вверху. Слушайте аудио и смотрите основные моменты. Исследуйте управление, изменяя скорость, меняя голоса, останавливая, перематывая вперед и назад. На следующем снимке экрана показана страница; текст «Пропускает скрытый абзац» выделен, потому что он в данный момент читается.

Читайте веб-страницы и выделяйте контент с помощью Amazon Polly PlatoBlockchain Data Intelligence. Вертикальный поиск. Ай.

Попробуйте то же самое для PRTPStaticConfig.html и PRTPStaticCustom.html. Результаты аналогичны. Например, все трое читают альтернативный текст для фотографии кота («Случайное изображение кота»). Все три слова NE, NW, SE и SW читаются как полные слова («северо-восток», «северо-запад», «юго-восток», «юго-запад»), используя лексикон Amazon Polly.

Обратите внимание на основные различия в звуке:

  • PRTPStaticDefault.html читает весь текст в основной части страницы, включая заключительную часть внизу с «Ваши мысли одним словом», «Отправить запрос», «Последнее обновление 1 апреля 2020 г.» и «Вопросы для команды разработчиков». PRTPStaticConfig.html и PRTPStaticCustom.html не читайте их, потому что они явно исключают завершение из синтеза речи.
  • PRTPStaticCustom.html читает Бестселлеры QB стол отличается от других. Он читает только первые три строки и считывает номер строки для каждой строки. Он повторяет столбцы для каждой строки. PRTPStaticCustom.html использует пользовательское преобразование для настройки считывания таблицы. На других страницах используется табличный рендеринг по умолчанию.
  • PRTPStaticCustom.html читает «Том Брэди» громче, чем остальной текст. Он использует язык разметки синтеза речи (SSML). prosody тег, чтобы адаптировать чтение Тома Брэди. Другие страницы не адаптируются таким образом.
  • PRTPStaticCustom.html, благодаря пользовательскому преобразованию, читает основные тайлы в порядке СЗ, ЮЗ, СВ, ЮВ; то есть «Сегодняшние статьи», «Цитата дня», «Фото дня», «Анекдоты дня». Другие страницы читаются в том порядке, в котором плитки появляются в естественном порядке СЗ, СВ, ЮЗ, ЮВ в HTML: «Сегодняшние статьи», «Фото дня», «Цитата дня», «Шутки дня». День."

Давайте углубимся в то, как генерируется звук и как страница выделяет текст.

Статический предварительный генератор

Наш репозиторий GitHub включает предварительно сгенерированные аудиофайлы для PRPTStatic страниц, но если вы хотите сгенерировать их самостоятельно, из оболочки bash в среде AWS Cloud9 IDE выполните следующие команды:

# navigate to examples
cd /home/ec2-user/environment/amazon-polly-reads-the-page-blog/pregen/examples

# Set env var for my S3 bucket. Example, I called mine prtp-output
S3_BUCKET=prtp-output # Use output BucketName from CloudFormation

#Add lexicon for pronuniciation of NE NW SE NW
#Script invokes aws polly put-lexicon
./addlexicon.sh.

#Gen each variant
./gen_default.sh
./gen_config.sh
./gen_custom.sh

Теперь давайте посмотрим, как работают эти скрипты.

Случай по умолчанию

Начнем с gen_default.sh:

cd ..
python FixHTML.py ../web/PRTPStaticDefault.html  
   example/tmp_wff.html
./gen_ssml.sh example/tmp_wff.html generic.xslt example/tmp.ssml
./run_polly.sh example/tmp.ssml en-US Joanna 
   ../web/polly/PRTPStaticDefault compass
./run_polly.sh example/tmp.ssml en-US Matthew 
   ../web/polly/PRTPStaticDefault compass

Сценарий начинается с запуска программы Python FixHTML.py сделать исходный файл HTML PRTPStaticDefault.html хорошо сформированный. Он записывает правильно сформированную версию файла в example/tmp_wff.html. Этот шаг важен по двум причинам:

  • Большая часть исходного HTML-кода имеет неправильный формат. Этот шаг восстанавливает исходный HTML, чтобы он был правильно сформирован. Например, многие HTML-страницы не закрываются. P элементы. Этот шаг закрывает их.
  • Мы отслеживаем, где на странице HTML мы находим текст. Нам нужно отслеживать местоположения, используя ту же структуру объектной модели документа (DOM), которую использует браузер. Например, браузер автоматически добавляет TBODY к TABLE. Программа на Python следует тому же правильно построенному ремонту, что и браузер.

gen_ssml.sh принимает правильно сформированный HTML в качестве входных данных, применяет к нему преобразование таблицы стилей XML (XSLT) и выводит файл SSML. (SSML — это язык в Amazon Polly для управления преобразованием звука из текста.) В текущем примере входными данными являются example/tmp_wff.html. На выходе example/tmp.ssml. Задача преобразования — решить, какой текст следует извлечь из HTML и передать в Amazon Polly. generic.xslt является разумным преобразованием XSLT по умолчанию для большинства веб-страниц. В следующем примере фрагмента кода он исключает элемент управления звуком, заголовок HTML, а также такие элементы HTML, как script и form. Он также исключает элементы со скрытым атрибутом. Он включает элементы, которые обычно содержат текст, например P, H1качества SPAN. Для них он отображает как метку, включая полное выражение XPath элемента, так и значение элемента.

<!-- skip the header -->
<xsl:template match="html/head">
</xsl:template>

<!-- skip the audio itself -->
<xsl:template match="html/body/table[@id='prtp-audio']">
</xsl:template>

<!-- For the body, work through it by applying its templates. This is the default. -->
<xsl:template match="html/body">
<speak>
      <xsl:apply-templates />
</speak>
</xsl:template>

<!-- skip these -->
<xsl:template match="audio|option|script|form|input|*[@hidden='']">
</xsl:template>

<!-- include these -->
<xsl:template match="p|h1|h2|h3|h4|li|pre|span|a|th/text()|td/text()">
<xsl:for-each select=".">
<p>
      <mark>
          <xsl:attribute name="name">
          <xsl:value-of select="prtp:getMark(.)"/>
          </xsl:attribute>
      </mark>
      <xsl:value-of select="normalize-space(.)"/>
</p>
</xsl:for-each>
</xsl:template>

Ниже приведен фрагмент отображаемого SSML. Это подается в качестве входных данных для Amazon Polly. Обратите внимание, например, что текст «Пропускает скрытый абзац» должен быть прочитан в аудио, и мы связываем его с отметкой, которая говорит нам, что этот текст встречается в месте на странице, заданном выражением XPath. /html/body[1]/div[2]/ul[1]/li[1].

<speak>
<p><mark name="/html/body[1]/div[1]/h1[1]"/>PollyReadsThePage Normal Test Page</p>
<p><mark name="/html/body[1]/div[2]/p[1]"/>PollyReadsThePage is a test page for audio readout with highlights.</p>
<p><mark name="/html/body[1]/div[2]/p[2]"/>Here are some features:</p>
<p><mark name="/html/body[1]/div[2]/ul[1]/li[1]"/>Skips hidden paragraph</p>
<p><mark name="/html/body[1]/div[2]/ul[1]/li[2]"/>Speaks but does not highlight collapsed content</p>
…
</speak>

Для генерации звука в Amazon Polly мы вызываем скрипт run_polly.sh, Это управляет Интерфейс командной строки AWS (интерфейс командной строки AWS) команда aws polly start-speech-synthesis-task дважды: один раз для создания аудио MP3 и еще раз для создания файла меток. Поскольку генерация является асинхронной, сценарий выполняет опрос до тех пор, пока не найдет выходные данные в указанной корзине S3. Когда он находит выходные данные, он загружает их на сервер сборки и копирует файлы на web/polly папка. Ниже приведен список веб-папок:

  • PRTPStaticDefault.html
  • PRTPStaticConfig.html
  • PRTPStaticCustom.html
  • PRTP.js
  • polly/PRTPStaticDefault/Joanna.mp3, Joanna.marks, Matthew.mp3, Matthew.marks
  • polly/PRTPStaticConfig/Joanna.mp3, Joanna.marks, Matthew.mp3, Matthew.marks
  • polly/PRTPStaticCustom/Joanna.mp3, Joanna.marks, Matthew.mp3, Matthew.marks

Каждая страница имеет свой собственный набор голосовых файлов MP3 и меток. Эти файлы являются предварительно сгенерированными файлами. Странице не нужно вызывать Amazon Polly во время выполнения; файлы являются частью веб-сборки.

Случай, управляемый конфигурацией

Далее рассмотрим gen_config.sh:

cd ..
python FixHTML.py ../web/PRTPStaticConfig.html 
  example/tmp_wff.html
python ModGenericXSLT.py example/transform_config.json 
  example/tmp.xslt
./gen_ssml.sh example/tmp_wff.html example/tmp.xslt 
  example/tmp.ssml
./run_polly.sh example/tmp.ssml en-US Joanna 
  ../web/polly/PRTPStaticConfig compass
./run_polly.sh example/tmp.ssml en-US Matthew 
  ../web/polly/PRTPStaticConfig compass

Сценарий аналогичен сценарию по умолчанию, но выделенные жирным шрифтом строки указывают на главное отличие. Наш подход основан на конфигурации. Мы адаптируем содержимое, которое будет извлечено со страницы, указав, что извлекать с помощью конфигурации, а не кода. В частности, мы используем файл JSON transform_config.json, который указывает, что включаемое содержимое — это элементы с идентификаторами title, main, maintableкачества qbtable. Элемент с идентификатором wrapup следует исключить. См. следующий код:

{
 "inclusions": [ 
 	{"id" : "title"} , 
 	{"id": "main"}, 
 	{"id": "maintable"}, 
 	{"id": "qbtable" }
 ],
 "exclusions": [
 	{"id": "wrapup"}
 ]
}

Запускаем программу Python ModGenericXSLT.py модифицировать generic.xslt, используемый в случае по умолчанию, чтобы использовать включения и исключения, которые мы указываем в transform_config.json. Программа записывает результаты во временный файл (example/tmp.xslt), который переходит к gen_ssml.sh как его XSLT-преобразование.

Это вариант с низким кодом. Веб-издателю не нужно знать, как писать XSLT. Но им необходимо понимать структуру HTML-страницы и идентификаторы, используемые в ее основных организующих элементах.

Случай настройки

Наконец, рассмотрим gen_custom.sh:

cd ..
python FixHTML.py ../web/PRTPStaticCustom.html 
   example/tmp_wff.html
./gen_ssml.sh example/tmp_wff.html example/custom.xslt  
   example/tmp.ssml
./run_polly.sh example/tmp.ssml en-US Joanna 
   ../web/polly/PRTPStaticCustom compass
./run_polly.sh example/tmp.ssml en-US Matthew 
   ../web/polly/PRTPStaticCustom compass

Этот сценарий почти идентичен сценарию по умолчанию, за исключением того, что он использует собственный XSLT.example/custom.xslt— а не общий XSLT. Ниже приведен фрагмент XSLT:

<!-- Use NW, SW, NE, SE order for main tiles! -->
<xsl:template match="*[@id='maintable']">
    <mark>
        <xsl:attribute name="name">
        <xsl:value-of select="stats:getMark(.)"/>
        </xsl:attribute>
    </mark>
    <xsl:variable name="tiles" select="./tbody"/>
    <xsl:variable name="tiles-nw" select="$tiles/tr[1]/td[1]"/>
    <xsl:variable name="tiles-ne" select="$tiles/tr[1]/td[2]"/>
    <xsl:variable name="tiles-sw" select="$tiles/tr[2]/td[1]"/>
    <xsl:variable name="tiles-se" select="$tiles/tr[2]/td[2]"/>
    <xsl:variable name="tiles-seq" select="($tiles-nw,  $tiles-sw, $tiles-ne, $tiles-se)"/>
    <xsl:for-each select="$tiles-seq">
         <xsl:apply-templates />  
    </xsl:for-each>
</xsl:template>   

<!-- Say Tom Brady load! -->
<xsl:template match="span[@style = 'color:blue']" >
<p>
      <mark>
          <xsl:attribute name="name">
          <xsl:value-of select="prtp:getMark(.)"/>
          </xsl:attribute>
      </mark>
      <prosody volume="x-loud">Tom Brady</prosody>
</p>
</xsl:template>

Если вы хотите подробно изучить код, обратитесь к сценариям и программам в репозитории GitHub.

Настройка браузера и основные моменты

Статические страницы включают элемент управления звуком HTML5, который использует в качестве источника звука файл MP3, созданный Amazon Polly и находящийся на веб-сервере:

<audio id="audio" controls>
  <source src="polly/PRTPStaticDefault/en/Joanna.mp3" type="audio/mpeg">
</audio>

Во время загрузки страница также загружает файл меток, созданный Amazon Polly. Это происходит в PRTP.js файл, который включает HTML-страница. Ниже приведен фрагмент файла меток для PRTPStaticDefault:

{“time”:11747,“type”:“sentence”,“start”:289,“end”:356,“value”:“PollyReadsThePage is a test page for audio readout with highlights.“}
{“time”:15784,“type”:“ssml”,“start”:363,“end”:403,“value”:“/html/body[1]/div[2]/p[2]“}
{“time”:16427,“type”:“sentence”,“start”:403,“end”:426,“value”:“Here are some features:“}
{“time”:17677,“type”:“ssml”,“start”:433,“end”:480,“value”:“/html/body[1]/div[2]/ul[1]/li[1]“}
{“time”:18344,“type”:“sentence”,“start”:480,“end”:502,“value”:“Skips hidden paragraph”}
{“time”:19894,“type”:“ssml”,“start”:509,“end”:556,“value”:“/html/body[1]/div[2]/ul[1]/li[2]“}
{“time”:20537,“type”:“sentence”,“start”:556,“end”:603,“value”:“Speaks but does not highlight collapsed content”}

Во время воспроизведения аудио есть обработчик событий таймера аудио в PRTP.js который проверяет текущее время аудио, находит текст для выделения, находит его местоположение на странице и выделяет его. Текст, который нужно выделить, является записью типа sentence в файле меток. Расположение — это выражение XPath в атрибуте имени записи типа SSML, которая предшествует предложению. Например, если время 18400 18334, согласно файлу меток, предложение, которое нужно выделить, — «Пропускает скрытый абзац», которое начинается с 17667 XNUMX. Местоположение — это запись SSML на момент времени XNUMX XNUMX: /html/body[1]/div[2]/ul[1]/li[1].

Тестировать динамические страницы

Страницы PRTPDynamic.html демонстрирует динамическое считывание аудио с использованием стандартных, управляемых конфигурацией и пользовательских подходов к извлечению аудио.

Случай по умолчанию

В браузере перейдите к PRTPDynamic.html. Страница имеет один параметр запроса, dynOption, который принимает значения default, configкачества custom. По умолчанию default, так что вы можете опустить его в этом случае. На странице есть два раздела с динамическим контентом:

  • Последние статьи - Часто меняется в течение дня
  • Греческие философы Поиск по дате - Позволяет посетителю искать греческих философов по дате и показывает результаты в таблице

Читайте веб-страницы и выделяйте контент с помощью Amazon Polly PlatoBlockchain Data Intelligence. Вертикальный поиск. Ай.

Создайте контент в Греческий философ раздел, введя диапазон дат от -800 до 0, как показано в примере. Тогда выбирай Найдите.

Теперь воспроизведите аудио, выбрав Играть в управлении звуком.

За кулисами страница запускает следующий код для рендеринга и воспроизведения звука:

   buildSSMLFromDefault();
   chooseRenderAudio();
   setVoice();

Сначала он вызывает функцию buildSSMLFromDefault in PRTP.js для извлечения большей части текста из тела HTML-страницы. Эта функция просматривает дерево DOM в поисках текста в общих элементах, таких как p, h1, pre, spanкачества td. Он игнорирует текст в элементах, которые обычно не содержат текста для чтения вслух, например audio, optionкачества script. Он создает разметку SSML для ввода в Amazon Polly. Ниже приведен фрагмент, показывающий извлечение первой строки из philosopher таблица:

<speak>
...
  <p><mark name="/HTML[1]/BODY[1]/DIV[3]/DIV[1]/DIV[1]/TABLE[1]/TBODY[1]/TR[2]/TD[1]"/>Thales</p>
  <p><mark name="/HTML[1]/BODY[1]/DIV[3]/DIV[1]/DIV[1]/TABLE[1]/TBODY[1]/TR[2]/TD[2]"/>-624 to -546</p>
  <p><mark name="/HTML[1]/BODY[1]/DIV[3]/DIV[1]/DIV[1]/TABLE[1]/TBODY[1]/TR[2]/TD[3]"/>Miletus</p>
  <p><mark name="/HTML[1]/BODY[1]/DIV[3]/DIV[1]/DIV[1]/TABLE[1]/TBODY[1]/TR[2]/TD[4]"/>presocratic</p>
...
</speak>

Ассоциация chooseRenderAudio функции в PRTP.js начинается с инициализации AWS SDK для Amazon Cognito, Amazon S3 и Amazon Polly. Эта инициализация происходит только один раз. Если chooseRenderAudio вызывается снова, потому что содержимое страницы изменилось, инициализация пропускается. См. следующий код:

AWS.config.region = env.REGION
AWS.config.credentials = new AWS.CognitoIdentityCredentials({
            IdentityPoolId: env.IDP});
audioTracker.sdk.connection = {
   polly: new AWS.Polly({apiVersion: '2016-06-10'}),
   s3: new AWS.S3()
};

Он генерирует аудио в формате MP3 из Amazon Polly. Генерация является синхронной для небольших входных данных SSML и асинхронной (с выводом, отправляемым в корзину S3) для больших входных данных SSML (более 6,000 символов). В синхронном случае мы просим Amazon Polly предоставить файл MP3, используя заранее заданный URL-адрес. Когда синтезированный выход готов, мы устанавливаем src атрибут элемента управления аудио к этому URL-адресу и загрузите элемент управления. Затем мы запрашиваем файл меток и загружаем его так же, как и в статическом случае. См. следующий код:

// create signed URL
const signer = new AWS.Polly.Presigner(pollyAudioInput, audioTracker.sdk.connection.polly);

// call Polly to get MP3 into signed URL
signer.getSynthesizeSpeechUrl(pollyAudioInput, function(error, url) {
  // Audio control uses signed URL
  audioTracker.audioControl.src =
    audioTracker.sdk.audio[audioTracker.voice];
  audioTracker.audioControl.load();

  // call Polly to get marks
  audioTracker.sdk.connection.polly.synthesizeSpeech(
    pollyMarksInput, function(markError, markData) {
    const marksStr = new
      TextDecoder().decode(markData.AudioStream);
    // load marks into page the same as with static
    doLoadMarks(marksStr);
  });
});

Случай, управляемый конфигурацией

В браузере перейдите к PRTPDynamic.html?dynOption=config. Воспроизведите аудио. Воспроизведение звука похоже на случай по умолчанию, но есть небольшие отличия. В частности, некоторый контент пропускается.

За кулисами, при использовании config параметр, страница извлекает содержимое иначе, чем в случае по умолчанию. По умолчанию страница использует buildSSMLFromDefault. В случае с конфигурацией страница указывает разделы, которые она хочет включить и исключить:

const ssml = buildSSMLFromConfig({
	 "inclusions": [ 
	 	{"id": "title"}, 
	 	{"id": "main"}, 
	 	{"id": "maintable"}, 
	 	{"id": "phil-result"},
	 	{"id": "qbtable"}, 
	 ],
	 "exclusions": [
	 	{"id": "wrapup"}
	 ]
	});

Ассоциация buildSSMLFromConfig функция, определенная в PRTP.js, просматривает дерево DOM в каждом из разделов, идентификатор которых указан в разделе inclusions. Он извлекает содержимое из каждого и объединяет их вместе в указанном порядке для формирования документа SSML. Он исключает разделы, указанные в exclusions. Он извлекает контент из каждого раздела одинаково buildSSMLFromDefault извлекает содержимое из тела страницы.

Случай настройки

В браузере перейдите к PRTPDynamic.html?dynOption=custom. Воспроизведите аудио. Есть три заметных отличия. Давайте отметим это и рассмотрим пользовательский код, который работает за кулисами:

  • Он читает основные плитки в порядке СЗ, ЮЗ, СВ, ЮВ. Пользовательский код получает каждый из этих блоков ячеек из maintable и добавляет их в SSML в порядке СЗ, ЮЗ, СВ, ЮВ:
const nw = getElementByXpath("//*[@id='maintable']//tr[1]/td[1]");
const sw = getElementByXpath("//*[@id='maintable']//tr[2]/td[1]");
const ne = getElementByXpath("//*[@id='maintable']//tr[1]/td[2]");
const se = getElementByXpath("//*[@id='maintable']//tr[2]/td[2]");
[nw, sw, ne, se].forEach(dir => buildSSMLSection(dir, []));

  • «Том Брэди» произносится громко. Пользовательский код помещает текст «Том Брэди» в SSML. prosody тег:
if (cellText == "Tom Brady") {
   addSSMLMark(getXpathOfNode( node.childNodes[tdi]));
   startSSMLParagraph();
   startSSMLTag("prosody", {"volume": "x-loud"});
   addSSMLText(cellText);
   endSSMLTag();
   endSSMLParagraph();
}

  • Он читает только первые три строки таблицы квотербеков. Он считывает заголовки столбцов для каждой строки. Проверьте код в репозитории GitHub, чтобы узнать, как это реализовано.

Убирать

Чтобы избежать будущих расходов, удалите стек CloudFormation.

Заключение

В этом посте мы продемонстрировали техническое решение важной бизнес-задачи: как использовать Amazon Polly для чтения содержимого веб-страницы и выделения содержимого по мере его чтения. Мы показали это, используя как статические, так и динамические страницы. Для извлечения контента со страницы мы использовали обход DOM и XSLT. Для облегчения выделения мы использовали функцию речевых меток в Amazon Polly.

Узнайте больше об Amazon Polly, посетив его служебная страница.

Не стесняйтесь задавать вопросы в комментариях.


Об авторах

Читайте веб-страницы и выделяйте контент с помощью Amazon Polly PlatoBlockchain Data Intelligence. Вертикальный поиск. Ай.Майк Хэви является архитектором решений для AWS с более чем 25-летним опытом создания корпоративных приложений. Майк является автором двух книг и многочисленных статей. Посетите его Амазонку авторская страница читать дальше.

Читайте веб-страницы и выделяйте контент с помощью Amazon Polly PlatoBlockchain Data Intelligence. Вертикальный поиск. Ай.Винит Качхаваха является архитектором решений в AWS с опытом работы в области машинного обучения. Он отвечает за помощь клиентам в разработке масштабируемых, безопасных и экономичных рабочих нагрузок на AWS.

Отметка времени:

Больше от Машинное обучение AWS