Consuming a Simple Web Service with .NET SDK
- How to Consume a Web Service
- Creating the Web Service Consumer
- Testing the Web Service Consumer
- Summary
In Chapter 2, "Creating a Simple Web Service with .NET SDK," using little more than a text editor and the .NET SDK's utilities, you created and tested a Web Service. In this chapter, you'll use the same tools to consume the Web Service in a Web Forms application, which is the enhanced version of the Active Server Pages applications you might have created in the past (see Figure 3.1). Your Web Forms application will call your Web Service, gather information, and then synthesize it into a Web page that's delivered to your Web Browser.
Figure 3.1 The basic architecture of your application.
Although you are creating a Web Service and a Web Forms application on the same computer for the purpose of this example, that's probably not how you will create production-quality applications. You will either create Web Services that others can use and access from anywhere, or you will create Web Forms applications (or Windows Forms applications) that use Web Services other organizations have created. To simulate two different Web Servers for this example, you will actually create a new sub-Web in your Default Web Site node in Internet Information Services.
How to Consume a Web Service
To consume a Web Service within your application, you have to know the following:
-
The location (URI) of the Web Service's WSDL file. You can find this information in a number of different ways. Someone could supply it to you, you could use DISCO to find it on a particular server, or you could use a UDDI search engine for Web Services. DISCO and UDDI are covered in more detail in Chapters 9, "Understanding DISCO," and 25, "Understanding UDDI."
-
After you have the WSDL file, you can create a proxy to the Web Service, which acts as the mediator for all requests and responses to or from the Web Service (see Figure 3.2). The proxy allows you to develop your application as though the Web Service resided locally on your computer. It serializes your method requests into SOAP and then sends the SOAP message to the Web Service via the network. After the Web Service has finished processing your request and returns its results encoded in a SOAP message, the proxy steps into action by intercepting the message, deserializing it, and returning the results to your application. The proxy is important because it hides the gory details of SOAP serialization and network communications.
You will use the wsdl.exe utility that I mentioned in Chapter 2 to create a proxy for your Web Service so that you can use it in your Web Forms application.
Creating a Separate Web Folder in IIS
As I mentioned, you need to create a separate sub-Web in IIS to simulate your Web Service and Web Forms application running on two physically different machines. For this example, you'll create a folder on your hard drive called C:\pmcalc_web and create a sub-Web called pmcalc_web that points to the folder. (For instructions on how to create a sub-Web in IIS, refer to Chapter 2.)
IMPORTANT
This chapter assumes you are using just the .NET Framework that can be downloaded from Microsoft's MSDN site (msdn.microsoft.com). I recommend that you add a PATH statement to your autoexec.bat file in order to use the command line utilities from any directory. This will save you a lot of time rummaging through the folders on your hard drive to find the wsdl.exe, vb.exe, and csc.exe applications, and will save you a great deal of effort to include the proper /out: parameters when defining where you want the code generated or compiled. To add the PATH statement, first locate the correct Program Files directory (contains the wsdl.exe) and the Windows directory (contains vb.exe and csc.exe) for the .NET Framework. You should find the following locations:
c:\Program Files\Microsoft.NET\FrameworkSDK\Bin c:\Windows\Microsoft.NET\Framework\v1.0.2914
Therefore, you should add the following PATH statement in your autoexec.bat file:
SET PATH=c:\Program Files\Microsoft.NET\FrameworkSDK\Bin;c:\Windows\ Microsoft.NET\Framework\v1.0.2914
After you make this change, you must reboot. Now you will be able to use the necessary command line applications from ANY directory on your hard drive.
Using the wsdl.exe to Create Your Proxy
First, open a DOS command-prompt window. Remember to navigate to the folder C:\pmcalc_web in the DOS prompt before running wsdl.exe so that it creates the proxy code in the appropriate folder of your hard drive. If you don't, you might have to search your hard drive to find it! Alternatively, you can use the utility's /out: switch to specify the exact folder where you want the proxy code file created.
To generate a Visual Basic proxy, enter this line:
wsdl /language:vb http://localhost/pmcalc/pmcalc.asmx?wsdl
Figure 3.2 How the proxy works.
After a few moments, you should see the following confirmation:
Microsoft (R) Web Services Description Language Utility [Microsoft .NET Framework Version 1.0.2728.2] Copyright (C) Microsoft Corp 2000. All rights reserved. C:\pmcalc\pmcalc.vb Writing file `C:\pmcalc\pmcalc.vb'.
To generate a C# proxy, enter this line:
C:\pmcalc>wsdl /language:cs http://localhost/pmcalc/pmcalc.asmx?wsdl
After a few moments, you should see the following confirmation:
Microsoft (R) Web Services Description Language Utility [Microsoft .NET Framework Version 1.0.2728.2] Copyright (C) Microsoft Corp 2000. All rights reserved. C:\pmcalc\pmcalc.cs Writing file `C:\pmcalc\pmcalc.cs'.
Examining the Generated Proxy Class
The wsdl.exe utility has created the source code for your proxy class. You will compile it into a component in a moment, but first inspect the source code to learn a little bit about how the proxy works. Use your favorite text editor and open the pmcalc.vb (for Visual Basic; see Listing 3.1) or pmcalc.cs (for C#; see Listing 3.2) file.
Listing 3.1 The pmcalc.vb Proxy File
`------------------------------------------------------------------------------ ` <autogenerated> ` This code was generated by a tool. ` Runtime Version: 1.0.2728.2 ` ` Changes to this file may cause incorrect behavior and will be lost if ` the code is regenerated. ` </autogenerated> `------------------------------------------------------------------------------ Option Strict On Option Explicit On Imports System Imports System.Web.Services Imports System.Web.Services.Protocols Imports System.Xml.Serialization ` `This source code was auto-generated by wsdl, Version=1.0.2728.2. ` <System.Web.Services.WebServiceBindingAttribute(Name:="pmcalcSoap", [Namespace]:="http://tempuri.org/")> _ Public Class pmcalc Inherits System.Web.Services.Protocols.SoapHttpClientProtocol Public Sub New() MyBase.New Me.Url = "http://localhost/pmcalc/pmcalc.asmx" End Sub <System.Web.Services.Protocols.SoapDocumentMethodAttribute("http://tempuri.org/ developerEstimate", Use:=System.Web.Services.Description.SoapBindingUse.Literal, ParameterStyle:=System.Web.Services.Protocols.SoapParameterStyle.Wrapped)> _ Public Function developerEstimate(ByVal xintHours As Integer) As Double Dim results() As Object = Me.Invoke("developerEstimate", New Object() {xintHours}) Return CType(results(0),Double) End Function Public Function BegindeveloperEstimate(ByVal xintHours As Integer, ByVal callback As System.AsyncCallback, ByVal asyncState As Object) As System.IAsyncResult Return Me.BeginInvoke("developerEstimate", New Object() {xintHours}, callback, asyncState) End Function Public Function EnddeveloperEstimate(ByVal asyncResult As System.IAsyncResult) As Double Dim results() As Object = Me.EndInvoke(asyncResult) Return CType(results(0),Double) End Function End Class
Listing 3.2 The pmcalc.cs Proxy File
//------------------------------------------------------------------------------ // <autogenerated> // This code was generated by a tool. // Runtime Version: 1.0.2728.2 // // Changes to this file may cause incorrect behavior and will be lost if // the code is regenerated. // </autogenerated> //------------------------------------------------------------------------------ // // This source code was auto-generated by wsdl, Version=1.0.2728.2. // using System.Xml.Serialization; using System; using System.Web.Services.Protocols; using System.Web.Services; [System.Web.Services.WebServiceBindingAttribute(Name="pmcalcSoap", Namespace="http://tempuri.org/")] public class pmcalc : System.Web.Services.Protocols.SoapHttpClientProtocol { public pmcalc() { this.Url = "http://localhost/pmcalc/pmcalc.asmx"; } [System.Web.Services.Protocols.SoapDocumentMethodAttribute("http://tempuri.org/ developerEstimate", Use=System.Web.Services.Description.SoapBindingUse.Literal, ParameterStyle=System.Web.Services.Protocols.SoapParameterStyle.Wrapped)] public System.Double developerEstimate(int xintHours) { object[] results = this.Invoke("developerEstimate", new object[] {xintHours}); return ((System.Double)(results[0])); } public System.IAsyncResult BegindeveloperEstimate(int xintHours, System.AsyncCallback callback, object asyncState) { return this.BeginInvoke("developerEstimate", new object[] {xintHours}, callback, asyncState); } public System.Double EnddeveloperEstimate(System.IAsyncResult asyncResult) { object[] results = this.EndInvoke(asyncResult); return ((System.Double)(results[0])); } }
Regardless of whether you use C# or Visual Basic.NET, you can see how the wsdl.exe utility performed a great service for you. The class itself inherits from System.Web.Services.Protocols.SoapClientProtocol, and then uses the Me (this) statement to refer to its instance. It then sets properties such as the URL when it is instantiated in the New method. This pmcalc class has three methods. The first is DeveloperEstimate, which you use in your Web Forms application. The next two methods, BeginDeveloperEstimate and EndDeveloperEstimate, allow for asynchronous calls to Web Services (covered in more depth in Chapter 19, "Calling Web Services Asynchronously"). When your Web Forms application calls the DeveloperEstimate method, your class calls the Invoke method on itself. This call starts the serialization and transportation of your information over the network and also handles deserialization in the response to your call. All this functionality is encapsulated in the System.Web.Services.Protocols.SoapClientProtocol class.
Compiling the Proxy
Now that you have the source code for your proxy, you need to compile it into a .NET Assembly. To accomplish this, the .NET Framework supplies you with a Visual Basic compiler (vbc.exe) and a C# compiler (csc.exe).
Before you compile, you'll need to create a folder called \bin as a subfolder in your pmcalc_web folder, as shown here:
C:\pmcalc_web\bin
To compile the proxy code, you'll need to navigate to the DOS prompt and type the following command for the Visual Basic.NET compiler:
vbc.exe /out:bin\pmcalc.dll /target:library /reference:system.xml.serialization.dll /reference:system.web.services.dll pmcalc.vb
If everything worked correctly, you will see the following message:
Microsoft (R) Visual Basic.NET Compiler version 7.00.9030 for Microsoft (R) .NET Framework Common Language Runtime version 1.00.2204.21 Copyright (C) Microsoft Corp 2000. All rights reserved.
For the C# compiler, enter this command:
csc.exe /out:bin\pmcalc.dll /target:library /reference:system.xml.serialization.dll /reference:system.web.services.dll pmcalc.cs
If you have typed in the command correctly, you should see the following confirmation message:
Microsoft (R) Visual C# Compiler Version 7.00.9030 [CLR version 1.00.2204.21] Copyright (C) Microsoft Corp 2000. All rights reserved.
Chapter 6, "How ASP.NET Works," explains in more detail what the compiler does. Briefly, the compiler does not compile your source code into native machine-level code. Instead, it creates an assembly (.dll file) containing Intermediate Language that's later compiled into machine language code by a "Just In Time" compiler specific to your operating system and computer chip.