甘草轩

Never surrender to complexity
  博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

深入探讨 SQL Server 2000 对XML的支持

Posted on 2006-07-27 17:56  甘草轩  阅读(335)  评论(0编辑  收藏  举报
  [作者:Wayne,新一代程序,十二岁时开始学习编程,十三岁时拥有自己的电脑,先后学BasicPascalCFOXPROVBDELPHIC++SQL,学Java言后,遂成Java狂崇拜者,于中国科技大学。

  引言

  我可以很简单的使用ADO访问数据中的数据,但是,如果我想把从数据索得到的数据以XML的格式示出来的,就要点神了,当然,我可以去找一些成的用程序或者是把有的存储过程修改一下,来完成个想法。

  虽说ADO2.5宣称支持XML,但是它仍需要一个外的理把数据化成XML程。幸好有了SQL Server 2000,它宣称可以直接从数据中取出数据,而不通ADO2.5直接把数据以XML方式示出来。个功能极大的提高了构造分布式、数据集中的用程序的性能,因为这个特性消除了不必要的代码层

  看一看,了支持XMLSQL Server 2000添加了什新的特性:

  1、能使用 HTTP 访问 SQL Server

  2、支持 XDRXML数据化)架构并且能指定对这些架构的 XPath 查询

  3、能够检索并写入 XML 数据:

    使用 SELECT 句和 FOR XML 子句 XML 数据。

    使用 OPENXML 行集提供程序写入 XML 数据。

    使用 XPath 查询语 XML 数据。

  4、增 Microsoft SQL Server 2000 OLE DB 提供程序 (SQLOLEDB),使得可以将 XML 文档命令文本并以流的形式返回果集。

  可,我可以使用好几方法使用SQL Server 2000访问XML格式的数据:第一,在 URL 行的查询可以直接访问 SQL Server 2000生成XML文档(也可以用存Web器上的XML模版生成XML数据文件)。第二,可以使用SELECT命令和FOR XML关键字,通过调用一个存储过程或是通使用XPath查询来取得XML数据。SQL Server 2000 完全支持 XDRXML数据化)架构,具有映射XML元素和属性到表和字段中的功能。下面,我就探一下SQL Server 2000XML的支持特性。

  一、配置SQL Server 2000IIS

  在本文的始,我想先如何配置SQL Server 2000IISSQL Server 2000 许为IIS建一个虚,用来直接访问一个SQL数据中的数据。一旦在一台配置了IIS算机上安装了SQL Server 2000,就可以运行SQL Server IIS 管理用工具来配置SQL Server 2000IIS

  好,们开始配置程吧!

  在"SQL Server 工具"程序单击" IIS 中配置 SQL XML 支持"这时就会出一个与IIS管理器相似的界面。展器,取默 Web 站点,点右,在出的菜新建选项,然后单击""命令。新虚的属性示在屏幕上。在"新的虚属性"对话框的""选项卡上,入虚的名称,在本例中,请输Northwind和物理目路径(例如 C:\Inetpub\Wwwroot\Northwind,假 C:\Inetpub\Wwwroot 中已建了 Northwind子目,当然我也可以使用浏览钮选择。在安全性选项卡上,填入有效的 SQL Server 信息,在入下一个选项,它将要求你确认刚入的密。在数据源选项卡上,在“SQL Server”框中入服器的名称,在数据框中, Northwind 数据的名称。在""选项卡上,你可以选择 URL 查询模板查询 XPath” POST”选项

  在构建一个用程序,你不但要考到能够访问SQL Server数据,要有足的安全级别以保你的数据的安全性。在名称选项卡上,你可以更具自己的需要选择新建模板型(template)、架构(schema)和模板和架构型(dbonject),并建它的路径。好,我们这样建了虚 Northwind。默情况下,使用录对 Northwind 数据库执行指定的查询。你一定迫不及待的吸高看看SQL果是什么样的了吧?好,浏览器中http://localhost/northwind?sql=SELECT * FROM CUSTOMERS FOR XML AUTO&root=root试验一下吧!

  我们还可以程来实现配置SQL Server 2000IIS请见下面的代

  
   Set ObjXML = CreateObject("SQLVDir.SQLVDirControl")

  ObjXML.Connect 
'Connect to the local computer and Web site "1"

  Set ObjVDirs 
= ObjXML.SQLVDirs

  Set ObjVDir 
= ObjVDirs.AddVirtualDirectory("Northwind")

  ObjVDir.PhysicalPath 
= "C:\Inetpub\wwwroot\northwind"

  ObjVDir.UserName 
= "wayne" 'SQL Server login

  ObjVDir.Password 
= "" 'SQL Server Password

  ObjVDir.DatabaseName 
= "Northwind"

  objVDir.AllowFlags 
= 73

  Set objVNames 
= objVDir.VirtualNames

  objVNames.AddVirtualName 
"dbobject"1""

  objVNames.AddVirtualName 
"schema"2,"C:\Inetpub\wwwroot\northwind\schema"

  objVNames.AddVirtualName 
"template"4 , "C:\Inetpub\wwwroot\northwind\template"

  objXML.Disconnect

  msgbox 
"Done."

  二、使用 HTTP SQL

  使用我们刚建的虚,我就可以通SQL查询语句写入URL的方式查询。打开浏览器,在地址中写入以下URLhttp://localhost/northwind?sql=SELECT+ *+FROM+Customers+WHERE+CustomerID='ANTON' +FOR+XML+AUTO&root=root,如果你使用的虚录别名不是Northwind或者你使用一个程服器,只需要把相改掉就可以了。

  浏览器中会出

<?xml version="1.0" encoding="utf-8" ?>
<root>
<Customers CustomerID
="ANTON" CompanyName="Antonio Moreno Taquería" ContactName="Antonio Moreno" ContactTitle="Owner" Address="Mataderos 2312" City="México D.F." PostalCode="05023" Country="Mexico" Phone="(5555-3932/
/root>

  来分析一下URL“http://localhost/northwind”后面跟了一个SQL查询语句,用来查询数据Northwind的任。在本例中,我使用的查询语句是“SELECT+*+FROM+Customers+WHERE+CustomerID='ANTON'”注意,句已URL编码过了,其中的空格都被替成加号“+”这样它才能被浏览器正确的送到数据中去,URL编码格式您参文档。

  在查询语句之后,有添加了两个新的关键字:FOR XMLAUTOFOR XML关键字可以对现有的系数据库执 SQL 查询,以返回 XML 文档形式。AUTO模式查询结果作嵌套 XML 元素返回,在 FROM 子句内,个在 SELECT 子句中至少有一列被列出的表都表示一个 XML 元素,SELECT 子句中列出的列映射到适当的元素特性,当指定了 ELEMENTS 选项后,表列映射到子元素而非特性。默情况下,AUTO 模式将表列映射到 XML 特性。

  在FOR XML AUTO后,需要添加一个参数“root”,其参数返回的XML文件的root元素名。比如,你可以把上面我出的例子中的root的参数值设为Northwind,你会发现,返回的XML文件中除了root元素名变为Northwind了以外,其它都没有化。

  上面我们说的是直接使用HTTP简单查询,除此之外你可以行更加复杂查询,比如说连接不同的表查询看下面的例子,在下例中,SELECT 接了 Northwind 数据的中的 Customers Orders 表,并返回信息。

http://localhost/northwind?sql=SELECT
Customer.CustomerID%2cCustomer.Contact
Name%2c%5bOrder%5d.OrderID+FROM+Customers+
Customer+INNER+JOIN+Orders+%5bOrder%
5d+ON+Customer.CustomerID%3d%5bOrder%
5d.CustomerID+FOR+XML+AUTO&root=Northwind

返回的XML文件太,我就不把它列出来了。

  如果你不想在Customers表和Orders表中出嵌套的SQL Server 2000提供另一个关键字用来替代AUTO关键字就是RAWRAW 模式将查询结果集中的一行转换为带标识 row XML 元素。您能深入了解RAW,我再出一个例子:使用 RAW 模式索客订单信息

  下面的查询返回客订单信息。在 FOR XML 子句中指定 RAW 模式。


SELECT Customers.CustomerID, Orders.OrderID, Orders.OrderDate 
FROM Customers, Orders 
WHERE Customers.CustomerID = Orders.CustomerID 
ORDER BY Customers.CustomerID 
FOR XML RAW

  下面是部分果:

row CustomerID="ALFKI" OrderID="10643" OrderDate="1997-08-25T00:00:00"/

row CustomerID="ANATR" OrderID="10308" OrderDate="1996-09-18T00:00:00"/

row CustomerID="ANATR" OrderID="10625" OrderDate="1997-08-08T00:00:00"/

row CustomerID="AROUT" OrderID="10355" OrderDate="1996-11-15T00:00:00"/

  可以使用外部接指定上面的查询果集中返回所有客,无论这些客是否有订单
   
SELECT C.CustomerID, O.OrderID, O.OrderDate
     
FROM Customers C LEFT OUTER JOIN Orders O ON C.CustomerID = O.CustomerID ORDER BY C.CustomerID FOR XML RAW

  下面是部分果:


row CustomerID="BONAP" OrderID="11076" OrderDate="1998-05-06T00:00:00"/

row CustomerID="FISSA"/

row CustomerID="PARIS"/

row CustomerID="RICSU" OrderID="11075" OrderDate="1998-05-06T00:00:00"/

  我们还可以使用 HTTP 行存储过程,比如下面个名GetXML的存储过程:
  
CREATE PROCEDURE GetXml
   ( 
    
@CustomerID varchar(5)
   )
   
AS
    
BEGIN
     
SELECT CustomerID, CompanyName,ContactName
      
FROM Customers
      
WHERE CustomerID LIKE @CustomerID + '%'
      
FOR XML AUTO
END

  个存储过程并送相的参数,我可以使用下面URLhttp://localhost/northwind?sql=exec+GetXml+'A'&root=root这样,我就能在更高一次使用存储过程,并且可以根据最想要得到的动态的改参数(比如在本例中,我用的是“A”)。

  三、使用XML模板查询

  SQL Server 2000HTTP求中内嵌SQL句的功能然是非常大并且有用的。但是这种见藏着极大的患,一旦某个最了解了直接使用浏览查询数据的方法,那数据中的数据就很危了,因可能会尝试执行他自己的insert,update甚至是delete程。

  维护大部分数据中数据交易的安全,使用不能直接使用URL查询SQL Server 2000XML模板的概念,可以SQL ServerURL查询导向那些含有所需的SQL程的XML模板中。

  在我们讨论模板概念之前,重新回到SQL ServerIIS管理器中,选项卡。了防止用使用HTTP访问,我 URL 查询选项给去掉。所有SQL查询现在都会被XML模板,XPath中。

  了允XML模板SQL查询名称选项卡,并单击新建按,新建一个模板文件,取名templates,在下拉菜选择template。然后,要么输入一个你的 XML模板将存的路径或者单击浏览。本例中使用C:\Inetpub\wwwroot\xml\templates。一旦你已提供了所有的必要的信息,请单击保存

在一个虚被映射到一个指定来保存 XML查询模板的文件们创建一个有效的 XML模板,用来 SQL查询。下面的代是一个模板示例。
  file2.xml

<Northwind xmlns:sql=
"urn:schemas
-microsoft-com:xml-sql">
<sql:query>
SELECT Customers.CustomerID, Customers.ContactName, 
Orders.OrderID, Orders.CustomerID
FROM Customers
INNER JOIN Orders
ON Customers.CustomerID = Orders.CustomerID
FOR XML AUTO
/sql:query>
/Northwind>

  段代中使用了一个名sql的前和一个URI urn:schemas-microsoft-com:xml-sql个前用来标识使用在 SQL Server XML ISAPI上的元素。有一个元素名query名思它就是用来标记模板文件中的SQL 查询语句。好,来演示一下如何使用个模板吧!在地址入,http://localhost/northwind/templates/file2.xml,当然你也可以根据你的需要改的服器名和虚名。

   URL拆分成独的片段,行分析,你可以看,我先使用了 northwind根,然后使用templates名,如前我们说过名已映射到templates的物理目中。最后, URL出了模板文件的名称。个模板,浏览器就会把表中customers元素下嵌套的不同的订单XML文档的形式示出来。

  使用模板而不使用 URL查询点。首先,在一个最就没有改SQL句的力了,去除URL查询访问 SQL Server选项 ,就只有SQL Server XML ISAPI可以用来理模板文件,就避免未的 插入、更新和除程序被行。其次, XML模板支持动态加入参数,就允你不用更改模板文件就可以更改一个 SQL WHERE子句的

  使用参数,就像插入一个 XML header元素一样简单的,在 header元素中,定了一个 param元素,使用一个值为CustomerID的名称属性。个参数被予一个默认值"A",你可以象在一个存储过程中一在模板文件中使用个参数,只要在个参数前添加一个@,然后把它放入SQL句或用来用一个存储过程就可以了。请见下面的代

<Northwind xmlns:sql="urn:schemas-microsoft-com:xml-sql">
<sql:header>
<sql:param name
='CustomerID'>A</sql:param> 
/sql:header> 
<sql:query>
SELECT Customers.CustomerID, Customers.ContactName,
Orders.OrderID, Orders.CustomerID
FROM Customers
INNER JOIN Orders
ON Customers.CustomerID = Orders.CustomerID
WHERE Customers.CustomerID LIKE @CustomerID + '%'
FOR XML AUTO
/sql:query>
/Northwind>

  在本例中,CustomerID参数被一个WHERE子句使用。如果把参数设为"B"SQL 句就会从CustomersOrders表中返回所有的CustomerIDB开头的行。用模板并传递正确的CustomerID参数,只要在查询字符串之后加上参数名和参数,如:http://localhost/northwind/templates/file2.xml?CustomerID=B即可,就这么简单

  四、XPath查询 架构和模板

  XPath查询也可以被内嵌一个XML模板文件中,下面的代是一个包含XPath查询简单XML模板文件。

<Northwind xmlns:sql=
"urn:schemas
-microsoft-com:
xml
-sql">
<sql:xpath
-query mapping-schema=
"file4.xdr">
/Customer[@CustomerID=
'ALFKI'
]/Order
/sql:xpath-query>
/Northwind>

  查询使用了一个架构(schema)返回CustomerIDALFKI的用的所有的订单,如果想要使XPath句运行,必使用一个XDR架构文件映射不同的XML元素和属性到相的数据表和字段名。下面出了个架构文件。

<?xml version="1.0" ?>
<Schema xmlns="urn:schemas-microsoft-com:xml-data"
xmlns:dt="urn:schemas-microsoft-com:datatypes"
xmlns:sql="urn:schemas-microsoft-com:xml-sql">

<ElementType name="Customer" sql:relation="Customers">
<AttributeType name="CustomerID" dt:type="id" />
<AttributeType name="CompanyName" />
<AttributeType name="ContactName" />
<AttributeType name="City" />
<AttributeType name="Fax" />
<AttributeType name="Orders" dt:type=
"idrefs" sql:id-prefix="Ord-" />

<attribute type="CustomerID" />
<attribute type="CompanyName" />
<attribute type="ContactName" />
<attribute type="City" />
<attribute type="Fax" />
<attribute type="Orders" sql:relation=
"Orders" sql:field="OrderID">
<sql:relationship 
key-relation="Customers" 
key="CustomerID"
foreign-relation="Orders" 
foreign-key="CustomerID" />
</attribute>

<element type="Order">
<sql:relationship 
key-relation="Customers" 
key="CustomerID"
foreign-relation="Orders" 
foreign-key="CustomerID" />
</element>
</ElementType>

<ElementType name="Order" sql:relation="Orders">
<AttributeType name="OrderID" dt:type=
"id" sql:id-prefix="Ord-" />
<AttributeType name="EmployeeID" />
<AttributeType name="OrderDate" />
<AttributeType name="RequiredDate" />
<AttributeType name="ShippedDate" />

<attribute type="OrderID" />
<attribute type="EmployeeID" />
<attribute type="OrderDate" />
<attribute type="RequiredDate" />
<attribute type="ShippedDate" />

<element type="OrderDetail">
<sql:relationship 
key-relation="Orders" 
key="OrderID"
foreign-relation="[Order Details]" 
foreign-key="OrderID" />
</element>
<element type="Employee">
<sql:relationship 
key-relation="Orders" 
key="EmployeeID"
foreign-relation="Employees" 
foreign-key="EmployeeID" />
</element>
</ElementType>

<ElementType name="OrderDetail" sql:relation=
"[Order Details]"
sql:key-fields="OrderID ProductID">
<AttributeType name="ProductID" dt:type="idref" 
sql:id-prefix="Prod-" />
<AttributeType name="UnitPrice"/>
<AttributeType name="Quantity" />

<attribute type="ProductID" />
<attribute type="UnitPrice"/>
<attribute type="Quantity" />

<element type="Discount" sql:field="Discount"/>
</ElementType>

<ElementType name="Discount" dt:type="string" 
sql:relation="[Order Details]"/>

<ElementType name="Employee" sql:relation="Employees">
<AttributeType name="EmployeeID" dt:type="idref" 
sql:id-prefix="Emp-" />
<AttributeType name="LastName" />
<AttributeType name="FirstName" />
<AttributeType name="Title" />
<attribute type="EmployeeID"/>

<attribute type="LastName" />
<attribute type="FirstName" />
<attribute type="Title" />
</ElementType>
</Schema>

  如果您想深入了解架构文件的参看SQL Server 2000的用文档或等待我的以后的文章。

  和内嵌在XML模板文件中的SQL
查询语句一XPath查询语句使用urn:schemas-microsoft-com:xml-sqlsql,共同示用在模板中的自定元素和属性,XPath查询而言,我使用一个名xpath-query的元素来标识查询语法,个元素也有一个名mapping-schema的属性,用来示相用以映射表和字段到特定的XML目的架构文件所在的路径。

  
下面的代码给出了另一个使用更复杂XPath查询的模板文件。

<Northwind xmlns:sql=
"urn:schemas
-microsoft-com:xml-sql">
<sql:xpath
-query mapping-schema=
"listing4.xdr">
/Customer[@CustomerID=
'ALFKI'
]/Order/
Employee
[@LastName='Suyama']
/sql:xpath-query>
/Northwind>

  当个模板文件XPath查询返回与某个客户签订单的雇(employee)的姓名,果如下:

<Northwind xmlns:sql=
"urn:schemas
-microsoft-com:xml-sql">
<Employee EmployeeID
="Emp-6
LastName
="Suyama" 
FirstName
="Michael"
Title
="Sales
Representative"
/> 
/Northwind>

  模板文件中使用的XPath查询也可以使用参数,程很象在XSL式表中使用参数一XSL,使用$指定一个量。下面的代码说明了如何在一个包含XPath查询的模板文件中整合量。

<Northwind xmlns:sql="urn:schemas-microsoft-com:xml-sql">
<sql:header>
<sql:param name
="ID"/
/sql:header>
<sql:xpath
-query mapping-schema="listing4.xdr"> {{should this be "listing6.xdr"?}}
/Customer/Order[@OrderID=$ID]
/sql:xpath-query>
/Northwind>

  通URL传递参数名和相的参数,我就可以完成把参数传递到模板中的操作。果如下:

<Northwind xmlns:sql="urn:schemas-microsoft-com:xml-sql">
<Order OrderID="Ord-10643" EmployeeID=
"6" OrderDate="1997-08-25T00:00:00" RequiredDate=
"1997-09-22T00:00:00" ShippedDate=
"1997-09-02T00:00:00">
<Employee EmployeeID="Emp-6" LastName=
"Suyama" FirstName="Michael" Title=
"Sales Representative" /> 
<OrderDetail ProductID="Prod-28" UnitPrice=
"45.6" Quantity="15">
<Discount>0.25</Discount> 
</OrderDetail>
<OrderDetail ProductID="Prod-39" UnitPrice=
"18" Quantity="21">
<Discount>0.25</Discount> 
</OrderDetail>
<OrderDetail ProductID="Prod-46" UnitPrice=
"12" Quantity="2">
<Discount>0.25</Discount> 
</OrderDetail>
</Order>
</Northwind>

  小

  通使用上面我介的几,我可以直接从SQL Server 2000数据中直接取得XML数据。如我所介URL查询XML模板文件、XDR架构和XPath查询提供了大的功能,从SQL Server 2000中直接XML数据。除此之外,有很多重要的概念,由于篇幅有限在本文中不可能述,如FOR XML EXPLICIT查询OPENXML些技,我会在以后的文章中步进讨论大家等待。