Exemple 7. Déclaration d’une DTD dans un fichier
<?xml version="1.0" encoding="ISO-8859-1"?>
<!DOCTYPE web-app
PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
"http://java.sun.com/dtd/web-app_2_3.dtd">
<web-app>
...
</webapp>
<!DOCTYPE
et se terminant par >.
Le premier mot se trouvant dans cet élément est le nom de la DTD, qui correspond au nom de l’élément racine :
web-app
dans notre cas.
Suit une déclaration, qui indique où se trouve, physiquement, le fichier dans lequel la DTD se trouve. Ce fichier peut se trouver en trois endroits :
SYSTEM
;
http
(par exemple), auquel cas on utilise le mot-clé
PUBLIC
(cas de notre exemple) ;
Exemple 8. Une première DTD dans un en-tête de fichier XML
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE marin [ <!ELEMENT marin (nom, prenom, remarque)> <!ELEMENT nom (#PCDATA)> <!ELEMENT prenom (#PCDATA)> <!ELEMENT remarque (#PCDATA)> <!ATTLIST remarque lang CDATA "FR"> ]> <!-- suit le reste du fichier marin.xml --> <marin> ... </marin>
marin.dtd
(par exemple), et de le référencer de la façon suivante :
Exemple 9. Référence à une DTD dans un fichier externe
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE marin SYSTEM "marin.dtd">
<marin>
...
</marin>
<!ELEMENT >
permettent de définir des éléments XML. Cette DTD nous indique que le premier élément XML que l’on doit trouver est un élément
marin
.
Suit dans cet élément
<!ELEMENT >
une définition du contenu de cet élément. Dans le cas de
marin
, on lit (
nom
,
prenom
,
commentaire
). Cela signifie que notre élément
marin
doit nécessairement contenir trois sous-éléments qui ont pour nom
nom
,
prenom
et
commentaire
, dans cet ordre. Telles que les choses sont déclarées, la présence de ces trois sous-éléments n’est pas facultative, et il ne peut pas y en avoir plusieurs.
Leur déclaration à cet endroit signifie que plus loin dans le document DTD, il doit se trouver trois autres
<!ELEMENT >
, chacun définissant les éléments
nom
,
prenom
et
commentaire
. Ce point est d'ailleurs bien respecté dans notre exemple.
La déclaration de nom est différente :
<!ELEMENT nom (#PCDATA)>
. Elle indique que l’élément
nom
ne contient pas de sous-élément, mais qu’il contient du texte.
Enfin la dernière déclaration, celle de
remarque
, est référencée par la déclaration d’un attribut :
lang
. Cet attribut est déclaré dans un élément
<!ATTLIST >
. Cet élément a pour premier argument le nom de l’élément dans lequel se trouve l’attribut, suivi du nom de l’attribut et de son type. En général le type d’un attribut est
CDATA
. La dernière déclaration
"FR"
permet de fixer une valeur par défaut à cet attribut. S’il n’est pas explicitement écrit dans un fichier XML, ou créé au niveau du DOM, il prendra la valeur par défaut
FR
.
EMPTY
.
Le contenu est porté entre parenthèses. S’il est composé de sous-éléments, alors on en donne la liste, séparée par des virgules. Chacun de ces sous-éléments doit figurer dans la DTD dans une balise
<!ELEMENT >
.
Enfin si un élément possède un contenu textuel, alors il est signalé par le code
#PCDATA
.
On peut ajouter trois modificateurs à un sous-élément :
?
;
*
;
+
.
Exemple 10. Exemple de codage de sous-éléments dans une DTD
<!DOCTYPE bateau [ <!ELEMENT bateau (capitaine, equipage, marchandises)> <!ELEMENT capitaine (nom, prenom, grade)> <!ELEMENT equipage (marin+)> <!ELEMENT marchandises (marchandise*)> ... ]>
<!Element >
de la DTD.
La valeur de l’attribut peut être spécifiée de plusieurs façon :
CDATA
, suivi éventuellement d’une valeur par défaut entre double quotes ;
#IMPLIED
, s’il est obligatoire, il est
#REQUIRED
;
#FIXED
, suivi de cette valeur obligatoire entre double quotes ;
Exemple 11. Exemple de codage d’attributs dans une DTD
<!DOCTYPE marin [ <!ELEMENT marin (nom, prenom)> <!ATTLIST marin age #REQUIRED> <!ATTLIST marin type #FIXED "marin"> <!ELEMENT commentaire (#PCDATA)> <!ATTLIST commentaire lang ("EN", "FR") "FR"> ... ]>Il existe d’autres possibilités de spécifier des attributs, notamment par
#ID
,
#IDREF
etc… On pourra se reporter aux spécifications officielles pour plus de détails.
web.xml
dans le cadre de la version 2.3 de l’API servlet. Ce document est téléchargeable sur l'URL http://java.sun.com/dtd/web-app_2_3.dtd. C’est là que les analyseurs XML validant vont aller le chercher, ce qui leur permettra de valider, ou non, que le fichier
web.xml
considéré est bien conformes aux spécifications.
Il est important de savoir lire à l’œil ce genre de document, dans la mesure où c’est souvent le seul moyen de trouver la raison pour laquelle Tomcat refuse de charger une application web, pour cause de
web.xml
invalide.
Ce document contient énormément de commentaires, le premier élément que l’on trouve est le suivant.
Exemple 12. Déclaration du contenu de
web.xml
dans
web-app_2_3.dtd
<!ELEMENT web-app ( icon?, display-name?, description?, distributable?, context-param*, filter*, filter-mapping*, listener*, servlet*, servlet-mapping*, session-config?, mime-mapping*, welcome-file-list?, error-page*, taglib*, resource-env-ref*, resource-ref*, security-constraint*, login-config?, security-role*, env-entry*, ejb-ref*, ejb-local-ref*) >
web-app
, l’ordre dans lequel on doit les trouver ainsi que leur cardinalité. Il apparaît donc que si l’on range l’élément
listener
, qui permet de poser des listeners sur l’ouverture et la fermeture des sessions, après les déclarations des servlets, le document XML ne sera plus valide, et Tomcat refusera de charger l’application web correspondante.
L’élément
listener
est lui-même spécifié un peu plus loin dans ce document.
Exemple 13. Spécification de l’élément
listener
dans
web-app_2_3.dtd
<!ELEMENT listener (listener-class)> <!ELEMENT listener-class (#PCDATA)>
Node
NodeList
Element
Attr
CharacterData
Comment
CDATASection
Text
Entity
EntityReference
ProcessingInstruction
Document
DocumentFragment
DocumentType