uia hatz

46
Crearea vocabularelor XML • Se pot crea cu diverse limbaje. Cele mai populare sunt: DTD (inclus de la început în standardul XML) XML Schema (apărut ulterior, mai puternic) • Un document creat după regulile unui vocabular trebuie indice acest lucru, astfel încât oricine îl poată valida (vocabularul trebuie fie accesibil online): Vocabularele create cu DTD se declară pe a doua linie a documentului cu <!DOCTYPE radacina SYSTEM URLvocabular> Vocabularele XML Schema se declară trecând în rădăcina documentului cu atributele: xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=URLvocabular

Upload: demiii

Post on 14-Jul-2016

46 views

Category:

Documents


3 download

DESCRIPTION

hatz

TRANSCRIPT

Page 1: uia hatz

Crearea vocabularelor XML• Se pot crea cu diverse limbaje. Cele mai populare sunt:– DTD (inclus de la început în standardul XML)– XML Schema (apărut ulterior, mai puternic)

• Un document creat după regulile unui vocabular trebuie să indice acest lucru, astfel încât oricine să îl poată valida (vocabularul trebuie să fie accesibil online):– Vocabularele create cu DTD se declară pe a doua linie a documentului cu

<!DOCTYPE radacina SYSTEM URLvocabular>– Vocabularele XML Schema se declară trecând în rădăcina documentului cu

atributele:xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation=URLvocabular

Page 2: uia hatz

Exemple de reguli create cu DTD<!ELEMENT AAA (BBB+,CCC?)> - elementul AAA poate conţine minim un element BBB și maxim un CCC<!ELEMENT BBB (DDD)> -elementul BBB va conţine obligatoriu un element DDD<!ELEMENT DDD EMPTY>-elementul DDD va fi obligatoriu vid<!ELEMENT CCC (#PCDATA|DDD)>-elementul CCC poate conţine fie un nod text, fie un element DDDUn document valid în raport cu aceste reguli:<?xml version="1.0"?><!DOCTYPE AAA SYSTEM "C:\DTDuri\exemplu.dtd"><AAA>

<BBB> fișierul DTD în care s-au salvat regulile!

<DDD /></BBB><CCC>text oarecare</CCC>

</AAA>

Page 3: uia hatz

Exemple de reguli create cu DTD

<!ELEMENT Curs EMPTY><!ATTRLIST Curs

CodCurs ID #REQUIRED -atribut obligatoriu cu valori uniceDescriere CDATA -atribut opţional cu valori textualeTipCurs (A|B|C) #REQUIRED> -atribut obligatoriu cu listă de valori permise

Exemple valide:<Curs ID="C1" TipCurs="B" /><Curs ID="C2" Descriere="…." TipCurs="C" />Exemplu invalid:<Curs Descriere="…" TipCurs="A">text oarecare</Curs>

Page 4: uia hatz

Tipuri de atribute în vocabulare DTD

• CDATA – atribute poate lua orice valoare exprimabilă ca string• (v1|v2|…|vn) – atributul poate lua una din valorile enumerate• ID – atributul e cheia primară a documentului, trebuie să aibă valori unice într-un

document• IDREF– atributul va funcţiona ca o "cheie străină", valoarea sa trebuie să fie un ID

existent (deci exprimă un link spre un alt element, vezi HREF în HTML!)• NMTOKEN – atributul va putea lua mai multe valori între aceleași ghilimele,

separate între ele prin spaţii (de exemplu CLASS în HTML poate enumera mai multe stiluri CSS!)

Observaţie:DTD nu poate impune tipuri de date (integer, boolean etc.)! În schimb XML Schema poate.

Page 5: uia hatz

Beneficii XML Schema faţă de DTD• XML Schema este el însuşi un vocabular XML (DTD are o sintaxă proprie, ce nu respectă

regulile de bună formare):Þ Vocabularele XML Schema sunt tot fișiere XML (de ex. regulile vocabularului pot fi interogate cu Xpath, pot fi

ele însele validate)• XML Schema oferă tipizare (DTD nu oferă tipizare)

Þ Tipuri de date + expresii regulate pot fi impuse asupra atributelor și nodurilor text• XML Schema permite modularitatea documentelor

Þ Elemente diferite din același document pot aparţine unor vocabulare diferite (cu DTD, un document trebuie să se supună integral unui același vocabular); de exemplu în pagini HTML putem avea și cod SVG (elemente grafice)

• XML Schema permite modularitatea vocabularelor:Þ Se pot crea vocabulare noi prin reunirea regulilor din vocabulare existente

• XML Schema are caracteristici obiectuale, posibilităţi de reutilizareÞ Se pot crea "clase de elemente", ce vor deveni reutilizabile (pot fi "moștenite" pentru a crea structuri

înrudite)• XML Schema permite chei mai sofisticate decât atributele ID:

Þ Chei multivaloare = când unicitatea se impune pe o combinaţie de atribute și/sau noduri textÞ Chei cu unicitate limitată = valori ce trebuie să fie unice doar în interiorul unui marcator (se pot repeta

în afara sa)Þ Aceste facilităţi permit modelarea unei întregi baze de date, cu mai multe tabele, în același document

Page 6: uia hatz

Exemplu de reguli XML Schema<xs:element name="DatePersonale">

<xs:complexType> <xs:sequence>

<xs:element name="profesie" type="xs:string" minOccurs="1" /><xs:element name="varsta" minOccurs="0">

<xs:simpleType><xs:restriction base="xs:nonNegativeInteger">

<xs:minInclusive value="18" /><xs:maxInclusive value="100" />

</xs:restriction></xs:simpleType>

</xs:element> valid!!</xs:sequence></xs:complexType>

</xs:element>

<DatePersonale><varsta>16</varsta>

</DatePersonale>(invalid!!!)

<DatePersonale><profesie><medic /></profesie>

</DatePersonale>(invalid!!)

<DatePersonale><profesie>Medic</profesie><varsta>25</varsta>

</DatePersonale>

Page 7: uia hatz

Tipurile de date din XML Schema

Page 8: uia hatz

Tipuri XML Schema• Un vocabular XML Schema se construiește prin definirea unor TIPURI

("clase de elemente") ce pot fi derivate ("moștenite") pentru a construi alte TIPURI– Elementele prezente în documente vor fi instanţe ale TIPURILOR

prevăzute de vocabular– Derivarea tipurilor duce la o "ierarhie de tipuri" (similară

ierarhiilor de clase create prin moștenire în programarea obiectuală). Derivarea se poate face pe două căi:• Constrângere = pornind de la un TIP existent, se elimină o parte din

marcatorii/atributele/valorile textuale permise• Extindere = pornind de la un TIP existent, i se adaugă

marcatori/atribute/valori permise

Page 9: uia hatz

Exemplu de reguli XML Schema<xs:element name="DatePersonale">

<xs:complexType> <xs:sequence>

<xs:element name="profesie" type="xs:string" minOccurs="1" /><xs:element name="varsta" minOccurs="0">

<xs:simpleType><xs:restriction base="xs:nonNegativeInteger">

<xs:minInclusive value="18" /><xs:maxInclusive value="100" />

</xs:restriction></xs:simpleType>

</xs:element></xs:sequence>

</xs:complexType></xs:element>

<DatePersonale><profesie>Sofer</profesie>

<varsta> 32 </varsta></DatePersonale>

<DatePersonale><profesie>Profesor</profesie><profesie>Cercetator</profesie>

</DatePersonale>

Acesta e un element de tip complex

Exemple de instanţe valide ce pot apare în documente:

Page 10: uia hatz

Tipuri XML Schema• TIPURILE pot fi:

– Simple (predefinite sau derivate) = vor sta la baza atributelor sau marcatorilor simpli (care nu au atribute și nici elemente fiu)

Exemplu marcator simplu: <Nume>Pop Ioan</Nume>– Complexe cu conţinut simplu = stau la baza marcatorilor cu atribute care nu au

elemente fiu, dar au conţinut textualExemplu: <Student Nota="10">Pop Ioan</Student>– Complexe cu conţinut vid = stau la baza marcatorilor cu atribute, dar lipsiţi de

orice conţinutExemplu: <Student Nume="Pop Ioan" Nota="10" />– Complexe cu conţinut mixt = stau la baza marcatorilor ce pot conţine alţi

marcatoriExemplu: <Student><Nume>Pop Ioan</Nume><Nota>10</Nota></Student>– Complexe cu conţinut derivat = sunt tipurile create prin derivare

Page 11: uia hatz

Tipurile simpleA. Tipuri predefinite = tipuri de date oferite de XML Schema pentru valori simple. Sunt

mai sofisticate decât tipurile de date din programarea clasică:– textuale: string, Name ("nume XML", un string care arată ca un nume, începe

cu literă etc.), token (listă de "cuvinte", separate cu maxim un spaţiu)– numerice: integer, float, short, byte– temporale: date, time, duration– moștenite de la DTD: ID, IDREF, ENTITY, NMTOKEN etc.– alte tipuri: anyURI (identificatori sau adrese URL), base64Binary (pt informaţii

non-text serializate ca text)Definirea unui tip de element simplu, folosind un tip predefinit pentru conţinutul său:<xs:element name="profesie" type="xs:string"/>Definirea unui tip de atribut, folosind un tip predefinit:<xs:attribute name="varsta" type="xs:integer"/>

B. Tipuri derivate din cele predefinite (se acceptă doar derivarea prin constrângere !)

Page 12: uia hatz

Tip simplu derivat din tip predefinit<xs:element name="varsta">

<xs:simpleType><xs:restriction base="xs:integer"><xs:minInclusive value="18" /><xs:maxInclusive value="99" /></xs:restriction>

</xs:simpleType></xs:element>

S-a creat tipul varsta:• Este un tip simplu de element - simpleType (marcatorul varsta nu va putea conţine alţi

marcatori și nici atribute)• Tipul e creat prin constrângere (xs:restriction) aplicată asupra tipului părinte

(base="xs:integer")• Constrângerea indică faptul ca valorile permise sunt numere în intervalul 18-99• Exemplu de instanţă validă: <varsta>20</varsta>

Page 13: uia hatz

Constrângerea tipurilor simple• Obs: Tipurile predefinite nu pot fi extinse, doar constrânse (nu putem adăuga valori noi la

tipul integer!)• Constrângerea se face prin faţete (restricţii, ca în slide-ul precedent):

– Se pot limita intervale numerice: minInclusive, maxInclusive, minExclusive– Se poate limita numărul de caractere: length, totalDigits, fractionDigits– Se poate impune o listă de valori permise: enumeration– Se poate impune o expresie regulată pe stringuri: pattern– Se poate preciza dacă la restricţiile de mai sus să se considere sau nu spaţiile albe

succesive: whiteSpace

Exemple:

<xs:pattern value="[A-Z][0-9].+"/>– Va permite doar stringuri formate dintr-o literă, o cifră și minim încă un caracter oarecare

<xs:length value="5"/><xs:whiteSpace value="collapse"/>

– Va permite doar stringuri care, în urma reducerii spaţiilor albe succesive la câte unul singur, au lungimea 5

• Tipurile simple se pot deriva din alte tipuri simple, caz în care vor moșteni aceste restricţii și le vor putea constrânge mai departe, prin restricţii suplimentare

Page 14: uia hatz

• Sunt numeroase cazurile în care un atribut (sau un marcator) trebuie să poată lua mai multe tipuri de valori– Exemplu: atributul COLOR din HTML poate lua atât coduri numerice (RGB) cât

și stringuri (denumiri de culori)

• În acest caz se definesc tipuri simple agregate, prin:– listă explicită de valori (cu ajutorul restricţiei enumeration)– reuniunea unor tipuri simple deja definite (union)– o combinaţie dintre cele două

Agregarea tipurilor simple

Page 15: uia hatz

Exemplu de tip simplu agregat<xs:element name="varsta"><xs:simpleType><xs:union>

<xs:simpleType><xs:restriction base="xs:integer">

<xs:minInclusive value="18"/><xs:maxInclusive value="100"/>

</xs:restriction></xs:simpleType><xs:simpleType>

<xs:restriction base="xs:string"><xs:enumeration value="necunoscuta"/>

</xs:restriction></xs:simpleType>

</xs:union></xs:simpleType></xs:element>Exemple valide: <varsta>20</varsta> sau <varsta>necunoscuta</varsta>

Page 16: uia hatz

Blocarea derivării• Dacă dorim ca un tip simplu să nu poată fi derivat în alte tipuri, în

definiţia sa putem bloca derivarea cu atributul final:– final="#all" blochează orice derivări– final="restriction" blochează derivarea prin constrângere– final="extension" blochează derivarea prin extindere– final="union" blochează derivarea prin reuniune

• Blocarea se poate aplica și la nivel de faţetă, cu atributul fixed:<xs:minInclusive value="18" fixed="true" />

Limita numerică minInclusive va putea fi moștenită de noi tipuri derivate, dar nu va putea fi redefinită în noile tipuri!

Page 17: uia hatz

Tipul complex cu conţinut simplu• Complex cu conţinut simplu = are atribute, conţinut textual, dar

nu și elemente copil• Se obţine derivând un tip simplu prin adăugare de atribute (deci

prin extindere):<xs:element name="ModelTelevizor"><xs:complexType><xs:simpleContent>

<xs:extension base="xs:string"><xs:attribute name="Diagonala" type="xs:integer"/></xs:extension>

</xs:simpleContent></xs:complexType></xs:element>

• Exemple de elemente valide (în mod implicit atributele sunt opţionale! cu use="required" în xs:attribute se poate impune obligativitatea):

<ModelTelevizor Diagonala="100">Samsung</ModelTelevizor><ModelTelevizor>Sony</ModelTelevizor>

Page 18: uia hatz

Metode de obţinere prin derivare a tipurilor complexe cu conţinut simplu

1. Extindem un tip simplu de element– prin adăugare de atribute noi

2. Constrângem un tip complex cu conţinut mixt– prin eliminare de elemente copil până rămâne doar

conţinutul textual3. Constrângem alt tip complex cu conţinut simplu, la

nivel de atribute– constrângem valorile atributelor (la un interval permis,

la o listă de valori permise, convertim atribute obligatorii în opţionale etc.)

Page 19: uia hatz

Tipul complex cu conţinut mixt• Complex cu conţinut mixt = poate avea elemente copil. Acestea pot apare în diverse moduri de

grupare:– sequence: impune ca elementele copil să apară într-o anumită ordine, implicit o dată– choice: doar unul din elementele copil posibile poate apare la o instanţă, implicit o dată– all: oricare din elementele copil poate să apară o dată, nu contează ordinea– sequence și choice se pot combina (secvenţe de alternative, alternative de secvenţe etc.)

<xs:complexType name="DescriereTelevizor" mixed="true"><xs:sequence>

<xs:element name="Diagonala" type="xs:integer"/><xs:element name="Producator" type="xs:string"/>

</xs:sequence></xs:complexType><xs:element name="Televizor" type="DescriereTelevizor"/>

Exemplu de element valid:<Televizor><Diagonala>22</Diagonala><Producator>Samsung</Producator></Televizor>

• În plus, pentru fiecare element copil se poate stabili de câte ori să apară, cu atributele minOccurs și maxOccurs (valoarea unbounded permite număr nelimitat de apariţii)

• Pentru a permite orice combinaţie posibilă a copiilor, cu oricâte repetiţii, vom crea un choice în care fiecare element poate apărea de minim 0 ori şi maxim unbounded

Page 20: uia hatz

Tipul complex vid cu atributeComplex vid cu atribute = poate avea atribute dar nu și conţinut textual sau copii:<xs:complexType name="DescriereTelevizor">

<xs:attribute name="Diagonala" type="xs:integer"/><xs:attribute name="Producator" type="xs:string"/>

</xs:complexType><xs:element name="Televizor" type="DescriereTelevizor"/>

Exemplu de element valid:<Televizor Diagonala="122" Producator="Samsung"/>

Page 21: uia hatz

Reutilizarea tipurilor• Tipurile pot fi reutilizate dacă primesc nume:<xs:complexType name="DescriereTelevizor">

<xs:attribute name="Diagonala" type="xs:integer"/><xs:attribute name="Producator" type="xs:string"/>

</xs:complexType><xs:element name="Televizor" type="DescriereTelevizor"/>

Reutilizare poate însemna:• Diferite elemente, chiar cu nume diferite, vor putea căpăta aceeași structură• Tipul va putea fi derivat în alte tipuri înrudite

Dacă nu primesc nume, tipurile sunt considerate anonime, nu pot fi moștenite/derviate și se aplică doar elementului în care s-au definit (mai jos, doar elementul are nume, nu și tipul!):<xs:element name="ModelTelevizor"><xs:complexType><xs:simpleContent>

<xs:extension base="xs:string"><xs:attribute name="Diagonala" type="xs:integer"/></xs:extension>

</xs:simpleContent></xs:complexType></xs:element>

Page 22: uia hatz

Tipul complex cu conţinut derivatE vorba aici de derivarea unui tip complex din alt tip complex (prin adăugare de copii și/sau atribute). Pornind de la definiţia la DescriereTelevizor din slide-ul precedent, realizăm un nou tip adăugând elementul copil StocCurent (sequence e necesar chiar și pentru un singur copil!) și atributul obligatoriu Pret:

<xs:element name="TelevizorPeStoc"><xs:complexType>

<xs:complexContent><xs:extension base="DescriereTelevizor">

<xs:sequence> <xs:element name="StocCurent" type="xs:integer"/> </xs:sequence>

<xs:attribute name="Pret" type="xs:integer" use="required"/></xs:extension>

</xs:complexContent></xs:complexType>

</xs:element>Exemplu de element valid (Diagonala lipsește deoarece e moștenită de la DescriereTelevizor, unde e opţională!):<TelevizorPeStoc Pret="1000" Producator="Samsung"><StocCurent>200</StocCurent></TelevizorPeStoc>

Page 23: uia hatz

"Chei primare" în XML Schema• În vocabulare DTD există un mod simplu de a defini chei

primare: atribute de tip ID, ce vor trebui să aibă valori unice în documentul în care se află– Ca și în bazele de date, la cheile primare se pot face referinţe

dinspre cheile străine aflate altundeva (atribute de tip IDREF)– Hyperlinkurile din HTML nu sunt altceva decât astfel de referinţe

spre chei primare (HREF e un atribut de tip IDREF, iar ID e un atribut de tip ID)

• XML Schema îmbogăţește aceste posibilităţi prin:– Chei multivaloare = Când unicitatea se aplică unei combinaţii de

atribute și noduri text– Chei cu unicitate limitată = Când unicitatea trebuie respectată

doar în interiorul unui marcator, nu neapărat în tot documentul

Page 24: uia hatz

Exemplu cheie multivaloare<xs:element name="CatalogProduse" type="Catalog"><xs:unique name="cheie">

<xs:selector xpath="produs"/><xs:field xpath="denumire"/><xs:field xpath="@model"/>

</xs:unique"></xs:element>• S-a creat o cheie primară (unique), cu numele cheie;• Unicitatea sa se verifică doar în interiorul elementului CatalogProduse• Cheia se aplică tuturor elementelor produs și e formată din perechea

(denumire, model), unde denumirea apare în produs ca element-copil, iar modelul ca atribut (s-au folosit căi Xpath relative!)

Combinaţia de valori care trebuie să fie unicăPentru fiecare "înregistrare"

"Înregistrările" ce trebuie să aibă fiecarecombinaţia unică

"Tabelul" în care trebuie asigurată unicitatea

Page 25: uia hatz

Exemplu de instanţă validă:<CatalogProduse><produs model="M1">

<denumire>yyyyyyyy</denumire></produs><produs model="M1">

<denumire>zzzzzz</denumire></produs>…………………………….</CatalogProduse><produs model="M1">

<denumire>yyyyyyyy</denumire></produs>...............................

Perechea trebuie să fie unică, nu fiecare din cele două valori luată separat!

Unicitatea e impusă doar în CatalogProduse, în afară perechea se poate repeta

Page 26: uia hatz

Exemplu de chei străineîntre “tabele” XML

<xs:element name="Produse"><xs:element name="ProduseCatalog">……..aici undeva e definit elementul-copil produscare are la rândul său copilul cod</xs:element>

<xs:element name="ProdusePeStoc"> ……..aici undeva e definit elementul-copil produscare are atributul codItem</xs:element>

<xs:unique name="cheie"><xs:selector xpath="ProduseCatalog/produs"/><xs:field xpath="cod"/>

</xs:unique"><xs:keyref name="referinta" refer="cheie">

<xs:selector xpath="ProdusePeStoc/produs"/><xs:field xpath="@codItem"/>

</xs:keyref>

</xs:element>

Se declară că produsele din catalog au cheia primară în copilul cod

Se definește un "tabel" care conţine o listă de produse prezente în catalog, fiecare produs are un cod unic sub forma unui element copil

Se declară că produsele din al doilea "tabel", au cheia străină atributul codItem (deci valorile acestui atribut trebuie alese dintre valorile cheii primare, evitând astfel repetarea tuturor informaţiilor despre produse!)

Se definește (în același document!) al doilea "tabel" cu produse pe stoc, fiecare identificat de un atribut codItem

Page 27: uia hatz

Exemplu valid<Produse><ProduseCatalog>

<produs producator="Samsung" tip="Televizor"><cod>P1</cod></produs><produs producator="Samsung" tip="Frigider"><cod>P2</cod></produs><produs producator="Apple" tip="Telefon"><cod>P3</cod></produs>

</ProduseCatalog><ProdusePeStoc>

<produs codItem="P1" bucati="10" pret="100"/><produs codItem="P3" bucati="1" pret="50"/>

</ProdusePeStoc></Produse>

Nu putem avea pe stoc produse pe care nu le avem în catalog!În schimb nu orice produs din catalog trebuie să fie pe stocÞ Valorile cheii străine trebuie alese dintre cele ale cheii primareÞ Nu mai suntem nevoiţi să repetăm detaliile produselor (producator, tip)!

Page 28: uia hatz

Modularizarea documentelorXML Schema permite ca un document să conţină marcatori din mai multe vocabulare (ceea ce duce la validare multiplă, faţă de mai multe vocabulare simultan).

Pentru evitarea conflictelor de nume, un prefix trebuie să indice vocabularul căruia aparţine fiecare element:

<v1:catalog xmlns:v1="http://organizatie1.com/vocabular1"><v1:produs v1:denumire="Ipod" v1:pret="300 RON"/>

</v1:catalog>

<v2:produs v2:ID="P001" xmlns:v2="http://organizatie2.com/vocabular2" ><v2:pret>500 RON</v2:pret>

</v2:produs>

În aceste exemplu, presupunând că apar în același document, avem două utilizări diferite ale marcatorului produs:

• Prima e conformă cu vocabularul v1, ce prevede ca produsul să aibă atributele denumire și pret, și să fie încadrat într-un element catalog

• Al doilea e conform cu vocabularul v2, ce prevede ca produsul să aibă atributul ID și să conţină preţul ca element fiu

Page 29: uia hatz

ModularizareaPrefixele v1: și v2: atașate fiecărui marcatori indică faptul că aceștia trebuie validaţi după reguli diferite, prezente în vocabulare diferite:• Fiecare din cele două vocabulare are un identificator universal (URI, unic în Internet,

numit și spaţiu de nume)• Identificatorii universali încep cu adrese de domeniu ale organizaţiilor care au creat

vocabularele (organizatie1.com și organizatie2.com) urmate de numele vocabularelor• Cum adresele de domeniu sunt unice în Internet (și controlate), ele vor elimina

ambiguitatea. Prefixele v1 și v2 sunt de fapt abrevieri ale identificatorilor; fără prefixe, ar trebui să indicăm provenienţa prin construcţii mai incomode, care e posibil să conţină caractere nepermise – ceva în genul:

<http://organizatie1.com/vocabular1/catalog><http://organizatie1.com/vocabular1 /produs http://organzitatie1.com/vocabular1/denumire="Ipod"http://organtizatie1.com/vocabular1/pret="300 RON"/>

</http://organizatie1.com/vocabular1/catalog>

Prefixul poate lipsi pentru UNUL din vocabularele folosite în document (considerat "principal", default). De exemplu în HTML puteţi întâlni adesea declararea vocabularului, fără a-i mai asocia un prefix (pentru a nu fi nevoiţi să prefixăm totul!)

<html xmlns="http://www.w3.org/1999/xhtml">

Page 30: uia hatz

Crearea identificatorilor de vocabularCând se creează un vocabular cu XML Schema, trebuie să i se definească acest identificator:

<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema"targetNamespace="http://organizatia-mea.com/vocabularul-

meu">.....regulile vocabularului….</xs:schema>

Observaţi cum însăși limbajul XML Schema e un vocabular XML!

De aceea toate "instrucţiunile" XML Schema au prefixul xs (locţiitor pentru identificatorul universal definit de Consorţiul w3.org pentru acest limbaj)

Page 31: uia hatz

Modularizarea vocabularelorPutem crea vocabulare XML Schema noi preluând elemente din vocabulare existente!

Tehnica prin includere:<xs:schema xmlns:xs="..." targetNamespace="...">

<xs:include schemaLocation="VocabularVechi.xsd" />……………………………………

</xs:schema>

Condiţie: vocabularul vechi să nu aibă identificator (targetNamespace) sau să aibă același identificator.În caz de conflict de nume, se preiau marcatorii/atributele din vocabularul vechi

Page 32: uia hatz

Modularizarea vocabularelorTehnica prin redefinire:<xs:schema xmlns:xs="..." targetNamespace="...">

<xs:redefine schemaLocation="VocabularVechi.xsd" />……………………………………</xs:schema>

În caz de conflict de nume, se păstrează elementele și atributele din noul vocabular.

Tehnica prin import:<xs:schema xmlns:xs="..." targetNamespace="http://organizatia-mea.com/vocabularul-meu"><xs:import schemaLocation="http://alta-organizatie.com/VocabularVechi.xsd" namespace="http://alta-

organizatie.com/alt-vocabular" />……………………………………</xs:schema>• În acest caz se permite ca noul vocabular să aibă un identificator (targetNamespace) diferit de al

vocabularului importat (namespace). Tehnica se aplică dacă importăm vocabulare de la alte organizaţii, asupra cărora nu deţinem controlul (nu le putem prelua identificatorul).

• Evident, în acest caz nu pot apare conflicte de nume (documentele vor folosi prefixe diferite)• Remarcaţi și că identificatorul unui vocabular nu trebuie să fie identic cu adresa la care s-a salvat fișierul .xsd

al acelui vocabular ! (identificatorii sunt un fel de denumiri sau ID-uri, chiar dacă arată ca niște adrese!)

Page 33: uia hatz

Exemplu de situaţie în care e utilă modularizarea

Problemă• Dorim să avem un vocabular pentur Facturi• Factura e un document eterogen care conţine informaţii

despre mai multe entităţi: produse, client, vânzător• E posibil să avem deja vocabulare care impun cum trebuie

descris clientul sau vânzătorulSoluţie:• Fie folosim în aceeași factură marcatori prefixaţi din mai

multe vocabulare, și validăm fiecare marcator după alt vocabular

• Fie creăm un vocabular nou în care le includem/importăm pe celelalte, apoi validăm facturile faţă de noul vocabular

Page 34: uia hatz

Exemplu de situaţie în care e utilă modularizarea

Se ridică dilema:Cât de fragmentate să fie vocabularele? Facem un vocabular pentru Facturi, sau vocabulare mai mici pentru Produse, Client, Vânzător etc.?

Tehnici consacrate:• Fragmentare după entităţi:

– Așa cum la bazele de date relaţionale se creează un tabel pe entitate, se poate crea și un vocabular XML pentru fiecare entitate

• Fragmentare după frecvenţa folosirii:– Un vocabular cu toate elementele/atributele obligatorii din factură și altul care le adaugă și pe

cele opţionale– Documentele vor putea fi validate faţă de primul sau faţă de al doilea, în funcţie de cât de

detaliate sunt!• O combinaţie între cele două tehnici:

– Un vocabular cu elementele/atributele sintetice (structura generală, totaluri) și altele pentru detalii corespunzătoare fiecărei entităţi (unul pentru lista de produse, altul pentru informaţiile despre client/vânzător)

– Diferite fragmente ale unui document se vor valida după vocabulare diferite.

Page 35: uia hatz

Cerinţe pentru vocabulareÎn general în proiectarea vocabularelor trebuie să ţinem cont de:• posibilele utilizări ale documentelor, cum vor fi ele procesate mai departe (dacă vor fi preluate de

alte sisteme ce au nevoie de un anumit grad de detaliere)• performanţăÎn acest sens, am discutat la început distincţia între diferite structuri de elemente: <Produs>

<Denumire>Televizorul <Denumire> costa <Pret>300</Pret><Moneda>RON</Moneda></Produs>Date uşor de găsit, dar performanţă slabă şi vocabular complicat datorită numărului mare de elemente

<Produs>Televizorul costa 300 RON</Produs>Date greu de găsit, dar afişare facilă şi vocabular uşor de creat

<Produs>Televizorul costa <Pret>300 RON</Pret></Produs>Vocabular complicat, unele date sunt mai uşor de extras decât altele (similar cu HTML!)

<Produs Denumire="Televizor" Pret="300" Moneda="RON" />Date uşor de găsit, performanţă optimă, vocabular de complexitate medie, însă dificil de construit mesaje textuale din dateMajoritatea bazelor de date relaţionale pot exporta structuri de acest tip din tabele!

Page 36: uia hatz

Standardul XSLStandardul XSL: set de standarde specializate pe manipularea documentelor XML• manipulare structurală – modificarea arborelui DOM• manipulare de format – formatare cu stiluri (similar CSS)

Componentele pachetului XSL sunt:• Xpath – interogarea arborelui DOM prin cale (alternativă mai

puternică la selectorii CSS!) – s-a studiat deja• XSLT – transformarea unui arbore DOM într-un document

oarecare ce trebuie să conţină unele informaţii din arborele iniţial (poate converti XML în alt XML, dar și în HTML ori text simplu) – îl studiem în acest curs

• XSL-FO – formatarea unui arbore DOM cu "șabloane de pagini" (stiluri, vag asemănătoare cu CSS), de obicei în scopul obţinerii unui document PDF – se va omite în acest curs, căci nu are o relevanţă directă

Page 37: uia hatz

Elemente de XSLT•transformă un document XML în alt document (nu neapărat tot XML), folosindu-se de XPath pentru a manipula arborele DOM• folosește reguli de substituire, formate din două componente:

– Componenta de înlocuit (accesată prin Xpath, devine nod curent pentru orice căi Xpath ce apar în interiorul regulii);

– Componenta de inserat (o combinaţie de marcatori si instrucţiuni XSLT) – poate lipsi, caz în care are loc ștergere!

<xsl:template match="calea Xpath a elementelor ce trebuie substituite">... elementele de inserat şi/sau alte instrucţiuni XSLT ...

</xsl:template>Exemplu (substituie orice element produs cu un paragraf HTML):<xsl:template match="//produs">

<p>S-a gasit un produs</p></xsl:template>

Toate regulile de substituire se enumeră într-o rădăcină xsl:stylesheet (deci XSLT este un vocabular XML!):<xsl:stylesheet>

<xsl:template>…regula1...</xsl:template><xsl:template>…regula2...</xsl:template><xsl:template>…regula3...</xsl:template>

</xsl:stylesheet>

Page 38: uia hatz

Reguli de ștergere• Sunt acele reguli care nu conţin nimic în interiorul lor (practic e

vorba de substituire cu șirul vid)• Şterge toate nodurile text din document:<xsl:template match="text()"/>

• Şterge toate nodurile invizibile (formate din spaţii, Tab, Enter):<xsl:template match="text()[normalize-space(.)='']"/>(se poate realiza și altfel, cu instrucţiunea dedicată xsl:strip-space)

• Şterge toate elementele produs din document:<xsl:template match="//produs"/>

• Atenţie: adesea nu trebuie să creăm reguli de ștergere, din cauza regulilor implicite care aplică unele ștergeri (slide-ul următor)

Page 39: uia hatz

Reguli impliciteR1. Dacă mai multe reguli accesează același nod, se aplică regula cea mai specifică (cu interogarea XPath cea mai ţintită). De exemplu...

//produs[@pret!=''] e mai ţintită decât //*R2. Toate nodurile care NU sunt afectate de nicio regulă de substituire sunt eliminate, cu excepţia nodurilor text!

• Din acest motiv, un fișier care conţine în rădăcină DOAR regula de mai jos...<xsl:template match="text()"/>... va goli tot documentul sursă! Deși această regulă se ocupă doar de ștergerea nodurilor text, elementele/atributele se elimină datorită regulii implicite (R2).

• Din același motiv, un fișier XSLT care își conţine DOAR rădăcina, fără nicio regulă definită....

<xsl:stylesheet></xsl:stylesheet>... va extrage din documentul sursă tot textul, eliminând marcatorii și atributele lor! Așadar prin regula implicită XSLT ne oferă un mecanism rapid de extragere a conţinutului textual dintr-un document.

Page 40: uia hatz

Reguli de conservareDin cauza regulilor implicite, trebuie să specificăm explicit când dorim să păstrăm anumite porţiuni din documentul original, prin crearea unor reguli de conservare:• xsl:copy-of se folosește pentru a crea copia identică a unui element din sursă• xsl:copy se folosește pentru a crea o copie goală (fără atribute și conţinut) a unui element, căreia să i

se aplice apoi diverse modificări

Regula de conservare cea mai generală, care realizează o copie a întregului document original (de fapt o copie a rădăcinii, cu tot ce conţine aceasta):<xsl:template match="/"> <xsl:copy-of select="."/></xsl:template>Regula de conservare a unui singur element, cu tot conţinutul și atributele sale:<xsl:template match="produs">

<xsl:copy-of select="." /></xsl:template>Regula de conservare a unui marcator, dar fără conţinut și atribute (acestea pot fi redefinite sau filtrate în interiorul lui xsl:copy!):<xsl:template match="produs">

<xsl:copy/></xsl:template>

Page 41: uia hatz

Reguli în cascadăCu xsl:apply-templates regulile pot apela alte reguli în cascadă. Exemplu:

<xsl:template match="/comanda"> <xsl:copy> <xsl:attribute name="AtributNou">ValoareaNoua</xsl:attribute> <xsl:apply-templates/> </xsl:copy></xsl:template> <xsl:template match="produs"> <xsl:copy> <CopilNou>TextNou</CopilNou> <xsl:apply-templates/> </xsl:copy></xsl:template>

Pas4. Se caută noi reguli pentru conţinutul produselor.Nu se găsesc, așa că se aplică regula implicită:se păstrează numele produselor, dar fără marcator!

Pas2. xsl:apply-templates caută ce alte reguli mai există pentru copiii comenzii. Se găsește a doua.

Sursa:<comanda client="Pop Ioan"> <produs pret="100"><nume>Telefon</nume></produs> <produs pret="200"><nume>Frigider</nume></produs></comanda>

Rezultat:<comanda AtributNou="TextNou"> <produs><CopilNou>TextNou</CopilNou>Telefon</produs> <produs><CopilNou>TextNou</CopilNou>Frigider</produs></comanda>

Pas1. Se realizează o copie goală a rădăcinii comanda,la care se creează nu atribut nou

Pas3. Se realizează o copie goală a fiecărui produs, și i se inserează un copil nou

Page 42: uia hatz

Reguli recursiveAcestea sunt reguli care se apelează pe sine, dinspre rădăcină spre frunze. Regula de mai jos realizează o copie a documentului original, din care elimină atributele (deci avem o regulă de conservare parţială!)<xsl:template match="node()"> <xsl:copy> <xsl:apply-templates/> </xsl:copy> </xsl:template>

Următorul exemplu realizează tot o conservare parţială, de data aceasta păstrând atributele și eliminând nodurile text. Regula recursivă aplică acum copiere recursivă nu doar pe noduri, ci și pe toate atributele (@*):<xsl:template match="node()|@*"> <xsl:copy> <xsl:apply-templates select="node()|@*"/> </xsl:copy></xsl:template><xsl:template match="text()"/>Eliminarea nodurilor text e realizată de ultima linie. În absenţa ei, avem de fapt o regulă de conservare completă (același rezultat cu xsl:copy-of!) Recursivitatea compensează faptul că se copiază marcatorii fără conţinut.

Aici xsl:apply-templates caută ce alte reguli mai sunt disponibilepentru copiii nodului curent și reaplică recursiv aceeași regulă, deoarece și copiii corespund interogării node(). Pentru fiecare nod găsit se realizează o copie goală => atributele se pierd, însă conţinuturile vor rămâne datorită copierii treptate (recursive) a tuturor nodurilor

Page 43: uia hatz

Redenumire și ștergereSursa:<produs pret="200" garantie="3 ani"> Imprimanta HP100</produs>Rezultat:<prod pretunitar="200">Imprimanta HP100</prod>Regula:<xsl:template match="produs"><prod pretunitar="{@pret}">

<xsl:apply-templates/></prod></xsl:template>

Caută toate elementele <produs>

Le înlocuiește cu elemente <prod>, dotate cu atributul pretunitar, care-și primește valoarea de la atributul pret (extras din sursă)

Aplică alte reguli (dacă există) pentru fiii elementului produs. Cum nu există, se aplică regula implicită care păstrează textul din elementul original

Regula nu indică nimic pentru atributul garanţie, deci acesta va dispărea (tot datorită regulii implicite)!

Page 44: uia hatz

Conversie element-atribut și inversSursa:<produs pret="200"><garantie>3 ani</garantie></produs>Rezultat:<produs garantie="3 ani"><pret>200</pret></produs>Regula:<xsl:template match="produs"><produs garantie="{garantie}"><pret>

<xsl:value-of select="@pret"/></pret></xsl:template>

Caută toate elementele <produs>Adaugă atribute garantie, cu valoarea extrasă de la elementele <garantie>Adaugă elemente-fiu <pret>, cu valoarea extrasă de la atributul pret

Page 45: uia hatz

Structuri de programare, generare de cod HTML

<xsl:template match="/comanda"><ol><xsl:for-each select="produs">

<xsl:if test="@pret"><li>Pretul pentru <xsl:value-of select="@nume"/>este<xsl:value-of select="@pret"></li></xsl:if>

</xsl:for-each></ol></xsl:template>

Pas1.Parcurge comanda (for-each)Pas2.Creează stringul Pretul pentru X este Y!, pentru acele produse la care se găsește atributul pret (cu X și Y extrase din atribute existente în documentul original).Pas3.Stringurile obţinute sunt formatate ca elemente de listă HTML (OL, LI)

IF-ul se poate evita dacă punem în select-ul ciclului FOR direct produs[@pret], pasând astfel responsabilitatea testării existenţei preţului spre Xpath!

Page 46: uia hatz

Versatilitatea XSLT

• Funcţia de bază: generarea de documente noi din datele prezente într-un arbore DOM=> poate juca rolul limbajului PHP, dacă se generează cod HTML dintr-o "bază de date" XML

• Funcţie secundară: limbaj de interogare:=> dacă, în loc de substituiri are loc doar copierea unor fragmente (după anumite condiţii), avem un mod de a realiza interogări, mai sofisticat decât ce poate XPath!