Publishing and Consuming Web Services

This section presents several examples of creating (also known as publishing) and using (also known as consuming) Web services. Recall that an application that consumes a Web service actually consists of two partsa proxy class representing the Web service and a client application that accesses the Web service via an instance of the proxy class. The instance of the proxy class passes a Web method's arguments from the client application to the Web service. When the Web method completes its task, the instance of the proxy class receives the result and parses it for the client application. Visual C# 2005 and Visual Web Developer create these proxy classes for you. We demonstrate this momentarily.

22.4.1. Defining the HugeInteger Web Service

Figure 22.9 presents the code-behind file for the HugeInteger Web service that you will build in Section 22.4.2. When creating Web services in Visual Web Developer, you work almost exclusively in the code-behind file. As we mentioned earlier, this Web service is designed to perform calculations with integers that have a maximum of 100 digits. long variables cannot handle integers of this size (i.e., an overflow occurs). The Web service provides methods that take two "huge integers" (represented as strings) and determine their sum, their difference, which one is larger or smaller and whether the two numbers are equal. You can think of these methods as services available to programmers of other applications via the Web (hence the term Web services). Any programmer can access this Web service, use the methods and thus avoid writing 172 lines of code.

Figure 22.9. HugeInteger Web service.

1 // Fig. 22.9: HugeInteger.cs 2 // HugeInteger Web service performs operations on large integers. 3 using System; 4 using System.Web; 5 using System.Web.Services; 6 using System.Web.Services.Protocols; 7 8 [ WebService( Namespace = "http://www.deitel.com/", 9 Description = "A Web service that provides methods for" + 10 " manipulating large integer values" ) ] 11 [ WebServiceBinding( ConformsTo = WsiProfiles.BasicProfile1_1 ) ] 12 public class HugeInteger : System.Web.Services.WebService 13 { 14 private const int MAXIMUM = 100; // maximum number of digits 15 public int[] number; // array representing the huge integer 16 17 // default constructor 18 public HugeInteger() 19 { 20 number = new int[ MAXIMUM ]; 21 } // end default constructor 22 23 // indexer that accepts an integer parameter 24 public int this[ int index ] 25 { 26 get 27 { 28 return number[ index ]; 29 } // end get 30 31 set 32 { 33 number[ index ] = value; 34 } // end set 35 } // end indexer 36 37 // returns string representation of HugeInteger 38 public override string ToString() 39 { 40 string returnString = ""; 41 42 foreach ( int i in number ) 43 returnString = i + returnString; 44 45 return returnString; 46 } // end method ToString 47 48 // creates HugeInteger based on argument 49 public static HugeInteger FromString( string value ) 50 { 51 // create temporary HugeInteger to be returned by the method 52 HugeInteger parsedInteger = new HugeInteger(); 53 54 for ( int i = 0 ; i < value.Length; i++ ) 55 parsedInteger[ i ] = Int32.Parse( 56 value[ value.Length - i - 1 ].ToString() ); 57 58 return parsedInteger; 59 } // end method FromString 60 61 // WebMethod that adds integers represented by the string arguments 62 [ WebMethod( Description = "Adds two huge integers." ) ] 63 public string Add( string first, string second ) 64 { 65 int carry = 0; 66 HugeInteger operand1 = HugeInteger.FromString( first ); 67 HugeInteger operand2 = HugeInteger.FromString( second ); 68 HugeInteger result = new HugeInteger(); // stores result of addition 69 70 // perform addition algorithm for each digit 71 for ( int i = 0; i < MAXIMUM; i++ ) 72 { 73 // add two digits in same column, 74 // result is their sum plus carry from 75 // previous operation modulo 10 76 result[ i ] = 77 ( operand1[ i ] + operand2[ i ] + carry ) % 10; 78 79 // set carry to remainder of dividing sums of two digits by 10 80 carry = ( operand1[ i ] + operand2[ i ] + carry ) / 10; 81 } // end for 82 83 return result.ToString(); 84 } // end method Add 85 86 // WebMethod that subtracts integers 87 // represented by the string arguments 88 [ WebMethod( Description = "Subtracts two huge integers." ) ] 89 public string Subtract( string first, string second ) 90 { 91 HugeInteger operand1 = HugeInteger.FromString( first ); 92 HugeInteger operand2 = HugeInteger.FromString( second ); 93 HugeInteger result = new HugeInteger(); 94 95 // subtract bottom digit from top digit 96 for ( int i = 0; i < MAXIMUM; i++ ) 97 { 98 // if top digit is smaller than bottom digit we need to borrow 99 if ( operand1[ i ] < operand2[ i ] ) 100 Borrow( operand1, i ); 101 102 // subtract bottom from top 103 result[ i ] = operand1[ i ] - operand2[ i ]; 104 } // end for 105 106 return result.ToString(); 107 } // end method Subtract 108 109 // borrow 1 from next digit 110 private void Borrow( HugeInteger hugeInteger, int place ) 111 { 112 // if no place to borrow from, signal problem 113 if ( place >= MAXIMUM - 1 ) 114 throw new ArgumentException(); 115 116 // otherwise if next digit is zero, borrow from column to left 117 else if ( hugeInteger[ place + 1 ] == 0 ) 118 Borrow( hugeInteger, place + 1 ); 119 120 // add ten to current place because we borrowed and subtract 121 // one from previous digit--this is the digit we borrowed from 122 hugeInteger[ place ] += 10; 123 hugeInteger[ place + 1 ]--; 124 } // end method Borrow 125 126 // WebMethod that returns true if first integer is bigger than second 127 [ WebMethod( Description = "Determines whether the first integer is " + 128 "larger than the second integer." ) ] 129 public bool Bigger( string first, string second ) 130 { 131 char[] zeros = { '0' }; 132 133 try 134 { 135 // if elimination of all zeros from result 136 // of subtraction is an empty string, 137 // numbers are equal, so return false, otherwise return true 138 if ( Subtract( first, second ).Trim( zeros ) == "" ) 139 return false; 140 else 141 return true; 142 } // end try 143 // if ArgumentException occurs, 144 // first number was smaller, so return false 145 catch ( ArgumentException exception ) 146 { 147 return false; 148 } // end catch 149 } // end method Bigger 150 151 // WebMethod returns true if first integer is smaller than second 152 [ WebMethod( Description = "Determines whether the first integer " + 153 "is smaller than the second integer." ) ] 154 public bool Smaller( string first, string second ) 155 { 156 // if second is bigger than first, then first is smaller than second 157 return Bigger( second, first ); 158 } // end method Smaller 159 160 // WebMethod that returns true if two integers are equal 161 [ WebMethod( Description = "Determines whether the first integer " + 162 "is equal to the second integer." ) ] 163 public bool EqualTo( string first, string second ) 164 { 165 // if either first is bigger than second, 166 // or first is smaller than second, they are not equal 167 if ( Bigger( first, second ) || Smaller( first, second ) ) 168 return false; 169 else 170 return true; 171 } // end method EqualTo 172 } // end class HugeInteger

Lines 810 contain a WebService attribute. Attaching this attribute to a Web service class declaration allows you to specify the Web service's namespace and description. Like an XML namespace (see Section 19.4), a Web service's namespace is used by client applications to differentiate that Web service from others available on the Web. Line 8 assigns http://www.deitel.com as the Web service's namespace using the WebService attribute's Namespace property. Lines 910 use the WebService attribute's Description property to describe the Web service's purposethis appears in the ASMX page (Fig. 22.2).

Visual Web Developer places line 11 in all newly created Web services. This line indicates that the Web service conforms to the Basic Profile 1.1 (BP 1.1) developed by the Web Services Interoperability Organization (WS-I), a group dedicated to promoting interoperability among Web services developed on different platforms with different programming languages. BP 1.1 is a document that defines best practices for various aspects of Web service creation and consumption (www.WS-I.org). As we discussed in Section 22.2, the .NET environment hides many of these details from you. Setting the WebServiceBinding attribute's ConformsTo property to WsiProfiles.BasicProfile1_1 instructs Visual Web Developer to perform its "behind-the-scenes" work, such as generating WSDL and ASMX files, in conformance with the guidelines laid out in BP 1.1. For more information on Web services interoperabilty and the Basic Profile 1.1, visit the WS-I Web site at www.ws-i.org.

By default, each new Web service class created in Visual Web Developer inherits from class System.Web.Services.WebService (line 12). Although a Web service need not derive from class WebService, this class provides members that are useful in determining information about the client and the Web service itself. Several methods in class HugeInteger are tagged with the WebMethod attribute (lines 62, 88, 127, 152 and 161), which exposes a method so that it can be called remotely. When this attribute is absent, the method is not accessible to clients that consume the Web service. Note that this attribute, like the WebService attribute, contains a Description property that allows the ASMX page to display information about the method (see these descriptions shown in Fig. 22.2).

Common Programming Error 22 1

Failing to expose a method as a Web method by declaring it with the WebMethod attribute prevents clients of the Web service from accessing the method.

Portability Tip 22 1

Specify a namespace for each Web service so that it can be uniquely identified by clients. In general, you should use your company's domain name as the Web service's namespace, since company domain names are guaranteed to be unique.

Portability Tip 22 2

Specify descriptions for a Web service and its Web methods so that the Web service's clients can view information about the service in the service's ASMX page.

Common Programming Error 22 2

No method with the WebMethod attribute can be declared staticfor a client to access a Web method, an instance of that Web service must exist.

Lines 2435 define an indexer, which enables us to access any digit in a HugeInteger. Lines 6284 and 88107 define Web methods Add and Subtract, which perform addition and subtraction, respectively. Method Borrow (lines 110124) handles the case in which the digit that we are currently examining in the left operand is smaller than the corresponding digit in the right operand. For instance, when we subtract 19 from 32, we usually examine the numbers in the operands digit-by-digit, starting from the right. The number 2 is smaller than 9, so we add 10 to 2 (resulting in 12). After borrowing, we can subtract 9 from 12, resulting in 3 for the rightmost digit in the solution. We then subtract 1 from the 3 in 32the next digit to the left (i.e., the digit we borrowed from). This leaves a 2 in the tens place. The corresponding digit in the other operand is now the 1 in 19. Subtracting 1 from 2 yields 1, making the corresponding digit in the result 1. The final result, when the digits are put together, is 13. Method Borrow is the method that adds 10 to the appropriate digits and subtracts 1 from the digits to the left. This is a utility method that is not intended to be called remotely, so it is not qualified with attribute WebMethod.

Recall that Fig. 22.2 presented a screen capture of the ASMX page HugeInteger.asmx for which the code-behind file HugeInteger.cs (Fig. 22.9) defines Web methods. A client application can invoke only the five methods listed in the screen capture in Fig. 22.2 (i.e., the methods qualified with the WebMethod attribute in Fig. 22.9).

22.4.2. Building a Web Service in Visual Web Developer

We now show you how to create the HugeInteger Web service. In the following steps, you will create an ASP.NET Web Service project that executes on your computer's local IIS Web server. To create the HugeInteger Web service in Visual Web Developer, perform the following steps:

Step 1: Creating the Project

To begin, we must create a project of type ASP.NET Web Service. Select File > New Web Site... to display the New Web Site dialog (Fig. 22.10). Select ASP.NET Web Service in the Templates pane. Select HTTP from the Location drop-down list to indicate that the files should be placed on a Web server. By default, Visual Web Developer indicates that it will place the files on the local machine's IIS Web server in a virtual directory named WebSite (http://localhost/WebSite). Replace the name WebSite with HugeInteger for this example. Next, select Visual C# from the Language drop-down list to indicate that you will use Visual C# to build this Web service. Visual Web Developer places the Web service project's solution file (.sln) in the Projects subfolder within the current Windows user's My DocumentsVisual Studio 2005 folder. If you do not have access to an IIS Web server to build and test the examples in this chapter, you can select File System from the Location drop-down list. In this case, Visual Web Developer will place your Web service's files on your local hard disk. You will then be able to test the Web service using Visual Web Developer's built-in Web server.

Figure 22.10. Creating an ASP.NET Web Service in Visual Web Developer.

Step 2: Examining the Newly Created Project

When the project is created, the code-behind file Service.cs, which contains code for a simple Web service (Fig. 22.11) is displayed by default. If the code-behind file is not open, it can be opened by double clicking the file in the App_Code directory listed in the Solution Explorer. Visual Web Developer includes four using declarations that are helpful for developing Web services (lines 14). By default, a new code-behind file defines a class named Service that is marked with the WebService and WebServiceBinding attributes (lines 67). The class contains a sample Web method named HelloWorld (lines 1417). This method is a placeholder that you will replace with your own method(s).

Figure 22.11. Code view of a Web service.

 

Step 3: Modifying and Renaming the Code-Behind File

To create the HugeInteger Web service developed in this section, modify Service.cs by replacing all of the sample code provided by Visual Web Developer with all of the code from the HugeInteger code-behind file (Fig. 22.9). Then rename the file HugeInteger.cs (by right clicking the file in the Solution Explorer and choosing Rename).

Step 4: Examining the ASMX File

The Solution Explorer lists one fileService.asmxin addition to the code-behind file. Recall from Fig. 22.2 that a Web service's ASMX page, when accessed through a Web browser, displays information about the Web service's methods and provides access to the Web service's WSDL information. However, if you open the ASMX file on disk, you will see that it actually contains only

<%@ WebService Language="C#" CodeBehind="~/App_Code/Service.cs" Class="Service" %>

to indicate the programming language in which the Web service's code-behind file is written, the code-behind file's location and the class that defines the Web service. When you request the ASMX page through IIS, ASP.NET uses this information to generate the content displayed in the Web browser (i.e., the list of Web methods and their descriptions).

Step 5: Modifying the ASMX File

Whenever you change the name of the code-behind file or the name of the class that defines the Web service, you must modify the ASMX file accordingly. Thus, after defining class HugeInteger in the code-behind file HugeInteger.cs, modify the ASMX file to contain the lines

<%@ WebService Language="C#" CodeBehind="~/App_Code/HugeInteger.cs" Class="HugeInteger" %>

Error Prevention Tip 22 2

Update the Web service's ASMX file appropriately whenever the name of a Web service's codebehind file or the class name changes. Visual Web Developer creates the ASMX file, but does not automatically update it when you make changes to other files in the project.

 

Step 6: Renaming the ASMX File

The final step in creating the HugeInteger Web service is to rename the ASMX file HugeInteger.asmx.

22.4.3. Deploying the HugeInteger Web Service

The Web service is already deployed because we created the HugeInteger Web service directly on our computer's local IIS server. You can choose Build Web Site from the Build menu to ensure that the Web service compiles without errors. You can also test the Web service directly from Visual Web Developer by selecting Start Without Debugging from the Debug menu. This opens a browser window that contains the ASMX page shown in Fig. 22.2. Clicking the link for a particular HugeInteger Web service method displays a Web page like the one in Fig. 22.4 that allows you to test the method. Note that you can also access the Web service's ASMX page from your computer by typing the following URL in a Web browser

http://localhost/HugeInteger/HugeInteger.asmx

 

Accessing the HugeInteger Web Service's ASMX Page from Another Computer

Eventually, you will want other clients to be able to access and use your Web service. If you deploy the Web service on an IIS Web server, a client can connect to that server to access the Web service with a URL of the form

http://host/HugeInteger/HugeInteger.asmx

where host is the hostname or IP address of the Web server. To access the Web service from another computer in your company's or school's local area network, you can replace host with the actual name of the computer on which IIS is running.

If you have the Windows XP Service Pack 2 operating system on the computer running IIS, that computer may not allow requests from other computers by default. If you wish to allow other computers to connect to your computer's Web server, perform the following steps:

 

1.

Select Start > Control Panel to open your system's Control Panel window, then double click Windows Firewall to view the Windows Firewall settings dialog.

 

2.

In the Windows Firewall settings dialog, click the Advanced tab, select Local Area Connection (or your network connection's name, if it is different) in the Network Connection Settings list box and click the Settings... button to display the Advanced Settings dialog.

 

3.

In the Advanced Settings dialog, ensure that the checkbox for Web Server (HTTP) is checked to allow clients on other computers to submit requests to your computer's Web server.

 

4.

Click OK in the Advanced Settings dialog, then click OK in the Windows Firewall settings dialog.

 

Accessing the HugeInteger Web Service's ASMX Page When the Web Service Executes in Visual Web Developer's Built-in Web Server

Recall from Step 1 of Section 22.4.2 that if you do not have access to an IIS server to deploy and test your Web service, you can create the Web service on your computer's hard disk and use Visual Web Developer's built-in Web server to test the Web service. In this case, when you select Start Without Debugging from the Debug menu, Visual Web Developer executes its built-in Web server, then opens a Web browser containing the Web service's ASMX page so that you can test the Web service.

Web servers typically receive requests on port 80. To ensure that Visual Web Developer's built-in Web server does not conflict with another Web server running on your local computer, Visual Web Developer's Web server receives requests on a randomly selected port number. When a Web server receives requests on a port number other than port 80, the port number must be specified as part of the request. In this case, the URL to access the HugeInteger Web service's ASMX page would be of the form

http://host:portNumber/HugeInteger/HugeInteger.asmx

where host is the hostname or IP address of the computer on which Visual Web Developer's built-in Web server is running and portNumber is the specific port on which the Web server receives requests. You can see this port number in your Web browser's Address field when you test the Web service from Visual Web Developer. Unfortunately, Web services executed using Visual Web Developer's built-in server cannot be accessed over a network.

22.4.4. Creating a Client to Consume the HugeInteger Web Service

Now that we have defined and deployed our Web service, we demonstrate how to consume it from a client application. In this section, you will create a Windows application as the client using Visual C# 2005. After creating the client application, you will add a proxy class to the project that allows the client to access the Web service. Recall that the proxy class (or proxy) is generated from the Web service's WSDL file and enables the client to call Web methods over the Internet. The proxy class handles all the details of communicating with the Web service. The proxy class is hidden from you by defaultyou can view it in the Solution Explorer by clicking the Show All Files button. The proxy class's purpose is to make clients think that they are calling the Web methods directly.

This example demonstrates how to create a Web service client and generate a proxy class that allows the client to access the HugeInteger Web service. You will begin by creating a project and adding a Web reference to it. When you add the Web reference, Visual C# 2005 will generate the appropriate proxy class. You will then create an instance of the proxy class and use it to call the Web service's methods. First, create a Windows application in Visual C# 2005, then perform the following steps:

Step 1: Opening the Add Web Reference Dialog

Right click the project name in the Solution Explorer and select Add Web Reference... (Fig. 22.12).

Figure 22.12. Adding a Web service reference to a project.

 

Step 2: Locating Web Services on Your Computer

In the Add Web Reference dialog that appears (Fig. 22.13), click Web services on the local machine to locate Web references stored on the IIS Web server on your local computer (http://localhost). This server's files are located at C:Inetpubwwwroot by default. Note that the Add Web Reference dialog allows you to search for Web services in several different locations. Many companies that provide Web services simply distribute the exact URLs at which their Web services can be accessed. For this reason, the Add Web Reference dialog also allows you to enter the specific URL of a Web service in the URL field.

Figure 22.13. Add Web Reference dialog.

(This item is displayed on page 1184 in the print version)

 

Step 3: Choosing the Web Service to Reference

Select the HugeInteger Web service from the list of available Web services (Fig. 22.14).

Figure 22.14. Web services located on localhost.

(This item is displayed on page 1184 in the print version)

 

Step 4: Adding the Web Reference

Add the Web reference by clicking the Add Reference button (Fig. 22.15).

Figure 22.15. Web reference selection and description.

(This item is displayed on page 1185 in the print version)

 

Step 5: Viewing the Web Reference in the Solution Explorer

The Solution Explorer (Fig. 22.16) should now contain a Web References folder with a node named after the domain name where the Web service is located. In this case, the name is localhost because we are using the local Web server. When we reference class HugeInteger in the client application, we will do so through the localhost namespace.

Figure 22.16. Solution Explorer after adding a Web reference to a project.

(This item is displayed on page 1185 in the print version)

 

Notes on Creating a Client to Consume a Web Service

The steps we just presented also apply to adding Web references to Web applications created in Visual Web Developer. We present a Web application that consumes a Web service in Section 22.6.

When creating a client to consume a Web service, add the Web reference first so that Visual C# 2005 (or Visual Web Developer) can recognize an object of the Web service proxy class. Once you add the Web reference to the client, it can access the Web service through an object of the proxy class. The proxy class (named HugeInteger) is located in namespace localhost, so you must use localhost.HugeInteger to reference this class. Although you must create an object of the proxy class to access the Web service, you do not need access to the proxy class's code. As we show in Section 22.4.5, you can invoke the proxy object's methods as if it were an object of the Web service class.

The steps that we described in this section work well if you know the appropriate Web service reference. However, what if you are trying to locate a new Web service? Two common technologies facilitate this processUniversal Description, Discovery and Integration (UDDI) and Discovery of Web services (DISCO). We discussed DISCO in Section 22.2. UDDI is an ongoing project for developing a set of specifications that define how Web services should be published so that programmers searching for Web services can find them. Microsoft and its partners are working on this project to help programmers locate Web services that conform to certain specifications, allowing developers to find Web services through search engines similar to Yahoo!® and Google™. You can learn more about UDDI and view a demonstration by visiting www.uddi.org and uddi.microsoft.com. These sites contain search tools that make finding Web services convenient.

22.4.5. Consuming the HugeInteger Web Service

The Windows Form in Fig. 22.17 uses the HugeInteger Web service to perform computations with positive integers up to 100 digits long. Line 22 declares variable remoteInteger of type localhost.HugeInteger. This variable is used in each of the application's event handlers to call methods of the HugeInteger Web service. The proxy object is created and assigned to this variable at line 31 in the Form's Load event handler. Lines 5253, 6667, 9596, 116117 and 135136 in the various button event handlers invoke methods of the Web service. Note that each call is made on the local proxy object, which then communicates with the Web service on the client's behalf. If you downloaded the example from www.deitel.com/books/csharpforprogrammers2, you might need to regenerate the proxy by removing the Web reference, then adding it again. To do so, right click localhost in the WebReferences folder in the Solution Explorer and select option Delete. Then follow the instructions in the preceding section to add the Web reference to the project.

Figure 22.17. Using the HugeInteger Web service.

1 // Fig. 22.17: UsingHugeIntegerService.cs 2 // Using the HugeInteger Web Service. 3 using System; 4 using System.Collections.Generic; 5 using System.ComponentModel; 6 using System.Data; 7 using System.Drawing; 8 using System.Text; 9 using System.Windows.Forms; 10 using System.Web.Services.Protocols; 11 12 namespace UsingHugeIntegerWebService 13 { 14 public partial class UsingHugeIntegerServiceForm : Form 15 { 16 public UsingHugeIntegerServiceForm() 17 { 18 InitializeComponent(); 19 } // end constructor 20 21 // declare a reference to Web service 22 private localhost.HugeInteger remoteInteger; 23 24 private char[] zeros = { '0' }; // character to trim from strings 25 26 // instantiates object to interact with Web service 27 private void UsingHugeIntegerServiceForm_Load( object sender, 28 EventArgs e ) 29 { 30 // instantiate remoteInteger 31 remoteInteger = new localhost.HugeInteger(); 32 } // end method UsingHugeIntegerServiceForm_Load 33 34 // adds two numbers input by user 35 private void addButton_Click( object sender, EventArgs e ) 36 { 37 // make sure numbers do not exceed 100 digits and that both 38 // are not 100 digits long, which would result in overflow 39 if ( firstTextBox.Text.Length > 100 || 40 secondTextBox.Text.Length > 100 || 41 ( firstTextBox.Text.Length == 100 && 42 secondTextBox.Text.Length == 100) ) 43 { 44 MessageBox.Show( "HugeIntegers must not be more " + 45 "than 100 digits Both integers cannot be " + 46 "of length 100: this causes an overflow", "Error", 47 MessageBoxButtons.OK, MessageBoxIcon.Information ); 48 return; 49 } // end if 50 51 // perform addition 52 resultLabel.Text = remoteInteger.Add( 53 firstTextBox.Text, secondTextBox.Text ).TrimStart( zeros ); 54 } // end method addButton_Click 55 56 // subtracts two numbers input by user 57 private void subtractButton_Click( object sender, EventArgs e ) 58 { 59 // make sure HugeIntegers do not exceed 100 digits 60 if ( SizeCheck( firstTextBox, secondTextBox ) ) 61 return; 62 63 // perform subtraction 64 try 65 { 66 string result = remoteInteger.Subtract( 67 firstTextBox.Text, secondTextBox.Text ).TrimStart( zeros ); 68 69 if ( result == "" ) 70 resultLabel.Text = "0"; 71 else 72 resultLabel.Text = result; 73 74 } // end try 75 76 // if WebMethod throws an exception, 77 // then first argument was smaller than second 78 catch ( SoapException exception ) 79 { 80 MessageBox.Show( 81 "First argument was smaller than the second" ); 82 } // end catch 83 } // end method subtractButton_Click 84 85 // determines whether first number 86 // input by user is larger than second 87 private void largerButton_Click( object sender, EventArgs e ) 88 { 89 // make sure HugeIntegers do not exceed 100 digits 90 if ( SizeCheck( firstTextBox, secondTextBox ) ) 91 return; 92 93 // call Web-service method to determine if 94 // first integer is larger than the second 95 if ( remoteInteger.Bigger( firstTextBox.Text, 96 secondTextBox.Text ) ) 97 resultLabel.Text = firstTextBox.Text.TrimStart( zeros ) + 98 " is larger than " + 99 secondTextBox.Text.TrimStart( zeros ); 100 else 101 resultLabel.Text = firstTextBox.Text.TrimStart( zeros ) + 102 " is not larger than " + 103 secondTextBox.Text.TrimStart( zeros ); 104 } // end method largerButton_Click 105 106 // determines whether first number 107 // input by user is smaller than second 108 private void smallerButton_Click( object sender, EventArgs e ) 109 { 110 // make sure HugeIntegers do not exceed 100 digits 111 if ( SizeCheck( firstTextBox, secondTextBox ) ) 112 return; 113 114 // call Web-service method to determine if 115 // first integer is smaller than second 116 if ( remoteInteger.Smaller( firstTextBox.Text, 117 secondTextBox.Text ) ) 118 resultLabel.Text = firstTextBox.Text.TrimStart( zeros ) + 119 " is smaller than " + 120 secondTextBox.Text.TrimStart( zeros ); 121 else 122 resultLabel.Text = firstTextBox.Text.TrimStart( zeros ) + 123 " is not smaller than " + 124 secondTextBox.Text.TrimStart( zeros ); 125 } // end method smallerButton_Click 126 127 // determines whether two numbers input by user are equal 128 private void equalButton_Click( object sender, EventArgs e ) 129 { 130 // make sure HugeIntegers do not exceed 100 digits 131 if ( SizeCheck( firstTextBox, secondTextBox ) ) 132 return; 133 134 // call Web-service method to determine if integers are equal 135 if ( remoteInteger.EqualTo( firstTextBox.Text, 136 secondTextBox.Text ) ) 137 resultLabel.Text = firstTextBox.Text.TrimStart( zeros ) + 138 " is equal to " + secondTextBox.Text.TrimStart( zeros ); 139 else 140 resultLabel.Text = firstTextBox.Text.TrimStart( zeros ) + 141 " is not equal to " + 142 secondTextBox.Text.TrimStart( zeros ); 143 } // end method equalButton_Click 144 145 // determines whether numbers input by user are too big 146 private bool SizeCheck( TextBox first, TextBox second ) 147 { 148 // display an error message if either number has too many digits 149 if ( ( first.Text.Length > 100 ) || 150 ( second.Text.Length > 100 ) ) 151 { 152 MessageBox.Show( "HugeIntegers must be less than 100 digits", 153 "Error", MessageBoxButtons.OK, MessageBoxIcon.Information); 154 return true; 155 } // end if 156 157 return false; 158 } // end method SizeCheck 159 } // end class UsingHugeIntegerServiceForm 160 } // end namespace UsingHugeIntegerWebService

The user inputs two integers, each up to 100 digits long. Clicking a button causes the application to invoke a Web method to perform the appropriate task and return the result. Note that client application UsingHugeIntegerService cannot perform operations using 100-digit numbers directly. Instead the application creates string representations of these numbers and passes them as arguments to Web methods that handle such tasks for the client. It then uses the return value of each operation to display an appropriate message.

Note that the application eliminates leading zeros in the numbers before displaying them by calling string method trimStart. Like string method TRim (discussed in Chapter 16), trimStart removes all occurrences of characters specified by a char array (line 24) from the beginning of a string.

Категории