ASP.NET 呼叫Web Services
接著我們看如何在 ASP.NET 中去使用 SQLXML 所產生出來的 Web Services,主要分為三個步驟:
Step1. 加入 Web 參考:在 Visual Studio.NET 方案總管中加入 Web 參考,接著輸入 WSDL 網址,就是剛才 SQLXML 產生出來的 WSDL 位址,並設定 Web 參考名稱。
圖 15
Step2. 產生 Proxy Class 的物件實體
Dim ProxyName As New WebReferenceName. WSName()
說明:
ProxyName:proxy 名稱
WebReferenceName:Web 參考名稱
WSName:Web 服務名稱
Step3. 透過 DataSet 或 XmlElement 接收結果
Dim DataSetName As New DataSet
DataSetName = ProxyName.WebMethodName(arg1,arg2,arg3,….)
說明:
DataSetName:DataSet名稱
ProxyName:proxy 名稱
WebMethodName:Web 方法名稱
arg1,arg2,arg3,….:Web 方法參數
預儲程序( Store Procedure ) 與 範本 ( Templates ) 範例
(SP_Sample.aspx),僅節錄 datagrid 中部分程式:
<asp:datagrid runat="server" AllowPaging="True" AutoGenerateColumns="False" >
<Columns>
<asp:EditCommandColumn ButtonType="PushButton" UpdateText="儲存" CancelText="取消" EditText="修改">
</asp:EditCommandColumn>
<asp:ButtonColumn Text="刪除" ButtonType="PushButton" CommandName="Delete"></asp:ButtonColumn>
<asp:BoundColumn DataField="EmployeeID" SortExpression="EmployeeID" HeaderText="EmployeeID">
</asp:BoundColumn>
<asp:TemplateColumn HeaderText="LastName">
<ItemTemplate>
<asp:Label runat="server" Text='<%# DataBinder.Eval(Container, "DataItem.LastName") %>'>
</asp:Label>
</ItemTemplate>
<EditItemTemplate>
<asp:TextBox runat="server" Text='<%# DataBinder.Eval(Container, "DataItem.LastName")
%>'>
</asp:TextBox>
</EditItemTemplate>
</asp:TemplateColumn>
…………
…………
</Columns>
<PagerStyle HorizontalAlign="Right" Mode="NumericPages"></PagerStyle>
</asp:datagrid>
圖16
(SP_Sample.aspx.vb)
Imports System.Xml
Public Class WebForm1
Inherits System.Web.UI.Page
Dim proxy1 As New wb1.SqlAsDataSet
Dim returnValue As Integer
Dim DataSet1 As DataSet
Private Sub Page_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
If Page.IsPostBack = False Then
BindGrid()
End If
End Sub
Private Sub BindGrid()
DataSet1 = proxy1.queryEmployees(0, True, returnValue)
DataView1 = DataSet1.Tables(0).DefaultView
DataGrid1.DataSource = DataView1
DataGrid1.DataKeyField = "EmployeeID"
DataGrid1.DataBind()
End Sub
Public Sub Update_Sample(ByVal sender As System.Object, ByVal e As DataGridCommandEventArgs)
'預存程序 (Store Procedure) 更新範例
returnValue = 0
Try
proxy1.SPUpdateSample(DataGrid1.DataKeys(e.Item.ItemIndex), True, CType(e.Item.FindControl("LastName"), TextBox).Text, CType(e.Item.FindControl("FirstName"), TextBox).Text, CType(e.Item.FindControl("Title"), TextBox).Text, CType(e.Item.FindControl("TitleOfCourtesy"), TextBox).Text, CType(e.Item.FindControl("Address"), TextBox).Text, CType(e.Item.FindControl("City"), TextBox).Text, CType(e.Item.FindControl("Country"), TextBox).Text, returnValue)
Response.Redirect("SP_Sample.aspx")
Catch ex As System.Exception
Response.Write(ex.Message)
End Try
End Sub
Public Sub Edit_Sample(ByVal sender As System.Object, ByVal e As DataGridCommandEventArgs)
Try
DataGrid1.EditItemIndex() = e.Item.ItemIndex
BindGrid()
Catch ex As System.Exception
Response.Write(ex.Message)
End Try
End Sub
Public Sub Cancel_Sample(ByVal sender As System.Object, ByVal e As DataGridCommandEventArgs)
Try
DataGrid1.EditItemIndex() = -1
BindGrid()
Catch ex As System.Exception
Response.Write(ex.Message)
End Try
End Sub
Public Sub Delete_Sample(ByVal sender As System.Object, ByVal e As DataGridCommandEventArgs)
'預存程序 (Store Procedure) 刪除範例
returnValue = 0
Try
proxy1.SPDeleteSample(DataGrid1.DataKeys(e.Item.ItemIndex), True, returnValue)
Response.Redirect("SP_Sample.aspx")
Catch ex As System.Exception
Response.Write(ex.Message)
End Try
End Sub
Private Sub DataGrid1_PageIndexChanged(ByVal sender As System.Object, ByVal e As DataGridPageChangedEventArgs) Handles DataGrid1.PageIndexChanged
DataGrid1.CurrentPageIndex = e.NewPageIndex
BindGrid()
DataGrid1.SelectedIndex = -1
End Sub
Private Sub btnAdd_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnAdd.Click
'預存程序 (Store Procedure) 新增範例
proxy1.SPInsertSample(txtLastName.Text, txtFirstName.Text, txtTitle.Text, txtTitleOfCourtesy.Text, txtAddress.Text, txtCity.Text, txtCountry.Text, returnValue)
Response.Redirect("SP_Sample.aspx")
End Sub
End Class
結果如下:
圖17
至於範本和預儲程序 的Web 方法主要差異在於:範本的資料操作邏輯是撰寫於中間層( Middle Tier ),而預儲程序則是撰寫於資料庫 (SQL Server ) 端。一般分工詳細的企業,程式設計師不能直接連線且操作資料庫,資料庫是由 DBA 管理。好處是不會因為操作資料庫而影響效能甚至是他人的資料。此外可以將多個查詢或stored procedures 撰寫於範本中,也可支援參數查詢和搭配 XSL 做資料轉換。以下是自定參數的範本範例:
(TempSelectSample.xml)
EmployeeID SELECT EmployeeID, LastName, FirstName,Title,TitleOfCourtesy, Address, City,Country FROM Employees where EmployeeID >= @EmployeeID FOR XML AUTO,ELEMENTS " src="file:///C:/Users/james/AppData/Local/Temp/msohtmlclip1/01/clip_image040.gif" width=712>
<sql:param> 的 tag 為自定參數,和和查詢語法裡 @EmployeeID 相對應,因為查詢後欲得到 XML 文件的回應,且希望得到的欄位值以元素( Elements ) 來呈現而不是屬性 ( Attributes ),所以查詢的語法加上 FOR XML AUTO,ELEMENTS。
了解範本格式後,就來實作範例,再寫三個範本:
新增:
(TempInsertSample.xml)
<?xml version='1.0' ?>
<root xmlns:sql="urn:schemas-microsoft-com:xml-sql" >
<sql:header>
<sql:param>LastName</sql:param>
<sql:param>FirstName</sql:param>
<sql:param>Title</sql:param>
<sql:param>TitleOfCourtesy</sql:param>
<sql:param>Address</sql:param>
<sql:param>City</sql:param>
<sql:param>Country</sql:param>
</sql:header>
<sql:query>
INSERT INTO Employees (LastName, FirstName, Title, TitleOfCourtesy, Address, City,Country)
VALUES (@LastName,@FirstName,@Title,@TitleOfCourtesy,@Address,@City,@Country)
</sql:query>
</root>
修改:
(TempUpdateSample.xml)
<?xml version='1.0' ?>
<root xmlns:sql="urn:schemas-microsoft-com:xml-sql" >
<sql:header>
<sql:param>EmployeeID</sql:param>
<sql:param>LastName</sql:param>
<sql:param>FirstName</sql:param>
<sql:param>Title</sql:param>
<sql:param>TitleOfCourtesy</sql:param>
<sql:param>Address</sql:param>
<sql:param>City</sql:param>
<sql:param>Country</sql:param>
</sql:header>
<sql:query>
UPDATE Employees SET LastName=@LastName, FirstName=@FirstName, Title=@Title, TitleOfCourtesy=@TitleOfCourtesy, Address=@Address, City=@City,Country=@Country
WHERE EmployeeId=@EmployeeId
</sql:query>
</root>
刪除:
(TempDeleteSample.xml)
<?xml version='1.0' ?>
<root xmlns:sql="urn:schemas-microsoft-com:xml-sql" >
<sql:header>
<sql:param>EmployeeID</sql:param>
</sql:header>
<sql:query>
DELETE FROM Employees
WHERE EmployeeId=@EmployeeId
</sql:query>
</root>
這四個範本檔案,把它放置於 SQLXML 設的虛擬目錄路徑中,在此路徑中新增名為 Templates的資料夾用來放置範本。然後到 SQLXML 『IIS 虛擬目錄管理』,之前所建立的 Northwind『虛擬目錄名稱』中,sqlwb 『虛擬名稱』設定,新增四個 Web 方法,型別都選擇『範本』,對應剛才的範本檔:
Web 方法名稱 |
對應的Templates |
TempSelectSample |
TempSelectSample.xml |
TempInsertSample |
TempInsertSample.xml |
TempUpdateSample |
TempUpdateSample.xml |
TempDeleteSample |
TempDeleteSample.xml |
選擇對應的範本檔路徑
圖18
網頁的部分另存一份Temp_Sample.aspx,內容和 SP_Sample.aspx 相同。程式的部分把前面 Store Procedure 的範例稍微改寫一下。
(Temp_Sample.aspx.vb)
……
Private Sub BindGrid()
'利用 XmlTextReader 讀取範本 (Template) 查詢結果
Dim xr As New XmlTextReader(CType(proxy1.TempSelectSample("0")(0), XmlElement).OuterXml, XmlNodeType.Element, New XmlParserContext(Nothing, Nothing, Nothing, XmlSpace.None))
'用 ReadXml 將查詢結果置入 DataSet1
DataSet1.ReadXml(xr)
'設定 DataGrid1 的資料來源為 DataSet1
DataGrid1.DataSource = DataSet1
DataGrid1.DataKeyField = "EmployeeID"
DataGrid1.DataBind()
End Sub
Public Sub Update_Sample(ByVal sender As System.Object, ByVal e As DataGridCommandEventArgs)
'範本 (Template) 更新範例
returnValue = 0
Try
proxy1.TempUpdateSample(DataGrid1.DataKeys(e.Item.ItemIndex), CType(e.Item.FindControl("LastName"), TextBox).Text, CType(e.Item.FindControl("FirstName"), TextBox).Text, CType(e.Item.FindControl("Title"), TextBox).Text, CType(e.Item.FindControl("TitleOfCourtesy"), TextBox).Text, CType(e.Item.FindControl("Address"), TextBox).Text, CType(e.Item.FindControl("City"), TextBox).Text, CType(e.Item.FindControl("Country"), TextBox).Text)
Response.Redirect("Temp_Sample.aspx")
Catch ex As System.Exception
Response.Write(ex.Message)
End Try
End Sub
Public Sub Delete_Sample(ByVal sender As System.Object, ByVal e As DataGridCommandEventArgs)
'範本 (Template) 刪除範例
returnValue = 0
Try
proxy1.TempDeleteSample(DataGrid1.DataKeys(e.Item.ItemIndex))
Response.Redirect("Temp_Sample.aspx")
Catch ex As System.Exception
Response.Write(ex.Message)
End Try
End Sub
Private Sub btnAdd_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnAdd.Click
'範本 (Template) 新增範例
proxy1.TempInsertSample(txtLastName.Text, txtFirstName.Text, txtTitle.Text, txtTitleOfCourtesy.Text, txtAddress.Text, txtCity.Text, txtCountry.Text)
Response.Redirect("Temp_Sample.aspx")
End Sub
……
Mr. Zabo 版權所有,歡迎轉載,但請註明出處及連結!
留言列表