将结果集检索到流中
ADO 可以改为将查询结果检索到流中,而不是在传统的 Recordset 对象中接收结果。 ADO Stream 对象(或支持 COM IStream 接口的其他对象,如 ASP 请求 和 响应 对象)可用于包含这些结果。 此功能的一个用途是检索 XML 格式的结果。 例如,借助 SQL Server,可以通过多种方式返回 XML 结果,例如将 FOR XML 子句与 SQL SELECT 查询一起使用或使用 XPath 查询。
若要以流格式接收查询结果,而不是在 Recordset中接收查询结果,必须将 ExecuteOptionEnum 中的 adExecuteStream 常量指定为 Command 对象的 Execute 方法的参数。 如果提供程序支持此功能,则执行后将在流中返回结果。 在执行代码之前,可能需要指定其他特定于提供程序的属性。 例如,对于 Microsoft OLE DB Provider for SQL Server,必须指定 Command 对象的 Properties 集合中的属性,例如 输出流。 有关与此功能相关的 SQL Server 特定动态属性的详细信息,请参阅 SQL Server 联机丛书中 XML-Related 属性。
FOR XML 查询示例
以下示例使用 VBScript 写入 Northwind 数据库:
<!-- BeginRecordAndStreamVBS -->
<%@ LANGUAGE = VBScript %>
<% Option Explicit %>
<HTML>
<HEAD>
<META NAME="GENERATOR" Content="Microsoft Developer Studio"/>
<META HTTP-EQUIV="Content-Type" content="text/html"; charset="iso-8859-1">
<TITLE>FOR XML Query Example</TITLE>
<STYLE>
BODY
{
FONT-FAMILY: Tahoma;
FONT-SIZE: 8pt;
OVERFLOW: auto
}
H3
{
FONT-FAMILY: Tahoma;
FONT-SIZE: 8pt;
OVERFLOW: auto
}
</STYLE>
<!-- #include file="adovbs.inc" -->
<%
Response.Write "<H3>Server-side processing</H3>"
Response.Write "Page Generated @ " & Now() & "<BR/>"
Dim adoConn
Set adoConn = Server.CreateObject("ADODB.Connection")
Dim sConn
sConn = "Provider=SQLOLEDB;Data Source=" & _
Request.ServerVariables("SERVER_NAME") & ";" & _
Initial Catalog=Northwind;Integrated Security=SSPI;"
Response.write "Connect String = " & sConn & "<BR/>"
adoConn.ConnectionString = sConn
adoConn.CursorLocation = adUseClient
adoConn.Open
Response.write "ADO Version = " & adoConn.Version & "<BR/>"
Response.write "adoConn.State = " & adoConn.State & "<BR/>"
Dim adoCmd
Set adoCmd = Server.CreateObject("ADODB.Command")
Set adoCmd.ActiveConnection = adoConn
Dim sQuery
sQuery = "<ROOT xmlns:sql='urn:schemas-microsoft-com:xml-sql'><sql:query>SELECT * FROM PRODUCTS WHERE ProductName='Gumbr Gummibrchen' FOR XML AUTO</sql:query></ROOT>"
Response.write "Query String = " & sQuery & "<BR/>"
Dim adoStreamQuery
Set adoStreamQuery = Server.CreateObject("ADODB.Stream")
adoStreamQuery.Open
adoStreamQuery.WriteText sQuery, adWriteChar
adoStreamQuery.Position = 0
adoCmd.CommandStream = adoStreamQuery
adoCmd.Dialect = "{5D531CB2-E6Ed-11D2-B252-00C04F681B71}"
Response.write "Pushing XML to client for processing " & "<BR/>"
adoCmd.Properties("Output Stream") = Response
Response.write "<XML ID='MyDataIsle'>"
adoCmd.Execute , , 1024
Response.write "</XML>"
%>
<SCRIPT language="VBScript" For="window" Event="onload">
Dim xmlDoc
Set xmlDoc = MyDataIsle.XMLDocument
xmlDoc.resolveExternals=false
xmlDoc.async=false
If xmlDoc.parseError.Reason <> "" then
Msgbox "parseError.Reason = " & xmlDoc.parseError.Reason
End If
Dim root, child
Set root = xmlDoc.documentElement
For each child in root.childNodes
dim OutputXML
OutputXML = document.all("log").innerHTML
document.all("log").innerHTML = OutputXML & "<LI>" & child.getAttribute("ProductName") & "</LI>"
Next
</SCRIPT>
</HEAD>
<BODY>
<H3>Client-side processing of XML Document MyDataIsle</H3>
<UL id=log>
</UL>
</BODY>
</HTML>
<!-- EndRecordAndStreamVBS -->
FOR XML 子句指示 SQL Server 以 XML 文档的形式返回数据。
FOR XML 语法
FOR XML [RAW|AUTO|EXPLICIT]
FOR XML RAW 生成将列值作为属性的泛型行元素。 FOR XML AUTO 使用启发法,根据表名称生成元素名称的分层树。 FOR XML EXPLICIT 生成一个通用表,其中包含元数据完全描述的关系。
下面是 SQL SELECT FOR XML 语句的示例:
SELECT * FROM PRODUCTS ORDER BY PRODUCTNAME FOR XML AUTO
该命令可以在字符串中指定,如前所述,分配给 CommandText,也可以以分配给 CommandStream的 XML 模板查询的形式指定。 有关 XML 模板查询的详细信息,请参阅 ADO 中的 命令流,或在 SQL Server 在线文档中使用流技术进行命令输入。
作为 XML 模板查询,FOR XML 查询如下所示:
<sql:query> SELECT * FROM PRODUCTS ORDER BY PRODUCTNAME FOR XML AUTO </sql:query>
此示例指定 ASP Response 对象的 Output Stream 属性:
adoCmd.Properties("Output Stream") = Response
接下来,指定 Execute的 adExecuteStream 参数。 此示例将流包装在 XML 标记中以创建 XML 数据岛:
Response.write "<XML ID=MyDataIsle>"
adoCmd.Execute , , adExecuteStream
Response.write "</XML>"
言论
此时,XML 已流式传输到客户端浏览器,它已准备好显示。 这是通过使用客户端 VBScript 将 XML 文档绑定到 DOM 实例并通过每个子节点循环生成 HTML 中的产品列表来完成的。