Lisez des pages Web et mettez en surbrillance le contenu à l'aide d'Amazon Polly PlatoBlockchain Data Intelligence. Recherche verticale. Aï.

Lire des pages Web et mettre en évidence du contenu à l'aide d'Amazon Polly

Dans cet article, nous montrons comment utiliser Amazon Polly— un service cloud de premier plan qui convertit le texte en paroles réalistes — pour lire le contenu d'une page Web et mettre en évidence le contenu au fur et à mesure qu'il est lu. L'ajout d'une lecture audio à une page Web améliore l'accessibilité et l'expérience des visiteurs de la page. Le contenu audio amélioré est plus percutant et mémorable, attire plus de trafic vers la page et exploite le pouvoir d'achat des visiteurs. Cela améliore également la marque de l'entreprise ou de l'organisation qui publie la page. La technologie de synthèse vocale permet d'atteindre ces avantages commerciaux. Nous accélérons ce voyage en démontrant comment atteindre cet objectif en utilisant Amazon Polly.

Cette capacité améliore l'accessibilité pour les visiteurs handicapés et pourrait être adoptée dans le cadre de la stratégie d'accessibilité de votre organisation. Tout aussi important, cela améliore l'expérience de la page pour les visiteurs sans handicap. Les deux groupes ont un pouvoir d'achat important et dépensent plus librement sur les pages qui utilisent l'amélioration audio pour attirer leur attention.

Présentation de la solution

PollyReadsThePage (PRTP) - comme nous nous référons à la solution - permet à un éditeur de page Web de déposer un contrôle audio sur sa page Web. Lorsque le visiteur choisit Jouez sur le champ, le champ lit la page et met en surbrillance le contenu. PRTP utilise la capacité générale d'Amazon Polly pour synthétiser la parole à partir du texte. Il invoque Amazon Polly pour générer deux artefacts pour chaque page :

  • Le contenu audio dans un format lisible par le navigateur : MP3
  • Un fichier de marques vocales qui indique pour chaque phrase de texte :
    • Le temps pendant la lecture que la phrase est lue
    • L'emplacement sur la page où la phrase apparaît

Lorsque le visiteur choisit Jouez, le navigateur lit le fichier MP3. Au fur et à mesure que l'audio est lu, le navigateur vérifie l'heure, trouve dans le fichier de marques la phrase à lire à ce moment-là, la localise sur la page et la met en surbrillance.

PRTP permet au visiteur de lire dans différentes voix et langues. Chaque voix nécessite sa propre paire de fichiers. PRTP utilise des voix neurales. Pour une liste des voix neurales et des langues prises en charge, voir Voix neuronales. Pour une liste complète des voix standard et neurales dans Amazon Polly, consultez Voix sur Amazon Polly.

Nous considérons deux types de pages Web : les pages statiques et les pages dynamiques. Dans un statique page, le contenu est contenu dans la page et ne change que lorsqu'une nouvelle version de la page est publiée. L'entreprise peut mettre à jour la page quotidiennement ou hebdomadairement dans le cadre de son processus de création Web. Pour ce type de page, il est possible de pré-générer les fichiers audio au moment de la construction et de les placer sur le serveur Web pour la lecture. Comme le montre la figure suivante, le script PRTP Pre-Gen appelle Amazon Polly pour générer l'audio. Il prend en entrée la page HTML elle-même et, éventuellement, un fichier de configuration qui spécifie le texte de la page à extraire (Text Extract Config). Si la configuration d'extraction est omise, le script pré-génération fait un choix judicieux de texte à extraire du corps de la page. Amazon Polly génère les fichiers dans un Service de stockage simple Amazon (Amazon S3) compartiment ; le script les copie sur votre serveur Web. Lorsque le visiteur lit l'audio, le navigateur télécharge le MP3 directement à partir du serveur Web. Pour les faits saillants, une bibliothèque en libre-service, PRTP.js, utilise le fichier de repères pour mettre en surbrillance le texte en cours de lecture.

Le contenu d'un Dynamic la page change en réponse à l'interaction du visiteur, de sorte que l'audio ne peut pas être pré-généré mais doit être synthétisé dynamiquement. Comme le montre la figure suivante, lorsque le visiteur lit l'audio, la page utilise PRTP.js pour générer l'audio dans Amazon Polly, et il met en évidence l'audio synthétisé en utilisant la même approche qu'avec les pages statiques. Pour accéder aux services AWS à partir du navigateur, le visiteur a besoin d'une identité AWS. Nous montrons comment utiliser un Amazon Cognito pool d'identités pour permettre au visiteur un accès suffisant à Amazon Polly et au compartiment S3 pour restituer l'audio.

Contenu dynamique

La génération à la fois d'audio MP3 et de marques vocales nécessite que le service Polly synthétise deux fois la même entrée. Se référer au Page de tarification d'Amazon Polly comprendre les répercussions sur les coûts. La pré-génération permet de réduire les coûts car la synthèse est effectuée au moment de la construction plutôt qu'à la demande pour chaque interaction du visiteur.

Le code accompagnant cet article est disponible en tant que référentiel open source sur GitHub.

Pour explorer la solution, nous suivons ces étapes :

  1. Configurez les ressources, y compris le serveur de génération pré-génération, le compartiment S3, le serveur Web et l'identité Amazon Cognito.
  2. Exécutez la version statique pré-génération et testez les pages statiques.
  3. Testez les pages dynamiques.

Pré-requis

Pour exécuter cet exemple, vous avez besoin d'un Compte AWS avec l'autorisation d'utiliser Amazon Polly, Amazon S3, Amazon Cognito et (à des fins de démonstration) AWSCloud9.

Provisionner les ressources

Nous partageons une AWS CloudFormation modèle pour créer dans votre compte un environnement de démonstration autonome pour vous aider à suivre la publication. Si vous préférez configurer PRTP dans votre propre environnement, reportez-vous aux instructions de README.md.

Pour provisionner l'environnement de démonstration à l'aide de CloudFormation, téléchargez d'abord une copie du Modèle CloudFormation. Effectuez ensuite les étapes suivantes :

  1. Sur la console AWS CloudFormation, choisissez Créez une pile.
  2. Selectionnez Avec de nouvelles ressources (standard).
  3. Sélectionnez Téléchargez un fichier modèle.
  4. Selectionnez Choisir le fichier pour télécharger la copie locale du modèle que vous avez téléchargé. Le nom du fichier est prtp.yml.
  5. Selectionnez Suivant.
  6. Entrez un nom de pile de votre choix. Plus tard, vous le saisissez à nouveau en remplacement de .
  7. Vous pouvez conserver les valeurs par défaut dans le Paramètres .
  8. Selectionnez Suivant.
  9. Continuez à travers les sections restantes.
  10. Lisez et cochez les cases dans le Fonctionnalités .
  11. Selectionnez Créer une pile.
  12. Lorsque la pile est complète, trouvez la valeur de BucketName dans les sorties de la pile.

Nous vous encourageons à examiner la pile avec votre équipe de sécurité avant de l'utiliser dans un environnement de production.

Configurer le serveur Web et le serveur pré-génération dans un AWS Cloud9 IDE

Ensuite, sur la console AWS Cloud9, localisez l'environnement PRTPDemoCloud9 créé par la pile CloudFormation. Choisir Ouvrir l'IDE pour ouvrir l'environnement AWS Cloud9. Ouvrez une fenêtre de terminal et exécutez les commandes suivantes, qui clonent le code PRTP, configurent les dépendances pré-génération et démarrent un serveur Web avec lequel tester :

#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> 

Pour , utilisez le nom que vous avez donné à la pile CloudFormation. Pour , spécifiez une plage d'adresses IP autorisées à accéder au serveur Web. Pour restreindre l'accès au navigateur sur votre ordinateur local, recherchez votre adresse IP à l'aide de https://whatismyipaddress.com/ et ajouter /32 pour spécifier la plage. Par exemple, si votre IP est 10.2.3.4, use 10.2.3.4/32. Le serveur écoute sur le port 8080. L'adresse IP publique sur laquelle le serveur écoute est donnée dans la sortie. Par exemple:

Public IP is

3.92.33.223

Tester les pages statiques

Dans votre navigateur, accédez à PRTPStaticDefault.html. (Si vous utilisez la démo, l'URL est http://<cloud9host>:8080/web/PRTPStaticDefault.html, Où est l'adresse IP publique que vous avez découverte lors de la configuration de l'IDE.) Choisissez Jouez sur la commande audio en haut. Écoutez l'audio et regardez les faits saillants. Explorez le contrôle en modifiant les vitesses, les voix, les pauses, l'avance rapide et le rembobinage. La capture d'écran suivante montre la page ; le texte "Ignore le paragraphe masqué" est mis en surbrillance car il est en cours de lecture.

Lisez des pages Web et mettez en surbrillance le contenu à l'aide d'Amazon Polly PlatoBlockchain Data Intelligence. Recherche verticale. Aï.

Essayez la même chose pour PRTPStaticConfig.html ainsi que PRTPStaticCustom.html. Les résultats sont similaires. Par exemple, tous les trois lisent le texte alternatif de la photo du chat ("Photo aléatoire d'un chat"). Tous trois lisent NE, NW, SE et SW comme des mots complets ("nord-est", "nord-ouest", "sud-est", "sud-ouest"), en tirant parti des lexiques d'Amazon Polly.

Notez les principales différences dans l'audio :

  • PRTPStaticDefault.html lit tout le texte dans le corps de la page, y compris la partie récapitulative en bas avec "Vos pensées en un mot", "Soumettre la requête", "Dernière mise à jour le 1er avril 2020" et "Questions pour l'équipe de développement". PRTPStaticConfig.html ainsi que PRTPStaticCustom.html ne les lisez pas car ils excluent explicitement la synthèse de la parole.
  • PRTPStaticCustom.html lit le Meilleures ventes QB table différemment des autres. Il lit uniquement les trois premières lignes et lit le numéro de ligne pour chaque ligne. Il répète les colonnes pour chaque ligne. PRTPStaticCustom.html utilise une transformation personnalisée pour personnaliser la lecture de la table. Les autres pages utilisent le rendu de tableau par défaut.
  • PRTPStaticCustom.html lit "Tom Brady" à un volume plus fort que le reste du texte. Il utilise le langage de balisage de synthèse vocale (SSML) prosody tag pour personnaliser la lecture de Tom Brady. Les autres pages ne s'adaptent pas de cette façon.
  • PRTPStaticCustom.html, grâce à une transformation personnalisée, lit les tuiles principales dans l'ordre NW, SW, NE, SE ; c'est-à-dire qu'il lit « Articles du jour », « Citation du jour », « Photo du jour », « Blagues du jour ». Les autres pages lues dans l'ordre d'apparition des tuiles dans l'ordre naturel NW, NE, SW, SE dans le code HTML : "Articles du jour", "Photo du jour", "Citation du jour", "Blagues du Jour."

Approfondissons la façon dont l'audio est généré et comment la page met en évidence le texte.

Pré-générateur statique

Notre référentiel GitHub comprend des fichiers audio pré-générés pour le PRPTStatic pages, mais si vous souhaitez les générer vous-même, à partir du shell bash dans l'AWS Cloud9 IDE, exécutez les commandes suivantes :

# 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

Voyons maintenant comment fonctionnent ces scripts.

Cas par défaut

Nous commençons avec 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

Le script commence par exécuter le programme Python FixHTML.py pour créer le fichier HTML source PRTPStaticDefault.html bien formé. Il écrit la version bien formée du fichier dans example/tmp_wff.html. Cette étape est cruciale pour deux raisons :

  • La plupart des sources HTML ne sont pas bien formées. Cette étape répare le HTML source pour qu'il soit bien formé. Par exemple, de nombreuses pages HTML ne se ferment pas P éléments. Cette étape les ferme.
  • Nous gardons une trace de l'endroit où nous trouvons du texte dans la page HTML. Nous devons suivre les emplacements en utilisant la même structure de modèle d'objet de document (DOM) que celle utilisée par le navigateur. Par exemple, le navigateur ajoute automatiquement un TBODY à TABLE. Le programme Python suit les mêmes réparations bien formées que le navigateur.

gen_ssml.sh prend le code HTML bien formé en entrée, lui applique une transformation de feuille de style XML (XSLT) et génère un fichier SSML. (SSML est le langage d'Amazon Polly permettant de contrôler le rendu audio à partir du texte.) Dans l'exemple actuel, l'entrée est example/tmp_wff.html. La sortie est example/tmp.ssml. Le travail de la transformation consiste à décider du texte à extraire du code HTML et à alimenter Amazon Polly. generic.xslt est une transformation XSLT par défaut sensible pour la plupart des pages Web. Dans l'exemple d'extrait de code suivant, il exclut le contrôle audio, l'en-tête HTML, ainsi que les éléments HTML tels que script ainsi que form. Il exclut également les éléments avec l'attribut caché. Il comprend des éléments qui contiennent généralement du texte, tels que P, H1et SPAN. Pour ceux-ci, il rend à la fois une marque, y compris l'expression XPath complète de l'élément, et la valeur de l'élément.

<!-- 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>

Voici un extrait du SSML rendu. Ceci est transmis en tant qu'entrée à Amazon Polly. Remarquez, par exemple, que le texte "Sauter le paragraphe masqué" doit être lu dans l'audio, et nous l'associons à une marque, qui nous indique que ce texte apparaît à l'emplacement sur la page donné par l'expression 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>

Pour générer de l'audio dans Amazon Polly, nous appelons le script run_polly.sh. Il exécute le Interface de ligne de commande AWS (AWS CLI) commande aws polly start-speech-synthesis-task deux fois : une fois pour générer l'audio MP3, et une autre fois pour générer le fichier de repères. Étant donné que la génération est asynchrone, le script interroge jusqu'à ce qu'il trouve la sortie dans le compartiment S3 spécifié. Lorsqu'il trouve la sortie, il la télécharge sur le serveur de génération et copie les fichiers sur le web/polly dossier. Voici une liste des dossiers Web :

  • 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

Chaque page a son propre ensemble de fichiers MP3 et de marques spécifiques à la voix. Ces fichiers sont les fichiers pré-générés. La page n'a pas besoin d'invoquer Amazon Polly lors de l'exécution ; les fichiers font partie de la construction Web.

Cas piloté par la configuration

Ensuite, considérez 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

Le script est similaire au script du cas par défaut, mais les lignes en gras indiquent la principale différence. Notre approche est basée sur la configuration. Nous adaptons le contenu à extraire de la page en spécifiant ce qu'il faut extraire via la configuration, et non le code. En particulier, nous utilisons le fichier JSON transform_config.json, qui spécifie que le contenu à inclure sont les éléments avec des identifiants title, main, maintableet qbtable. L'élément avec ID wrapup devrait être exclu. Voir le code suivant :

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

Nous exécutons le programme Python ModGenericXSLT.py modifier generic.xslt, utilisé dans le cas par défaut, pour utiliser les inclusions et les exclusions que nous spécifions dans transform_config.json. Le programme écrit les résultats dans un fichier temporaire (example/tmp.xslt), auquel il passe à gen_ssml.sh comme sa transformation XSLT.

Il s'agit d'une option low-code. L'éditeur Web n'a pas besoin de savoir comment écrire XSLT. Mais ils doivent comprendre la structure de la page HTML et les identifiants utilisés dans ses principaux éléments d'organisation.

Cas de personnalisation

Enfin, considérez 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

Ce script est presque identique au script par défaut, sauf qu'il utilise son propre XSLT—example/custom.xslt— plutôt que le XSLT générique. Voici un extrait du 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>

Si vous souhaitez étudier le code en détail, reportez-vous aux scripts et programmes du référentiel GitHub.

Configuration du navigateur et points forts

Les pages statiques incluent un contrôle audio HTML5, qui prend comme source audio le fichier MP3 généré par Amazon Polly et résidant sur le serveur Web :

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

Au moment du chargement, la page charge également le fichier de repères généré par Amazon Polly. Cela se produit dans le PRTP.js fichier, que la page HTML inclut. Ce qui suit est un extrait du fichier de marques pour 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”}

Pendant la lecture audio, il y a un gestionnaire d'événements de minuterie audio dans PRTP.js qui vérifie l'heure actuelle de l'audio, trouve le texte à mettre en surbrillance, trouve son emplacement sur la page et le met en surbrillance. Le texte à mettre en évidence est une entrée de type sentence dans le fichier des marques. L'emplacement est l'expression XPath dans l'attribut name de l'entrée de type SSML qui précède la phrase. Par exemple, si l'heure est 18400, selon le fichier de repères, la phrase à mettre en surbrillance est "Ignore le paragraphe masqué", qui commence à 18334. L'emplacement est l'entrée SSML à l'heure 17667 : /html/body[1]/div[2]/ul[1]/li[1].

Tester les pages dynamiques

La page PRTPDynamic.html illustre la relecture audio dynamique à l'aide d'approches d'extraction audio par défaut, basées sur la configuration et personnalisées.

Cas par défaut

Dans votre navigateur, accédez à PRTPDynamic.html. La page a un paramètre de requête, dynOption, qui accepte les valeurs default, configet custom. Il est par défaut default, vous pouvez donc l'omettre dans ce cas. La page comporte deux sections avec du contenu dynamique :

  • Nouveaux Articles – Change fréquemment tout au long de la journée
  • Recherche de philosophes grecs par date – Permet au visiteur de rechercher des philosophes grecs par date et affiche les résultats dans un tableau

Lisez des pages Web et mettez en surbrillance le contenu à l'aide d'Amazon Polly PlatoBlockchain Data Intelligence. Recherche verticale. Aï.

Créez du contenu dans le philosophe grec section en entrant une plage de dates de -800 à 0, comme indiqué dans l'exemple. Alors choisi Trouvez.

Maintenant, lisez l'audio en choisissant Jouez dans le contrôle audio.

Dans les coulisses, la page exécute le code suivant pour restituer et lire l'audio :

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

Il appelle d'abord la fonction buildSSMLFromDefault in PRTP.js pour extraire la majeure partie du texte du corps de la page HTML. Cette fonction parcourt l'arborescence DOM, à la recherche de texte dans des éléments communs tels que p, h1, pre, spanet td. Il ignore le texte des éléments qui ne contiennent généralement pas de texte à lire à haute voix, tels que audio, optionet script. Il crée un balisage SSML à entrer dans Amazon Polly. Ce qui suit est un extrait montrant l'extraction de la première ligne de la philosopher table:

<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>

La chooseRenderAudio fonctionner dans PRTP.js commence par initialiser le kit SDK AWS pour Amazon Cognito, Amazon S3 et Amazon Polly. Cette initialisation n'a lieu qu'une seule fois. Si chooseRenderAudio est appelée à nouveau car le contenu de la page a changé, l'initialisation est ignorée. Voir le code suivant :

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()
};

Il génère de l'audio MP3 à partir d'Amazon Polly. La génération est synchrone pour les petites entrées SSML et asynchrone (avec sortie envoyée au compartiment S3) pour les grandes entrées SSML (plus de 6,000 3 caractères). Dans le cas synchrone, nous demandons à Amazon Polly de fournir le fichier MPXNUMX à l'aide d'une URL pré-signée. Lorsque la sortie synthétisée est prête, nous définissons le src attribut du contrôle audio à cette URL et chargez le contrôle. Nous demandons ensuite le fichier de marques et le chargeons de la même manière que dans le cas statique. Voir le code suivant :

// 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);
  });
});

Cas piloté par la configuration

Dans votre navigateur, accédez à PRTPDynamic.html?dynOption=config. Faites jouer le son. La lecture audio est similaire au cas par défaut, mais il existe des différences mineures. En particulier, certains contenus sont ignorés.

Dans les coulisses, lors de l'utilisation du config option, la page extrait le contenu différemment que dans le cas par défaut. Dans le cas par défaut, la page utilise buildSSMLFromDefault. Dans le cas piloté par la configuration, la page spécifie les sections qu'elle souhaite inclure et exclure :

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

La buildSSMLFromConfig fonction, définie dans PRTP.js, parcourt l'arborescence DOM dans chacune des sections dont l'ID est fourni sous inclusions. Il extrait le contenu de chacun et les combine ensemble, dans l'ordre spécifié, pour former un document SSML. Il exclut les sections spécifiées sous exclusions. Il extrait le contenu de chaque section de la même manière buildSSMLFromDefault extrait le contenu du corps de la page.

Cas de personnalisation

Dans votre navigateur, accédez à PRTPDynamic.html?dynOption=custom. Faites jouer le son. Il y a trois différences notables. Notons-les et considérons le code personnalisé qui s'exécute dans les coulisses :

  • Il lit les tuiles principales dans l'ordre NW, SW, NE, SE. Le code personnalisé obtient chacun de ces blocs de cellules à partir de maintable et les ajoute au SSML dans l'ordre NW, SW, NE, SE :
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, []));

  • "Tom Brady" est prononcé à haute voix. Le code personnalisé place le texte "Tom Brady" dans un SSML prosody tag:
if (cellText == "Tom Brady") {
   addSSMLMark(getXpathOfNode( node.childNodes[tdi]));
   startSSMLParagraph();
   startSSMLTag("prosody", {"volume": "x-loud"});
   addSSMLText(cellText);
   endSSMLTag();
   endSSMLParagraph();
}

  • Il ne lit que les trois premières lignes du tableau des quarterbacks. Il lit les en-têtes de colonne pour chaque ligne. Vérifiez le code dans le référentiel GitHub pour découvrir comment cela est implémenté.

Nettoyer

Pour éviter des frais futurs, supprimez la pile CloudFormation.

Conclusion

Dans cet article, nous avons présenté une solution technique à un problème commercial de grande valeur : comment utiliser Amazon Polly pour lire le contenu d'une page Web et mettre en évidence le contenu au fur et à mesure de sa lecture. Nous l'avons montré en utilisant des pages statiques et dynamiques. Pour extraire le contenu de la page, nous avons utilisé la traversée DOM et XSLT. Pour faciliter la mise en surbrillance, nous avons utilisé la fonction de marques vocales d'Amazon Polly.

Apprenez-en plus sur Amazon Polly en visitant son page de service.

N'hésitez pas à poser des questions dans les commentaires.


À propos des auteurs

Lisez des pages Web et mettez en surbrillance le contenu à l'aide d'Amazon Polly PlatoBlockchain Data Intelligence. Recherche verticale. Aï.Mike Havey est un architecte de solutions pour AWS avec plus de 25 ans d'expérience dans la création d'applications d'entreprise. Mike est l'auteur de deux livres et de nombreux articles. Visitez son Amazone page auteur lire plus.

Lisez des pages Web et mettez en surbrillance le contenu à l'aide d'Amazon Polly PlatoBlockchain Data Intelligence. Recherche verticale. Aï.Vineet Kachhawaha est un architecte de solutions chez AWS avec une expertise en apprentissage automatique. Il est chargé d'aider les clients à concevoir des charges de travail évolutives, sécurisées et rentables sur AWS.

Horodatage:

Plus de Apprentissage automatique AWS