Professional Documents
Culture Documents
24/1/2002
11:08
Page 1
16 captulo 16
24/1/2002
11:08
Page b
16 captulo 16
24/1/2002
11:08
Page 1
16
Trabajar con datos XML
en SQL Server 2000
SQL Server 2000 puede usar protocolos y estndares propios de Internet
para comunicarse con otras aplicaciones y otros sistemas. El lenguaje
extensible de marcacin, o XML (eXtensible Markup Language) es el
formato estndar de facto para la comunicacin entre aplicaciones en
Internet.
En este captulo aprenderemos de qu manera SQL Server usa las
tecnologas de la Web y XML para proveer una comunicacin independiente
de la plataforma. Ser solamente una introduccin a este tema amplio y
muy difundido; para una discusin ms completa del funcionamiento de
XML en general remitimos al lector a algn libro sobre XML, por ejemplo el
de Benot Marchal, XML con Ejemplos. En este captulo aprenderemos lo
siguiente:
Los conceptos bsicos de XML
Cmo leer datos en formato XML en SQL Server 2000
El uso de documentos XML en Transact-SQL
Cmo acceder a SQL Server a travs de HTTP
El uso de updategrams XML para modificar, insertar y eliminar datos
en SQL Server
16 captulo 16
24/1/2002
11:08
Page 2
<Products>
<Product ProductID=1 ProductName=Chai UnitPrice=18.0000/>
<Product ProductID=2 ProductName=Chang UnitPrice=19.0000/>
<Product ProductID=3 ProductName=Aniseed Syrup UnitPrice=10.0000/>
</Products>
16 captulo 16
24/1/2002
11:08
Page 3
En el documento XML del listado 16.1 podemos ver diferentes secciones. La etiqueta
que sigue es una instruccin para el procesador que identifica el documento como
documento XML, adems de la versin de XML usada:
<xml? version=1.0 ?>
La etiqueta siguiente identifica el elemento raz descrito por este documento. Todo
documento XML bien formado debe tener un elemento raz. Este documento
describe productos:
<Products>
Cada una de las lneas siguientes describe un elemento en particular (un producto,
en este caso) e indica tres atributos para cada producto: ProductID, ProductName y
UnitPrice (el identificador, el nombre y el precio unitario, respectivamente). Para
cada atributo, el documento indica el nombre del atributo y el valor que tiene ese
atributo para cada producto en particular. El smbolo / al final de cada lnea
representa el final de la definicin del elemento individual. En este caso es una
simplificacin de la sintaxis formal </Product>.
<Product ProductID=1 ProductName=Chai UnitPrice=18.0000/>
<Product ProductID=2 ProductName=Chang UnitPrice=19.0000/>
<Product ProductID=3 ProductName=Aniseed Syrup UnitPrice=10.0000/>
Al final del documento XML, debe haber una etiqueta de cierre que marque el fin
de la definicin del elemento raz.
</Products>
PRECAUCIN
Observe que en XML se distingue entre maysculas y minsculas. Si la etiqueta de inicio
de un elemento y la de cierre no coinciden en el uso de maysculas y minsculas, se producir
un error de sintaxis de XML. Por ejemplo, el listado 16.2 produce el mensaje de error que
aparece en la salida incluida. La nica diferencia entre el listado 16.1 y el 16.2 es que en este
ltimo la etiqueta de cierre </products> empieza con minsculas y la etiqueta de inicio con
maysculas; la etiqueta de cierre debera haber sido </Products>.
16 captulo 16
24/1/2002
11:08
Page 4
<Products>
<Product ProductID=1 ProductName=Chai UnitPrice=18.0000/>
<Product ProductID=2 ProductName=Chang UnitPrice=19.0000/>
<Product ProductID=3 ProductName=Aniseed Syrup UnitPrice=10.0000/>
</products>
SALIDA
EJEMPLO
16 captulo 16
24/1/2002
11:08
Page 5
EJEMPLO
<Customers>
<Customer CompanyName=Victuailles en stock>
<Order Date=1996-07-08>
<Product Name=Gustafaposs Knackebrod Price=16.8000 Quantity=6/>
<Product Name=Ravioli Angelo Price=15.6000 Quantity=15/>
<Product Name=Louisiana Fiery Hot Pepper Sauce Price=16.8000
Quantity=20/>
</Order>
<Order Date=1996-10-21>
<Product Name=Filo Mix Price=5.6000 Quantity=8/>
<Product Name=Scottish Longbreads Price=10.0000 Quantity=10/>
</Order>
<Order Date=1997-02-19>
<Product Name=Ikura Price=24.8000 Quantity=20/>
<Product Name=Tourtiere Price=5.9000 Quantity=6/>
</Order>
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
24/1/2002
11:08
Page 6
16 captulo 16
24/1/2002
11:08
Page 7
16 captulo 16
24/1/2002
11:08
Page 8
Customer
Victuailles
en stock
Customers
Customer
Vins and Alcohols
Chevalier
Order 1996-07-08
Order 1996-10-21
Order 1997-02-19
Order 1997-02-27
Order 1997-03-18
Order 1997-05-23
Order 1997-12-31
Order 1996-07-04
Order 1996-08-06
Order 1996-09-02
Order 1997-11-11
Order 1997-11-12
{
{
{
{
{
{
{
{
{
{
{
{
Product Gustaf...
Product Ravioli...
Product Louisiana...
Product Filo...
Product Scottish...
Product Ikura
Product Tourtiere
Product Uncle...
Product Spegesild...
Product Mozzare...
Product Ikura
Product Uncle...
Product Steeleye...
Product Tarte...
Product Chang
Product Louisiana...
Product Longlife...
Product Queso...
Product Singap...
Product Mozzare...
Product Flotem...
Product Mozzare...
Product Gnocchi...
Product Konbu
Product Jack...
Product Inglad...
Product Filo...
16 captulo 16
24/1/2002
11:08
Page 9
apropiado. El listado define una hoja de estilo pensada para aplicarle un formato
al documento del listado 16.1. El listado 16.6 muestra el documento del listado
16.1, con una referencia al archivo XSL. La figura 16.5 muestra cmo se ve la
salida formateada en Internet Explorer.
EJEMPLO
<xsl:stylesheet xmlns:xsl=http://www.w3.org/TR/WD-xsl>
<xsl:template match=/>
<HTML>
<Title>Lista de productos</Title>
<Body>
<Table border=0>
<TR><TD>Producto</TD><TD>Nombre</TD><TD>Precio</TD></TR>
<xsl:for-each select=Products/Product>
<TR>
<TD><xsl:value-of select=@ProductID/></TD>
<TD><xsl:value-of select=@ProductName/></TD>
<TD><xsl:value-of select=@UnitPrice/></TD>
</TR>
</xsl:for-each>
</Table>
</Body>
</HTML>
</xsl:template>
</xsl:stylesheet>
16 captulo 16
10
24/1/2002
11:08
Page 10
De esta manera se puede cambiar fcilmente la apariencia de un sitio Web por completo,
sin afectar la lgica de la programacin o los datos disponibles en los archivos XML.
Lista de productos
Producto Nombre
Precio
Chai
18.000
Chang
19.000
16 captulo 16
24/1/2002
11:08
Page 11
11
EJEMPLO
<xsl:stylesheet xmlns:xsl=http://www.w3.org/TR/WD-xsl>
<xsl:template match=/>
<HTML>
<HEAD>
<Title>Lista de productos</Title>
<STYLE>
.subject {
font-family: Garamond;
font-weight: bold;
font-size: 48;
}
.headings {
font-family: Garamond;
font-weight: bold;
font-size: 24;
}
.productname {
font-family: Garamond;
font-weight: bold;
font-size: normal;
}
</STYLE>
</HEAD>
<Body>
<Table>
<TR>
<TD CLASS=subject>Lista de productos</TD>
</TR>
</Table>
<Table border=1>
<TR>
<TD CLASS=headings>Producto</TD>
<TD CLASS=headings>Nombre</TD>
<TD CLASS=headings>Precio</TD>
</TR>
<xsl:for-each select=Products/Product>
<TR>
<TD><xsl:value-of select=@ProductID/></TD>
<TD CLASS=productname><xsl:value-of select=@ProductName/></TD>
<TD><xsl:value-of select=@UnitPrice/></TD>
</TR>
</xsl:for-each>
</Table>
</Body>
</HTML>
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
12
24/1/2002
11:08
Page 12
El estudio de las posibilidades que ofrece este lenguaje poderoso y a la vez simple
est ms all del alcance de este libro. Puede aprender ms acerca de XML con el
libro XML by Example (Benot Marchal, QUE, ISBN 0-7897-2242-9).
16 captulo 16
24/1/2002
11:09
Page 13
13
Traduccin de updategrams XML a las correspondientes instrucciones TransactSQL INSERT, DELETE y UPDATE.
En las secciones que siguen aprenderemos acerca del uso de estas nuevas prestaciones.
Como ya hemos mencionado, esto no es ms que una introduccin a esta tecnologa
extremadamente amplia. Los ejemplos contenidos en este captulo estn pensados
para guiar al lector a travs de las primeras etapas de su aventura con XML.
16 captulo 16
14
24/1/2002
11:09
Page 14
PRECAUCIN
Ajuste la cantidad mxima de caracteres por columna en el analizador de consultas a un valor
mayor que 2.033, o algunos de los ejemplos de esta seccin saldrn cortados.
Para ajustar esta opcin puede ir a Herramientas, Opciones y entrar a la ficha Resultados.
16 captulo 16
24/1/2002
11:09
Page 15
15
Listado 16.9: La salida de una consulta que us la clusula FOR XML, luego de formatearla manualmente
EJEMPLO
<Categories
CategoryID=1
CategoryName=Beverages
Description=Soft drinks, coffees, teas, beers, and ales/>
<Categories
CategoryID=2
CategoryName=Condiments
Description=Sweet and savory sauces, relishes, spreads, and seasonings/>
<Categories
CategoryID=3
CategoryName=Confections
Description=Desserts, candies, and sweet breads/>
<Categories
CategoryID=4
CategoryName=Dairy Products
Description=Cheeses/>
<Categories
CategoryID=5
CategoryName=Grains/Cereals
Description=Breads, crackers, pasta, and cereal/>
<Categories
CategoryID=6
CategoryName=Meat/Poultry
Description=Prepared meats/>
<Categories
CategoryID=7
CategoryName=Produce
Description=Dried fruit and bean curd/>
<Categories
CategoryID=8
CategoryName=Seafood
Description=Seaweed and fish/>
16 captulo 16
16
24/1/2002
11:09
Page 16
EJEMPLO
<CategoryList>
<Categories
CategoryID=1
CategoryName=Beverages
Description=Soft drinks, coffees, teas, beers, and ales/>
<Categories
CategoryID=2
CategoryName=Condiments
Description=Sweet and savory sauces, relishes, spreads, and seasonings/>
<Categories
CategoryID=3
CategoryName=Confections
Description=Desserts, candies, and sweet breads/>
<Categories
CategoryID=4
CategoryName=Dairy Products
Description=Cheeses/>
<Categories
CategoryID=5
CategoryName=Grains/Cereals
Description=Breads, crackers, pasta, and cereal/>
<Categories
CategoryID=6
CategoryName=Meat/Poultry
Description=Prepared meats/>
16 captulo 16
24/1/2002
11:09
Page 17
17
Sin embargo, se pueden usar alias para producir una salida que mejore los
nombres de los elementos, como en la consulta del listado 16.11. Una convencin
de nombres que mejorara la legibilidad sera usar el nombre de la tabla en
singular para denominar cada elemento.
Como ejemplo podemos usar el alias Category para la tabla Categories, de modo
que cada elemento de la salida XML lleve el nombre Category. El listado 16.12
muestra la salida, despus de agregar el nodo raz Categories para completar el
fragmento XML producido por esta consulta.
Listado 16.11: Uso de alias de tabla y de columna para mejorar el uso de nombres en la salida XML
USE Northwind
GO
EJEMPLO
SALIDA
<Categories>
<Category
ID=1
Name=Beverages
Description=Soft drinks, coffees, teas, beers, and ales/>
<Category
ID=2
Name=Condiments
Description=Sweet and savory sauces, relishes, spreads, and seasonings/>
<Category
ID=3
Name=Confections
Description=Desserts, candies, and sweet breads/>
<Category
ID=4
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
18
24/1/2002
11:09
Page 18
El listado 16.13 muestra la misma consulta que el 16.11, pero en modo RAW, con su
salida no formateada. Como puede apreciar en la salida, la principal diferencia
est en el nombre de los elementos, que en este caso siempre es row.
Listado 16.13: Uso de FOR XML RAW para producir resultados en formato XML
USE Northwind
GO
EJEMPLO
16 captulo 16
24/1/2002
11:09
Page 19
19
SALIDA
XML_F52E2B61-18A1-11d1-B105-00805F49916B
-------------------------------------------------<row ID=1 Name=Beverages
Description=Soft drinks, coffees, teas, beers, and ales/>
<row ID=2 Name=Condiments
Description=Sweet and savory sauces, relishes, spreads, and seasonings/>
<row ID=3 Name=Confections
Description=Desserts, candies, and sweet breads/>
<row ID=4 Name=Dairy Products
Description=Cheeses/><row ID=5 Name=Grains/Cereals
Description=Breads, crackers, pasta, and cereal/>
<row ID=6 Name=Meat/Poultry Description=Prepared meats/>
<row ID=7 Name=Produce Description=Dried fruit and bean curd/>
<row ID=8 Name=Seafood Description=Seaweed and fish/>
(8 filas afectadas)
Sin embargo, si la instruccin SELECT lee datos de ms de una tabla hay una gran
diferencia entre cmo trabajan los modos RAW y AUTO. El listado 16.14 muestra la
misma consulta en ambos formatos, con sus correspondientes salidas.
Listado 16.14: Comparacin de los modos RAW y AUTO cuando se ejecutan consultas sobre varias tablas
USE Northwind
GO
EJEMPLO
SELECT CategoryName,
ProductName
FROM Categories as Category
JOIN Products as Product
ON Product.CategoryID = Category.CategoryID
WHERE Product.CategoryID < 3
ORDER BY CategoryName, ProductName
FOR XML RAW
SELECT CategoryName,
ProductName
FROM Categories as Category
JOIN Products as Product
ON Product.CategoryID = Category.CategoryID
WHERE Product.CategoryID < 3
ORDER BY CategoryName, ProductName
FOR XML AUTO
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
20
24/1/2002
11:09
Page 20
SALIDA
XML_F52E2B61-18A1-11d1-B105-00805F49916B
-----------------------------------------------<row CategoryName=Beverages ProductName=Chai/>
<row CategoryName=Beverages ProductName=Chang/>
<row CategoryName=Beverages ProductName=Chartreuse verte/>
<row CategoryName=Beverages ProductName=Cte de Blaye/>
<row CategoryName=Beverages ProductName=Guaran Fantstica/>
<row CategoryName=Beverages ProductName=Ipoh Coffee/>
<row CategoryName=Beverages ProductName=Lakkalikri/>
<row CategoryName=Beverages ProductName=Laughing Lumberjack Lager/>
<row CategoryName=Beverages ProductName=Outback Lager/>
<row CategoryName=Beverages ProductName=Rhnbru Klosterbier/>
<row CategoryName=Beverages ProductName=Sasquatch Ale/>
<row CategoryName=Beverages ProductName=Steeleye Stout/>
<row CategoryName=Condiments ProductName=Aniseed Syrup/>
<row CategoryName=Condiments
ProductName=Chef Anton's Cajun Seasoning/>
<row CategoryName=Condiments ProductName=Chef Anton's Gumbo Mix/>
<row CategoryName=Condiments ProductName=Genen Shouyu/>
<row CategoryName=Condiments
ProductName=Grandma's Boysenberry Spread/>
<row CategoryName=Condiments ProductName=Gula Malacca/>
<row CategoryName=Condiments
ProductName=Louisiana Fiery Hot Pepper Sauce/>
<row CategoryName=Condiments ProductName=Louisiana Hot Spiced Okra/>
<row CategoryName=Condiments ProductName=Northwoods Cranberry Sauce/>
<row CategoryName=Condiments
ProductName=Original Frankfurter grne Soe/>
<row CategoryName=Condiments ProductName=Sirop d'rable/>
<row CategoryName=Condiments ProductName=Vegie-spread/>
(24 filas afectadas)
XML_F52E2B61-18A1-11d1-B105-00805F49916B
-----------------------------------------------<Category CategoryName=Beverages>
<Product ProductName=Chai/>
<Product ProductName=Chang/>
<Product ProductName=Chartreuse verte/>
<Product ProductName=Cte de Blaye/>
<Product ProductName=Guaran Fantstica/>
<Product ProductName=Ipoh Coffee/>
<Product ProductName=Lakkalikri/>
<Product ProductName=Laughing Lumberjack Lager/>
<Product ProductName=Outback Lager/>
<Product ProductName=Rhnbru Klosterbier/>
16 captulo 16
24/1/2002
11:09
Page 21
21
SALIDA
SELECT CategoryName,
ProductName
FROM Categories as Category
JOIN Products as Product
ON Product.CategoryID = Category.CategoryID
WHERE Product.CategoryID <3
ORDER BY CategoryName, ProductName
FOR XML AUTO, ELEMENTS
XML_F52E2B61-18A1-11d1-B105-00805F49916B
-----------------------------------------------<Category>
<CategoryName>Beverages</CategoryName>
<Product>
<ProductName>Chai</ProductName>
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
22
24/1/2002
11:09
Page 22
16 captulo 16
24/1/2002
11:09
Page 23
23
Se puede usar la opcin XMLDATA para que la salida produzca un esquema XML,
como en el listado 16.16.
Listado 16.16: Uso de la opcin XMLDATA para incluir un esquema XML en la salida
USE Northwind
GO
EJEMPLO
SELECT CategoryName,
ProductName
FROM Categories as Category
JOIN Products as Product
ON Product.CategoryID = Category.CategoryID
WHERE Product.CategoryID <3
ORDER BY CategoryName, ProductName
FOR XML AUTO, XMLDATA
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
24
24/1/2002
11:09
Page 24
SALIDA
XML_F52E2B61-18A1-11d1-B105-00805F49916B
<Schema name=Schema2
xmlns=urn:schemas-microsoft-com:xml-data
xmlns:dt=urn:schemas-microsoft-com:datatypes>
<ElementType name=Category
content=eltOnly model=closed order=many>
<element type=Product maxOccurs=*/>
<AttributeType name=CategoryName dt:type=string/>
<attribute type=CategoryName/>
</ElementType>
<ElementType name=Product
content=empty model=closed>
<AttributeType name=ProductName dt:type=string/>
<attribute type=ProductName/>
</ElementType>
</Schema>
<Category xmlns=x-schema:#Schema2 CategoryName=Beverages>
<Product ProductName=Chai/>
<Product ProductName=Chang/>
<Product ProductName=Chartreuse verte/>
<Product ProductName=Cte de Blaye/>
<Product ProductName=Guaran Fantstica/>
<Product ProductName=Ipoh Coffee/>
<Product ProductName=Lakkalikri/>
<Product ProductName=Laughing Lumberjack Lager/>
<Product ProductName=Outback Lager/>
<Product ProductName=Rhnbru Klosterbier/>
<Product ProductName=Sasquatch Ale/>
<Product ProductName=Steeleye Stout/>
</Category>
<Category xmlns=x-schema:#Schema2 CategoryName=Condiments>
<Product ProductName=Aniseed Syrup/>
<Product ProductName=Chef Anton's Cajun Seasoning/>
<Product ProductName=Chef Anton's Gumbo Mix/>
<Product ProductName=Genen Shouyu/>
<Product ProductName=Grandma's Boysenberry Spread/>
<Product ProductName=Gula Malacca/>
<Product ProductName=Louisiana Fiery Hot Pepper Sauce/>
<Product ProductName=Louisiana Hot Spiced Okra/>
<Product ProductName=Northwoods Cranberry Sauce/>
<Product ProductName=Original Frankfurter grne Soe/>
<Product ProductName=Sirop d'rable/>
<Product ProductName=Vegie-spread/>
</Category>
(24 filas afectadas)
16 captulo 16
24/1/2002
11:09
Page 25
25
Como puede ver, la salida del listado 16.16 es igual a la de la segunda consulta del
listado 16.14. La nica diferencia es la presencia de la informacin del esquema al
principio de la salida. Esta informacin se puede usar para crear un archivo XDR
(XML Data Reduced, XML simplificado).
PRECAUCIN
Si trata de leer las salidas de los listados 16.14 a 16.16 directamente en Internet Explorer se
producirn errores de sintaxis de XML, a menos que aada un nodo raz vlido y guarde estas
salidas en formato Unicode desde el Bloc de notas.
16 captulo 16
26
24/1/2002
11:09
Page 26
adUseClient = 3
adWriteChar = 0
adWriteLine = 1
adExecuteStream = 1024
16 captulo 16
24/1/2002
11:09
Page 27
27
=
=
=
=
=
sQuery
sQuery
sQuery
sQuery
sQuery
&
&
&
&
&
SELECT CategoryName,
ProductName
FROM Categories as Category
JOIN Products as Product
ON Product.CategoryID = Category.CategoryID
16 captulo 16
28
24/1/2002
11:09
Page 28
16 captulo 16
24/1/2002
11:09
Page 29
29
16 captulo 16
30
24/1/2002
11:09
Page 30
Chai
Chang
Chartreuse verte
Cte de Blaye
Guaran Fantstica
Ipoh Coffee
Lakkalikri
SALIDA
<HTML>
<HEAD>
<META HTTP-EQUIV=Content-Type content=text/html charset=UTF-8/>
<TITLE>SQL-XML con ejemplos - SQLXML.asp</TITLE>
<XML ID=CatalogIsle>
<Catalog xmlns:sql=urn:schemas-microsoft-com:xml-sql>
<Category CategoryName=Beverages>
16 captulo 16
24/1/2002
11:09
Page 31
31
16 captulo 16
32
24/1/2002
11:09
Page 32
Ahora puede usar el listado 16.17 como una plantilla para presentar sus propias
consultas.
16 captulo 16
24/1/2002
11:09
Page 33
33
NOTA
Ambos procedimientos, sp_xml_preparedocument y sp_xml_removedocument, son procedimientos
extendidos que llaman a bibliotecas externas. El hecho de que su nombre comience con sp implica
que estos procedimientos son globales y que se los puede llamar desde cualquier base de datos,
sin indicar master como nombre de la base de datos.
El listado 16.19 contiene un ejemplo que usa el documento XML del listado 16.1.
Listado 16.19: Uso de la funcin OPENXML para leer un documento XML desde una secuencia de comandos Transact-SQL
DECLARE @xml varchar(8000)
EJEMPLO
@xml
@xml
@xml
@xml
@xml
@xml
@xml
@xml
=
=
=
=
=
=
=
=
<Products>
@xml + <Product ProductID=1
@xml + ProductName=Chai UnitPrice=18.0000/>
@xml + <Product ProductID=2
@xml + ProductName=Chang UnitPrice=19.0000/>
@xml + <Product ProductID=3
@xml + ProductName=Aniseed Syrup UnitPrice=10.0000/>
@xml + </Products>
SALIDA
id
----0.00
2.00
3.00
14.00
parentid
-------NULL
0.00
2.00
3.00
nodetype
-------1.00
1.00
2.00
3.00
localname
-----------Products
Product
ProductID
#text
prefix
-----NULL
NULL
NULL
NULL
namespaceuri
-----------NULL
NULL
NULL
NULL
datatype
-------NULL
NULL
NUL
NUL
prev
---NULL
NULL
NULL
NULL
text
----------NULL
NULL
NULL
1
16 captulo 16
34
24/1/2002
11:09
Page 34
2.00
4.00
2.00
5.00
0.00
6.00
7.00
6.00
8.00
6.00
9.00
0.00
10.00
11.00
10.00
12.00
0.00
13.00
2.00
3.00
2.00
3.00
1.00
2.00
3.00
2.00
3.00
2.00
3.00
1.00
2.00
3.00
2.00
3.00
2.00
3.00
ProductName
#text
UnitPrice
#text
Product
ProductID
#text
ProductName
#text
UnitPrice
#text
Product
ProductID
#text
ProductName
#text
UnitPrice
#text
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NUL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
NULL
2.00
NULL
NULL
NULL
NULL
NULL
NULL
6.00
NULL
NULL
NULL
NULL
NULL
NULL
NULL
Chai
NULL
18.0000
NULL
NULL
2
NULL
Chang
NULL
19.0000
NULL
NULL
3
NULL
Aniseed Syrup
NULL
10.0000
SET
SET
SET
SET
SET
SET
SET
SET
@xml
@xml
@xml
@xml
@xml
@xml
@xml
@xml
=
=
=
=
=
=
=
=
<Products>
@xml + <Product ProductID=1
@xml + ProductName=Chai UnitPrice=18.0000/>
@xml + <Product ProductID=2
@xml + ProductName=Chang UnitPrice=19.0000/>
@xml + <Product ProductID=3
@xml + ProductName=Aniseed Syrup UnitPrice=10.0000/>
@xml + </Products>
16 captulo 16
24/1/2002
11:09
Page 35
35
SALIDA
ProductID
----------1.00
2.00
3.00
ProductName
-------------------------Chai
Chang
Aniseed Syrup
UnitPrice
-------------------$18.00
$19.00
$10.00
(3 filas afectadas)
El resultado del listado 16.20 es ms legible que el del listado 16.19 y es similar a
cualquier otro conjunto de resultados.
PRECAUCIN
Si no ejecuta el procedimiento sp_xml_removedocument, la estructura en forma de rbol podra
permanecer en memoria hasta que se reinicie el servidor. Esto puede causar ciertos problemas de
memoria tratndose de documentos XML de gran tamao.
La funcin OPENXML
El ejemplo del listado 16.20 es muy sencillo: slo contiene tres elementos de una
sola entidad y tres atributos para cada elemento. La funcin OPENXML se puede
usar para leer conjuntos de resultados a partir de documentos XML mucho ms
complejos.
Considere el documento XML del listado 16.4, que contiene informacin
organizada jerrquicamente proveniente de las tablas Customers, Orders y
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
36
24/1/2002
11:09
Page 36
EJEMPLO
16 captulo 16
24/1/2002
11:09
Page 37
37
16 captulo 16
38
24/1/2002
11:09
Page 38
16 captulo 16
24/1/2002
11:09
Page 39
39
Name
----------------------------------------Gustafaposs Knackebrod
Ravioli Angelo
Louisiana Fiery Hot Pepper Sauce
Filo Mix
Scottish Longbreads
Ikura
Tourtiere
Uncle Bobaposs Organic Dried Pears
Spegesild
Mozzarella di Giovanni
Ikura
Uncle Bobaposs Organic Dried Pears
Steeleye Stout
Tarte au sucre
Chang
Louisiana Fiery Hot Pepper Sauce
Longlife Tofu
Queso Cabrales
Singaporean Hokkien Fried Mee
Mozzarella di Giovanni
Flotemysost
Mozzarella di Giovanni
Gnocchi di nonna Alice
Konbu
Jacks New England Clam Chowder
Inlagd Sill
Filo Mix
Price
---------------------$16.80
$15.60
$16.80
$5.60
$10.00
$24.80
$5.90
$24.00
$9.60
$27.80
$24.80
$30.00
$18.00
$49.30
$19.00
$21.05
$10.00
$14.00
$9.80
$34.80
$17.20
$27.80
$30.40
$6.00
$9.65
$19.00
$7.00
Quantity
--------------6.00
15.00
20.00
8.00
10.00
20.00
6.00
16.00
20.00
40.00
20.00
10.00
30.00
40.00
20.00
2.00
15.00
12.00
10.00
5.00
20.00
7.00
4.00
4.00
12.00
6.00
18.00
16 captulo 16
40
24/1/2002
11:09
Page 40
Consulta 4
Combinacin de atributos de diferentes niveles
CompanyName
---------------------Victuailles en stock
Victuailles en stock
Victuailles en stock
Victuailles en stock
Victuailles en stock
Victuailles en stock
Victuailles en stock
Victuailles en stock
Victuailles en stock
Victuailles en stock
Copyright 2001 PEARSON EDUCATION S.A.
Date
---------1996.07.08
1996.07.08
1996.07.08
1996.10.21
1996.10.21
1997.02.19
1997.02.19
1997.02.27
1997.02.27
1997.02.27
Name
-------------------------------Gustafaposs Knackebrod
Ravioli Angelo
Louisiana Fiery Hot Pepper
Filo Mix
Scottish Longbreads
Ikura
Tourtiere
Uncle Bobaposs Organic Dried
Spegesild
Mozzarella di Giovanni
Price
-----$16.80
$15.60
$16.80
$5.60
$10.00
$24.80
$5.90
$24.00
$9.60
$27.80
Quantity
---------6.00
15.00
20.00
8.00
10.00
20.00
6.00
16.00
20.00
40.00
16 captulo 16
24/1/2002
11:09
Page 41
41
1997.03.18
1997.05.23
1997.05.23
1997.05.23
1997.12.31
1997.12.31
1997.12.31
1996.07.04
1996.07.04
1996.07.04
1996.08.06
1996.08.06
1996.09.02
1997.11.11
1997.11.11
1997.11.12
1997.11.12
Ikura
Uncle Bobaposs Organic Dried
Steeleye Stout
Tarte au sucre
Chang
Louisiana Fiery Hot Pepper
Longlife Tofu
Queso Cabrales
Singaporean Hokkien Fried
Mozzarella di Giovanni
Flotemysost
Mozzarella di Giovanni
Gnocchi di nonna Alice
Konbu
Jacks New England Clam
Inlagd Sill
Filo Mix
$24.80
$30.00
$18.00
$49.30
$19.00
$21.05
$10.00
$14.00
$9.80
$34.80
$17.20
$27.80
$30.40
$6.00
$9.65
$19.00
$7.00
20.00
10.00
30.00
40.00
20.00
2.00
15.00
12.00
10.00
5.00
20.00
7.00
4.00
4.00
12.00
6.00
18.00
Price
-----$27.80
$18.00
$49.30
Quantity
---------40.00
30.00
40.00
Date
---------1997.02.27
1997.05.23
1997.05.23
Name
-------------------------------Mozzarella di Giovanni
Steeleye Stout
Tarte au sucre
(3 filas afectadas)
Con esta consulta, slo podemos obtener datos en el nivel de los productos, ya
que en la funcin OPENXML hemos definido la ruta a los datos como
Customers/Customer/Order/Product. La clusula WITH contiene los campos
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
42
24/1/2002
11:09
Page 42
El tercer ejemplo slo lee nombres de compaas, del nivel de los clientes
(seleccionado mediante su ruta, Customers/Customer).
SELECT *
FROM OPENXML(@iDoc, Customers/Customer, 1)
WITH (CompanyName nvarchar(40))
Hasta ahora fue bastante sencillo. Seleccionamos la ruta para llegar a los datos
que queremos leer (en el segundo parmetro de la funcin OPENXML) e indicamos
las definiciones de las columnas en la clusula WITH.
El cuarto ejemplo es un poco ms complejo, porque queremos leer algo de informacin
de cada uno de los niveles combinando la salida de los tres ejemplos previos:
SELECT CompanyName,
CONVERT(varchar(10), [Date], 102) As Date,
Name, Price, Quantity
FROM OPENXML(@iDoc, Customers/Customer/Order/Product, 1)
WITH (CompanyName nvarchar(40) ../../@CompanyName,
Date smalldatetime ../@Date,
Name nvarchar(40),
Price money,
Quantity int)
16 captulo 16
24/1/2002
11:09
Page 43
43
16 captulo 16
44
24/1/2002
11:09
Page 44
EJEMPLO
@xml
@xml
@xml
@xml
@xml
@xml
@xml
@xml
=
=
=
=
=
=
=
=
<Products>
@xml + <Product ProductID=1
@xml + ProductName=Chai UnitPrice=18.0000/>
@xml + <Product ProductID=2
@xml + ProductName=Chang UnitPrice=19.0000/>
@xml + <Product ProductID=3
@xml + ProductName=Aniseed Syrup UnitPrice=10.0000/>
@xml + </Products>
16 captulo 16
24/1/2002
11:09
Page 45
45
SALIDA
Date
---------1996.08.20
1996.10.30
1996.12.25
1996.09.05
1996.10.11
1996.07.17
1996.07.24
1996.08.26
ProductName
-------------------------Chai
Chang
Chang
Chang
Chang
Chang
Chang
Aniseed Syrup
UnitPrice
---------------------$18.00
$19.00
$19.00
$19.00
$19.00
$19.00
$19.00
$10.00
Quantity
-------45.00
24.00
25.00
40.00
25.00
50.00
35.00
30.00
(8 filas afectadas)
16 captulo 16
46
24/1/2002
11:09
Page 46
PRECAUCIN
El envo de consultas o plantillas directamente a travs de HTTP representa un problema de
seguridad, ya que mediante este mtodo los usuarios pueden enviar cualquier consulta
Transact-SQL vlida (siempre que puedan conectarse al directorio virtual).
En un entorno de Internet de produccin (destinado al uso real), se recomienda deshabilitar las
consultas POST y restringir el acceso HTTP exclusivamente al uso de archivos de plantilla, ya que
de esta forma es posible limitar las consultas que los usuarios pueden enviar a travs de HTTP.
NOTA
Para poder usar updategrams XML en SQL Server 2000, hay que instalar el soporte de
XML para SQL Server (XML for SQL Server Web Release), que se puede descargar de:
http://msdn.microsoft.com/downloads/default.asp?URL=/code/sample.asp?url=/
msdn-files/027/001/554/msdncompositedoc.xml
Como alternativa, puede descargar la nueva versin SQ:XML 2.0 de la siguiente direccin:
http://download.microsoft.com/download/SQLSSVR2000/Install/2.0/W98NT42KMeXP/
EN-US/sqlxml.msi
Pero asegrese de que lee los ficheros que acompaan a esta nueva versin para asegurarse de
que mantiene los criterios de compatibilidad con versiones anteriores de esta nueva versin.
En esta seccin aprenderemos a crear un directorio virtual en IIS para SQL Server y
a enviar consultas a travs de HTTP, mediante consultas en URL y plantillas.
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
24/1/2002
11:09
Page 47
47
16 captulo 16
48
24/1/2002
11:09
Page 48
Figura 16.10: Indicacin del modo de autentificacin usado para acceder a datos
de SQL Server a travs de HTTP.
16 captulo 16
24/1/2002
11:09
Page 49
49
NOTA
Si quiere proveer diferentes modos de seguridad para el acceso puede crear diferentes directorios
virtuales para el mismo servidor. Desde IIS podr administrar la seguridad de acceso de cada uno
de estos directorios virtuales.
16 captulo 16
50
24/1/2002
11:09
Page 50
Figura 16.12: Configuracin del mtodo de acceso a los datos de SQL Server.
Para probar el directorio virtual que acaba de configurar abra Internet Explorer y
escriba el siguiente URL en la lnea de direccin:
http://localhost/sqlxml?sql=SELECT+CategoryName+FROM+Categories+As+Category+FOR+XML+AUT
O&root=Categories
16 captulo 16
24/1/2002
11:09
Page 51
51
EJEMPLO
<?xml version=1.0?>
<Categories xmlns:sql=urn:schemas-microsoft-com:xml-sql>
<sql:query>
SELECT CategoryName
FROM Categories AS Category
FOR XML AUTO
</sql:query>
</Categories>
16 captulo 16
52
24/1/2002
11:09
Page 52
Figura 16.14: Este directorio virtual contiene un nombre virtual para una plantilla.
NOTA
No hace falta que la carpeta para las plantillas coincida con el directorio virtual. Sin embargo,
si los archivos de plantilla no estn guardados en una carpeta con nombre virtual de tipo
Plantillas, IIS no los reconocer como plantillas XML vlidas.
16 captulo 16
24/1/2002
11:09
Page 53
53
Listado 16.24: Una plantilla XML que muestra clientes y sus pedidos
EJEMPLO
<?xml version=1.0?>
<Customers xmlns:sql=urn:schemas-microsoft-com:xml-sql>
<sql:header>
<sql:param name=Customer>NULL</sql:param>
<sql:param name=Product>NULL</sql:param>
</sql:header>
<sql:query>
SELECT CompanyName,
OrderDate,
ProductName,
Quantity,
Item.
UnitPrice
FROM Customers AS Customer
JOIN Orders AS [Order]
ON [Order].CustomerID = Customer.CustomerID
JOIN [Order Details] AS Item
ON Item.OrderID = [Order].OrderID
JOIN Products AS Product
ON Product.ProductID = Item.ProductID
WHERE CompanyName LIKE
CASE @Customer
WHEN NULL THEN %
ELSE @Customer + %
END
AND ProductName LIKE
CASE @Product
WHEN NULL THEN %
ELSE @Product + %
END
ORDER BY CompanyName, OrderDate, ProductName
FOR XML AUTO
</sql:query>
</Customers>
Si examina el cdigo del listado 16.24 puede identificar la presencia de una nueva
seccin al principio del archivo:
<sql:header>
<sql:param name=Customer>NULL</sql:param>
<sql:param name=Product>NULL</sql:param>
</sql:header>
Esta seccin define los parmetros usados, que funcionan de manera similar a los
de los procedimientos almacenados o los de las funciones definidas por el usuario.
En este caso hemos declarado dos parmetros: Customer y Product. Para ambos
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
54
24/1/2002
11:09
Page 54
Para probar esta plantilla puede escribir este URL en Internet Explorer:
http://localhost/sqlxml/Plantillas/CustomersOrders.xml
Sin embargo, la forma en que el listado 16.24 enva las consultas no es eficiente.
El listado 16.25 muestra una secuencia de instrucciones Transact-SQL que es ms
larga pero ms eficiente, ya que SQL Server puede optimizar el uso de los ndices
segn los parmetros enviados. La nica diferencia entre estos dos ejemplos es
que el listado 16.25 divide la consulta en cuatro consultas individuales:
Cuando el usuario no indica ninguno de los parmetros (Product y Customer
son ambos NULL) la consulta lee informacin acerca de todos los pedidos.
Cuando Customer es NULL se lee slo informacin acerca de los pedidos
relacionados con los productos cuyo nombre comienza con el valor indicado
en el parmetro Product.
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
24/1/2002
11:09
Page 55
55
Cuando Product es NULL se lee slo informacin acerca de los clientes cuyo
nombre comienza con el valor indicado en el parmetro Customer.
En el caso restante se lee slo informacin acerca de los productos cuyo
nombre comienza con el valor indicado en el parmetro Product y clientes
cuyo nombre comienza con el valor indicado en el parmetro Customer.
Listado 16.25: Una plantilla XML ms eficiente para mostrar clientes y sus pedidos
EJEMPLO
<?xml version=1.0?>
<Customers xmlns:sql=urn:schemas-microsoft-com:xml-sql>
<sql:header>
<sql:param name=Customer>NULL</sql:param>
<sql:param name=Product>NULL</sql:param>
</sql:header>
<sql:query>
IF @Customer = NULL
IF @Product = NULL
SELECT CompanyName,
OrderDate,
ProductName,
Quantity,
Item.
UnitPrice
FROM Customers AS Customer
JOIN Orders AS [Order]
ON [Order].CustomerID = Customer.CustomerID
JOIN [Order Details] AS Item
ON Item.OrderID = [Order].OrderID
JOIN Products AS Product
ON Product.ProductID = Item.ProductID
ORDER BY CompanyName, OrderDate, ProductName
FOR XML AUTO
ELSE
SELECT CompanyName,
OrderDate,
ProductName,
Quantity,
Item.
UnitPrice
FROM Customers AS Customer
JOIN Orders AS [Order]
ON [Order].CustomerID = Customer.CustomerID
JOIN [Order Details] AS Item
ON Item.OrderID = [Order].OrderID
JOIN Products AS Product
ON Product.ProductID = Item.ProductID
WHERE ProductName LIKE @Product + %
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
56
24/1/2002
11:09
Page 56
Como puede ver en el listado 16.25, en una plantilla no se est limitado a escribir
una sola consulta, sino que puede escribirse un lote completo que incluya varias
instrucciones, siempre que en todas las instrucciones SELECT se use la clusula
FOR XML.
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
24/1/2002
11:09
Page 57
57
EJEMPLO
<CustomerUpdate xmlns:updg=urn:schemas-microsoft-com:xml-updategram>
<updg:sync>
<updg:before>
<Customers CustomerID=ALFKI>
<ContactName>Maria Anders</ContactName>
</Customers>
</updg:before>
<updg:after>
<Customers CustomerID=ALFKI>
<ContactName>Stephen Johns</ContactName>
</Customers>
</updg:after>
</updg:sync>
</CustomerUpdate>
Use el bloc de notas para crear el ejemplo del listado 16.26 y gurdelo con el nombre
CustomerUpdate.xml en el directorio Plantillas que cre con anterioridad (en la
seccin Creacin de un directorio virtual para SQL Server en IIS de este captulo).
Para ejecutar el updategram, abra Internet Explorer y escriba el siguiente URL:
http://localhost/sqlxml/plantillas/CustomerUpdate.xml
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
58
24/1/2002
11:09
Page 58
SUGERENCIA
Si recibe un mensaje de error, controle cmo escribi el archivo XML. Recuerde que las etiquetas XML distinguen entre maysculas y minsculas.
Esta lnea, al principio del archivo, define el archivo XML como una plantilla
XML que contiene un updategram.
<updg:sync>
...
</updg:sync>
Estas dos etiquetas definen la imagen previa de los datos. En cierto modo,
podemos considerar esta seccin como la clusula WHERE de una instruccin
UPDATE, en la que definimos qu filas sufrirn las modificaciones.
<updg:after>
...
</updg:after>
Por ltimo, estas dos etiquetas delimitan los valores a modificar. Esta seccin
produce el mismo efecto que la clusula SET de la instruccin UPDATE.
En este ejemplo usamos la codificacin (mapping) predeterminada, en la que el
cdigo XML muestra los nombres reales de las tablas y las columnas (en este caso,
la tabla Customers y las columnas CustomerID y ContactName). En ocasiones
puede ser preferible suministrar un archivo de esquema, por ejemplo
CustomerSchema.xml, en cuyo caso hay que cambiar la lnea <updg:sync> del
archivo del updategram y proveer el atributo mapping-schema, como en la lnea
siguiente:
<updg:sync mapping-schema=CustomerSchema.xml>
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
24/1/2002
11:09
Page 59
59
NOTA
Si el esquema no estuviera guardado en la misma ruta que el updategram, en el atributo
mapping-schema se puede indicar la ruta completa.
Usando ADO 2.6 se puede invocar un updategram desde una pgina ASP, como en
el ejemplo del listado 16.27.
Listado 16.27: Uso de ADO 2.6 en VBScript para ejecutar un updategram
<%@ LANGUAGE = VBScript %>
<% Option Explicit %>
EJEMPLO
<HTML>
<HEAD>
<META HTTP-EQUIV=Content-Type content=text/html charset=UTF-8/>
<TITLE>SQL-XML by Example - SQLXML.asp</TITLE>
<%
ESTE ES EL SCRIPT DE SERVIDOR
Esta parte no ser visible en el cliente
Algunas constantes para que el cdigo sea ms legible.
Algunas de estas constantes se pueden encontrar en el
archivo adovbs.inc
const
const
const
const
adUseClient = 3
adWriteChar = 0
adWriteLine = 1
adExecuteStream = 1024
16 captulo 16
60
24/1/2002
11:09
Page 60
16 captulo 16
24/1/2002
11:09
Page 61
61
Como puede ver, el ejemplo del listado 16.27 es bsicamente el mismo que el del
listado 16.17. Las nicas diferencias son el updategram y la ausencia de script de
cliente, que en este caso no hace falta.
EJEMPLO
<CategoryAdd xmlns:updg=urn:schemas-microsoft-com:xml-updategram>
<updg:sync>
<updg:before>
</updg:before>
<updg:after>
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
62
24/1/2002
11:09
Page 62
Como puede ver en el listado 16.28, la imagen previa (before) est vaca y la
ejecucin de este updategram provocar el agregado de una nueva categora con el
nombre Nueva categ., y con los valores predeterminados (o NULL) en todos los
dems campos.
La operacin de insercin puede ser ms compleja, por ejemplo, insertar en la
misma operacin una nueva categora y un nuevo producto perteneciente a esa
categora. El problema es que el identificador de categora (CategoryID) es una
columna de identidad y necesitamos usar ese nuevo valor en la tabla Products. El
listado 16.29 muestra el updategram que lleva a cabo esta accin.
Listado 16.29: Uso de un updategram para insertar una nueva categora y un nuevo producto perteneciente a esa categora
EJEMPLO
<CategoryProductAdd xmlns:updg=urn:schemas-microsoft-com:xml-updategram>
<updg:sync>
<updg:before>
</updg:before>
<updg:after updg:returnid=ID>
<Categories updg:at-identity=ID>
<CategoryName>Otra categ.</CategoryName>
</Categories>
<Products CategoryID=ID ProductName=Nuevo producto Discontinued=1 />
</updg:after>
</updg:sync>
</CategoryProductAdd>
16 captulo 16
24/1/2002
11:09
Page 63
63
SALIDA
- <CategoryProductAdd xmlns:updg=urn:schemas-microsoft-com:xml-updategram>
- <returnid>
<ID>11</ID>
</returnid>
</CategoryProductAdd>
EJEMPLO
<DeleteCatProducts xmlns:updg=urn:schemas-microsoft-com:xml-updategram>
<updg:sync>
<updg:before>
<Products ProductName=Nuevo producto />
<Categories CategoryName=Otra categ. />
<Categories CategoryName=Nueva categ. />
</updg:before>
<updg:after>
</updg:after>
</updg:sync>
</DeleteCatProducts>
PRECAUCIN
Tenga cuidado al definir la imagen before del updategram. Recuerde que es la clusula WHERE
de una instruccin DELETE.
Qu viene ahora?
La informacin contenida en este captulo es apenas un elemento ms en el panorama
total de SQL Server 2000. El lector puede intentar usar muchas de las posibilidades y
ejemplos de los otros captulos junto con las tcnicas de las que hablamos en este.
La programacin ASP es un importante componente del desarrollo de aplicaciones
con SQL Server y el nuevo paradigma ASP.NET abre nuevos horizontes para este
popular entorno de programacin.
Copyright 2001 PEARSON EDUCATION S.A.
16 captulo 16
64
24/1/2002
11:09
Page 64