Le web sémantique

Comment annoter sémantiquement un document ?

Le web sémantique a de plus en plus le vent en poupe. Même si les moteurs de recherche ne savent pas encore intégrer le web sémantique dans les analyses et la pertinence des résultats.

Malgré tout, l’engouement pour cette technologie est telle que des référentiels existent déjà (DBPedia, GeoWeb, FreeBase, etc.) et que de plus en plus de contributeurs annotent leurs documents avec du web sémantique afin d’être prêts pour le jour J.

Cependant, annoter un document n’est pas une chose aisée. En effet, nous pourrions annoter chaque mot du texte ou chaque objet afin de donner la signification sémantique. Mais dans ce cas, le volume d’informations serait multiplié et la lisibilité technique (code source) serait dégradée.

Trop peu d’annotation serait inutile. Autant ne rien mettre du tout.

Quel est donc le bon équilibre, la bonne quantité d’annotation pour une sémantique optimale ?

La juste proportion

Avant toute chose, il ne faut pas se précipiter sur les annotations sémantiques. Les moteurs de recherche actuels sont suffisamment performants pour déduire un grand nombre d'information sémantique dans du texte normal.

Pour cela, ils comparent le document en lui-même, mais aussi des corpus de textes, les habitudes des utilisateurs, etc.

Il convient donc de n'ajouter, en premier lieu, des annotations sémantiques que pour lever une ambigüité (homonymie de personnes, etc.), améliorer les relations (entre l'auteur de l'article et ses autres publications, par exemple), affiner la précision des mots-clefs (par exemple différencier deux lieux portant le même nom).

C'est essentiellement dans ces cas biens précis que le web sémantique peut avoir une vraie plus-value.

En revanche, les moteurs de recherche ont encore bien du mal à analyser les photographies. Même si des progrès ont été réalisés dans ce sens, ils ne sont actuellement effectifs que pour les visages.

Annotation systématique

Les métadonnées du document

Sur le web, les documents possèdent en général des métadonnées (date de création, auteur, etc.). A minima et dans tous les cas, il convient de systématiquement les documenter.

Cette documentation peut être incluse directement dans le document ou externe. Tout dépend de la façon de gérer ces données et des habitudes de l'architecte technique.

En général, ces métadonnées sont décrites par le Dublin Core.

xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:dcx="http://purl.org/dc/terms/"

Les mots-clef

Le TF-IDF est un bon point de départ pour une annotation du document lui-même. Les premières versions du moteur de recherche Google utilisaient cette méthode pour analyser les documents. Elle consiste à déterminer simplement les occurences des mots. Et plus un mot apparaît souvent dans le texte, plus il a de chances de devenir un mot-clef.

Il s’agit d’une méthode relativement simple à implémenter. À tel point que les développeurs web disposent d’outils capables de trouver les mots-clef d’une page web.

La première étape est donc d’évaluer ces mots-clefs. Normalement, l’auteur les connaît déjà. Mais, on ne sait jamais, il se peut qu’il y ait des surprises.

Ou bien, par fainéantise (en général, les outils d’analyse sont aussi capables d’exporter la liste des mots).

Choix des mots-clef (convention)

Afin de faciliter les recherches et les regroupements, l'idéal est de choisir une uniformité dans les notations sous-jacentes.

Or, dans le language naturel, il y a souvent plusieurs notations possibles.

Par exemple, l'être humain et l'homme, sont synonymes puisque dans le language usuel, l'homme désigne les hommes et les femmes (métonymie).

Le mot-clef sous-jacent sera toujours le même (grâce à l'attribut content) mais il sera invisible au lecteur.

Ce mot-clef sera préférentiellement choisi par les règles suivantes :

  • le plus court : dans notre exemple l'être humain fait 13 caractères et l'homme 7. l'homme sera donc le mot-clef préférentiel ;

  • sans les articles : ainsi l'homme sera défini et utilisé sous la forme homme ;

  • le plus générique possible : ainsi homme sera défini et utilisé sous la forme humain si c'est le sens du contexte (les hommes et les femmes) ;

  • au singulier, sauf pour les mots qui sont généralement utilisés au pluriel (mathématiques, etc.) ;

  • au neutre grammatical : en français le neutre étant le masculin, les mots-clef seront choisis préférentiellement au masculin.

Intégration des mots-clef

Pour l'intégration des mots-clefs, il existe des vocabulaires RDF. Nous utiliserons le CommonTag, simple à mettre en place et à utiliser.

Il s'intègre aisément dans le document en appelant son espace de nom :

xmlns:ctag="http://commontag.org/ns#"

dans la balise html.

Une fois l'espace de nom ajouté, il suffit d'ajouter les mots-clef définis de la façon suivante :

  • Dans l'en-tête du document HTML, au format habituel (pour les moteurs de recherche n'utilisant pas le web sémantique de façon efficace)

    <meta name="keywords" content="RDF, RDFa, web sémantique"/>
  • Dans l'en-tête du document, mais codé en RDFa/ctag :

    <meta typeof="ctag:Tag" rel="ctag:means" resource="http://dbpedia.org/page/Berlin" property="ctag:label" content="Berlin"/>
  • Dans le corps du document, de préférence au début ou à la fin

    <p>Mots-clef :
    <span typeof="ctag:Tag" rel="ctag:means" resource="http://dbpedia.org/page/Berlin">Berlin</span> ,
    ...
    </p>

Pour faciliter la lecture, il est préférable de les placer dans l'ordre hiérachique du plus générique au moins générique.

Remarque

L’annoteur peut, bien évidemment, ajouter tous les mots qu’il souhaite. Attention cependant à ne pas trop en faire !

Il ne faut, bien entendu, annoter que si le document fait référence et pas si le document n'y fait pas référence. Par exemple :

  • annoter : cette image (ou vidéo) montre X…

  • ne pas annoter : cette image (ou vidéo) ne montre pas X…

    Le mot-clef X apparaît ici pour indiquer qu'il n'y fait pas référence. Il est donc inutile d'annoter le document pour X.

Comme les mots-clef sont, normalement, répétés plusieurs fois, il serait contre-productif de les annoter systématiquement. Le mieux est de les ajouter dans les keyword et tag du document et éventuellement y faire référence à chaque utilisation.

Typage de données

Par défaut, tout est considéré comme du texte. Cependant, certaines valeurs peuvent avoir une réelle signification. Prenez l'habitude d'annoter tout ce qui est une date.

Définissez l'espace de nom :

xmlns:xsd="http://www.w3.org/2001/XMLSchema#"

puis utilisez-le :

<time pubdate="pubdate" property="dc:date" datatype="xsd:gYear">1981</time> <time pubdate="pubdate" property="dc:date" datatype="xsd:gYearMonth" content="2012-01">Janvier 2012</time>

Les entités

Au-delà de la simple reconnaissance de mots-clef, le traitement sémantique de base effectué en TALN est la reconnaissance d’entités nommées (lieux, personnes, organisations). En plus des mots-clef, il convient donc de définir des atomes d'informations liés aux entités à annoter.

Les objets graphiques

Autant que possible, il faut annoter les objets (images, vidéos, etc.), ne serait-ce que pour décrire leur source, l'auteur/compositeur et, éventuellement, les mots-clef rattachés.

Il est aussi utile de décrire le contenu du document, les moteurs de recherche ayant encore du mal à interpréter images et vidéos.

Commencer par identifier l'objet :

<img src="./img/photo.jpg" alt="description" title="description" rel="ctag:tagged" id="fig_1"/>

puis annotez l'objet à partir de son identifiant. À partir du moment où il est identifié, l'annotation peut être placée n'importe où dans la page.

Cette notation peut être visible

<span typeof="ctag:Tag" about="#fig_1" rel="ctag:means" resource="http://lien/vers/ressource">mot-clef</span>

ou invisible.

<span typeof="ctag:Tag" about="#fig_1" rel="ctag:means" resource="http://lien/vers/ressource"></span>

Les publications

Les publications doivent systématiquement être annotées. C'est à la fois une question de respect pour l'auteur de la publication et d'intérêt scientifique. Le plus souvent, Dublin Core suffit largement. Une bonne annotation devrait contenir le titre, l'auteur et l'année de publication :

<p about="http://uri/ressource"> <cite property="dc:title" xml:lang="en">Titre de la référence</cite> ◆ <span property="dc:creator">Auteur 1</span>, <span property="dc:creator">Auteur 2</span> ◆ <time pubdate="pubdate" property="dc:date" datatype="xsd:gYear">2005</time>.</p>

Si vous disposez de l'ISBN :

<p about="urn:isbn:0123456789"> <cite property="dc:title" xml:lang="en">Titre de la référence</cite> ◆ <span property="dc:creator">Auteur 1</span>, <span property="dc:creator">Auteur 2</span> ◆ <time pubdate="pubdate" property="dc:date" datatype="xsd:gYear">2005</time>.</p>

Bien entendu, la notation étant très souple, un auteur peut être une personne :

…<span property="dc:creator" typeof="foaf:Person"><span property="foaf:givenName">Alain</span> <span property="foaf:familyName">Benoît</span></span>…

Les personnes

Le risque d'homonymie ou d'anonymat étant important, surtout dans un monde comme celui du Web, il convient de rendre à César ce qui est à César.

Définissez toute référence à une personne. Commencez par ajouter l'espace de nom :

xmlns:foaf="http://xmlns.com/foaf/0.1/"

Puis utilisez-le pour définir vos personnes. Par défaut, de façon générique :

<span typeof="foaf:Person"><span property="foaf:name">Alain Benoît</span></span>

ou :

<span typeof="foaf:Person"><span property="foaf:givenName">Alain</span> <span property="foaf:familyName">Benoît</span></span>
  • Les personnages célèbres : renvoyez vers un document de référence décrivant leur vie.

    <span typeof="foaf:Person" resource="http://lien/vers/ressource><span property="foaf:givenName">Alain</span> <span property="foaf:familyName">Benoît</span></span>
  • Les anonymes (amis, contacts, ...) : renvoyez vers leur activité sociale ou professionnelle (facebook, weblog, site, CV, etc.)

Annotation au cas par cas

Les blocs

Parfois, l’information textuelle n’a de cohérence que dans un bloc. Par exemple :

Une adresse est composée, en général d’un ensemble d’informations : rue, numéro, code postal, ville, pays. Il peut aussi y avoir un numéro de téléphone...

Un événement : une date seule n’est pas forcément sémantiquement explicite. il convient de la rattacher à un type (date de naissance,...) ou un titre (Concert de X).

En plus d’être annotés, ces blocs pourront être extrait par des processus externes (GRDDL, etc.) dans un tout cohérent et, éventuellement, exportés vers des applications tierces (agenda, calendrier, …)

En général, un bloc n’est pas répété plusieurs fois. Il peut donc être annoté directement. Si une répétition était pourtant nécessaire, le plus propre serait de créer une ancre dans le document afin d’y faire référence à chaque fois que c’est utile.

Donc tout dépend de l'usage que vous voulez autoriser. Par exemple si vous voulez signaler la date d'un concert de votre groupe préféré, l'annotation de la date suffira. En revanche, si vous désirez permettre l'import de l'événement complet dans une application, alors l'annotation complète du bloc est requis. Vous annoterez alors le nom du groupe, le lieu, la date, etc.

<div prefix="v: http://rdf.data-vocabulary.org/#" typeof="v:Event">
<a rel="v:url" href="http://amyandtheredfoxies.example.com/events"
property="v:summary">Tour Info: Amy And The Red Foxies</a>

<span rel="v:location">
<a typeof="v:Organization" rel="v:url" href="http://www.kammgarn.de/" property="v:name">Kammgarn</a>
</span>
<div rel="v:photo"><img src="foxies.jpg"/></div>
<span property="v:summary">Hey K-Town, Amy And The Red Foxies will rock Kammgarn in October.</span>
When:
<span property="v:startDate" content="20091015T19:00">15. Oct., 7:00 pm</span>-
<span property="v:endDate" content="20091015T21:00">9:00 pm</span>
</span>

Category: <span property="v:eventType">concert</span>
</div>

De la même façon, pour les personnes, vous devez annoter a minima le nom, mais vous pouvez annoter son adresse, son entreprise, son numéro de téléphone, etc.

<div vocab="http://xmlns.com/foaf/0.1/" typeof="Person">
<p>
<span property="name">Alice Birpemswick</span>,
Email: <a property="mbox" href="mailto:alice@example.com">alice@example.com</a>,
Phone: <a property="phone" href="tel:+1-617-555-7332">+1 617.555.7332</a>,
<a property="homepage" href="http://example.com/alice/">site web</a> </p>
</div>

Rechercher la signification

Trouver des mots-clef, identifier des structures... tout cela ne sert à rien si il n'y a pas, derrière, une description sémantique suffisamment performante.

Chacun pouvant construire son propre référentiel sémantique, la première des difficultés est de trouver un référentiel suffisamment crédible pour être alimenté, mis à jour et pérenne.

Malheureusement, il n'existe pas de règles pour trouver ces référentiels. Il faut chercher, tenter, faire des choix.

Cependant, pour choisir, cherchez un référentiel qui réponde aux critères suivants :

  • Accessibilité : Les données doivent être accessibles facilement. Une simple requête doit vous permettre de trouver votre référence. Si vous devez télécharger une base complète afin d'accéder aux informations, passez votre chemin.

  • Lisibilité : Les données doivent être aussi lisible aisément par un être humain (vous) de façon à valider que c'est bien l'annotation sémantique que vous recherchiez. Si vous devez lire dans du code source (XML, RDF/XML, RDF/N3) et qu'il n'y a aucune interface humaine, passez votre chemin.

  • Réputation : Vérifiez la réputation de la source. Plus elle est citée et utilisée, plus elle a de chance d'être pérenne.

  • Richesse : Vérifiez la richesse de l'information. Le référentiel doit couvrir le plus possible le sujet qui vous préoccupe.

  • Maintenance : Vérifiez qui est propriétaire du référentiel et de sa maintenance. Préférez une source libre à une source appartenant à une entreprise.

  • Facilité de recherche : La recherche et le parcours de la base d'informations doivent être aisés.

    Par exemple, pour DBPedia, la recherche se fait par l'interface Openlink et est intégrable dans votre navigateur par un greffon OpenSearch.

Exemple : Exploitation des mots-clef (tags)

Comme nous avons utilisé un certain nombre de conventions, l'exploitation personnelle des mots-clef est aisée.

Remarque

L'exploitation d'un document pour une extraction nécessite qu'il soit rédigé en XML ou un dérivé (XHTML).

Extraction des mots-clef

Il est aisé d'extraire les mots-clef et de générer une recherche sur ceux-ci.

Mot-clef invisible

Les mots-clef invisibles sont de la forme :

<span typeof="ctag:Tag" about="#fig_0" rel="ctag:means" resource="http://dbpedia.org/resource/Berlin"></span>

Par exemple, ici pour ajouter le tag Berlin (à une image,…).

Nous conserverons cette notation qui ne sera pas utile pour une exploitation locale, mais juste destinée aux moteurs de recherche.

Mot-clef invisible pour le lecteur

Les mots-clef invisibles pour le lecteur mais pas pour le traitement local sont de la forme :

<span typeof="ctag:Tag" about="#fig_0" rel="ctag:means" resource="http://dbpedia.org/resource/Berlin" property="ctag:label" content="Berlin" data-tag="Berlin"></span>

La partie content permet d'identifier le texte en langue locale tandis que data-tag servira d'identifiant de regroupement (pas d'espaces ni de caractères accentués).

Cette notation sera extraite simplement avec le code XSL suivant :

<xsl:template match="span[ @typeof='ctag:Tag' and @property='ctag:label' and exists(@content) ]">
<xsl:variable name="tag.id" select="@data-tag"/>
<xsl:variable name="tag.label" select="@content"/>

<tag id="{$tag.id}" label="{$tag.label}" href="{$url}">
<title><xsl:value-of select="$title"/></title>
<desc><xsl:value-of select="$description"/></desc>
</tag><xsl:text>
</xsl:text>
</xsl:template>

Mot-clef visible pour le lecteur

Les mots-clef visibles pour le lecteur sont de la forme :

<span typeof="ctag:Tag" about="#fig_0" rel="ctag:means" resource="http://dbpedia.org/resource/Berlin" property="ctag:label" data-tag="Berlin">Berlin</span>

Le content disparaît et il faut récupérer le contenu du span :

<xsl:template match="span[ @typeof='ctag:Tag' and @property='ctag:label' and not(exists(@content)) ]">
<xsl:variable name="tag.id" select="@data-tag"/>
<xsl:variable name="tag.label" select="."/>

<tag id="{$tag.id}" label="{$tag.label}" href="{$url}">
<title><xsl:value-of select="$title"/></title>
<desc><xsl:value-of select="$description"/></desc>
</tag><xsl:text>
</xsl:text>
</xsl:template>

Les synonymes sont rattachés au mot-clef par défaut :

<span typeof="ctag:Tag" about="#fig_0" rel="ctag:means" resource="http://dbpedia.org/resource/Tag" property="ctag:label" content="Tag" data-tag="Tag">Blabla1</span> <span typeof="ctag:Tag" about="#fig_1" rel="ctag:means" resource="http://dbpedia.org/resource/Tag" property="ctag:label" content="Tag" data-tag="Tag">Blabla2</span>

Mot-clef avec hyperlien

Le mot-clef avec hyperlien est de la forme :

<a href="tag.sh?tag=Berlin" typeof="ctag:Tag" about="#fig_1" rel="ctag:means" resource="http://dbpedia.org/resource/Berlin" property="ctag:label" data-tag="Berlin">Berlin</a>

Il permet de naviguer et à travers le mot-clef présent dans les autres articles.

Il est récupéré par :

<xsl:template match="a[ @typeof='ctag:Tag' and @property='ctag:label' and not(exists(@content)) ]">
<xsl:variable name="tag.id" select="@data-tag"/>
<xsl:variable name="tag.label" select="."/>
<tag id="{$tag.id}" label="{$tag.label}" href="{$url}">
<title><xsl:value-of select="$title"/></title>
<desc><xsl:value-of select="$description"/></desc>
</tag><xsl:text>
</xsl:text>
</xsl:template>

Le script tags.sh permet de concaténer la base de données des mots-clef et de présenter un résultat de recherche (tous les articles rattachés au mot-clef sélectionné).

Mot-clef dans les méta-données

Les mots-clefs dans les méta-données sont de la forme :

<meta name="keywords" typeof="ctag:Tag" rel="ctag:means" resource="http://dbpedia.org/resource/Berlin" property="ctag:label" content="Berlin" data-tag="Berlin"/>

Et sont récupérés par :

<xsl:template match="meta[ @typeof='ctag:Tag' and @property='ctag:label' and exists(@content) ]">
<xsl:variable name="tag.id" select="@data-tag"/>
<xsl:variable name="tag.label" select="@content"/>
<tag id="{$tag.id}" label="{$tag.label}" href="{$url}">
<title><xsl:value-of select="$title"/></title>
<desc><xsl:value-of select="$description"/></desc>
</tag><xsl:text>
</xsl:text>
</xsl:template>

Ou de la forme :

<meta name="keywords" typeof="ctag:Tag" rel="ctag:means" resource="http://dbpedia.org/resource/Berlin" property="ctag:label" data-tag="Berlin">Berlin</meta>

Et sont récupérés par :

<xsl:template match="meta[ @typeof='ctag:Tag' and @property='ctag:label' and not(exists(@content)) ]">
<xsl:variable name="tag.id" select="@data-tag"/>
<xsl:variable name="tag.label" select="."/>
<tag id="{$tag.id}" label="{$tag.label}" href="{$url}">
<title><xsl:value-of select="$title"/></title>
<desc><xsl:value-of select="$description"/></desc>
</tag><xsl:text>
</xsl:text>
</xsl:template>

Traitement

L'extraction donne des fichiers de la forme :

<tag id="Tag" label="mot-clef" href="article.html"><title>Titre de l'article</title><desc>Description de l'article</desc></tag>

Les données doivent être regroupées car un même mot-clef peut apparaître plusieurs fois dans le même article, mais il ne doit apparaître qu'une seule fois dans le résultat.

le contenu de data-tag sert à alimenter id. Il est constant au travers des articles pour un même mot-clef, quel que soit le texte affiché dans l'article. Il peut être un numéro, un code, n'importe quelle chaîne de caractères.

Le contenu de content sert à alimenter label, le mot-clef dans sa langue locale, le mot-clef qui sera affiché dans la page de recherche. Il est constant au travers des articles pour un même mot-clef, quel que soit le texte affiché l'article.

Le contenu de title de l'article sert à alimenter title, et permettra d'afficher le titre de l'article dans le résultat de cherche.

Le contenu de meta name="description" de l'article sert à alimenter desc, et permettra d'afficher la description de l'article dans le résultat de cherche.

href est le nom du fichier physique correspondant à l'article.

Il suffit ensuite de nettoyer la base de mots-clef en supprimant les doublons grâce à un simple :

cat tags.xml | sort | uniq > tags.db

Exploitation

À partir de cette base de données nettoyée, il est possible soit de faire une recherche dynamique (comme dans n'importe quelle base de données) grâce à une commande XPath de la forme :

tag[@id = $param.tag]

depuis le lien hypertexte :

<a href="tag.sh?tag=Berlin" … >Berlin</a>

Elle affichera ainsi tous les articles contenant le même mot-clef.

Il est aussi possible de générer (grâce à une transformation XSL) une page statique contenant l'ensemble des mots-clef et les articles associés pour chacun.