In this article I will show how to call ASP.NET webservice using jQuery. Webservice call using jQuery will let you to prevent the re-rendering the entire content of the page. The request is made partially and you can replace the content of the page without postback. Thus increasing usability and leads to less data transfer for the same cause. In order to call webservice you need to keep two things in mind:
The example I have taken to show how to call ASP.NET webservice is in this way:
Let's start with database part first and create a sample table say "Users" and insert data into it. Below is the script for it:
CREATE TABLE [Users] ( [UserID] INT IDENTITY , [UserName] NVARCHAR(50), [FirstName] NVARCHAR(50), [LastName] NVARCHAR(50), [MiddleName] NVARCHAR(50), [EmailID] NVARCHAR(50) ) GO INSERT INTO Users ( UserName , FirstName , LastName , MiddleName , EmailID ) SELECT dbo.GenerateRandomName(10), dbo.GenerateRandomName(10), dbo.GenerateRandomName(10), dbo.GenerateRandomName(10), dbo.GenerateRandomName(10)+'@'+ dbo.GenerateRandomName(3)+'.com' GO 500
Above you must be wondering what is "GenerateRandomName" function ? I have used that user defined function so as to create a random name and by "GO 500" I have made the insert script to run 500 times. Below is the script of function. Note in this function I have used "RandNumberView" View. Because I need to use the random number if I had used the rand() simply in the function I would have received this error "Invalid use of side-effecting or time-dependent operator in 'rand' within a function". Below is the script for it:
CREATE FUNCTION [GenerateRandomName] ( @LENGTH INT ) RETURNS NVARCHAR(255) AS BEGIN --DECLARE VARIABLES DECLARE @RandomNumber NVARCHAR(255) DECLARE @I SMALLINT DECLARE @RandNumber FLOAT DECLARE @Position TINYINT DECLARE @ExtractedCharacter VARCHAR(1) DECLARE @ValidCharacters VARCHAR(255) DECLARE @VCLength INT --SET VARIABLES VALUE SET @ValidCharacters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' SET @VCLength = LEN(@ValidCharacters) SET @ExtractedCharacter = '' SET @RandNumber = 0 SET @Position = 0 SET @RandomNumber = '' SET @I = 1 WHILE @I < ( @Length + 1 ) BEGIN SET @RandNumber = ( SELECT RandNumber FROM [RandNumberView] ) SET @Position = CONVERT(TINYINT, ( ( @VCLength - 1 ) * @RandNumber + 1 )) SELECT @ExtractedCharacter = SUBSTRING(@ValidCharacters, @Position, 1) SET @I = @I + 1 SET @RandomNumber = @RandomNumber + @ExtractedCharacter END RETURN @RandomNumber END GO CREATE VIEW [RandNumberView] AS SELECT RAND() AS [RandNumber]
After running the insert script shown above you will see the following screen in the message window of query analyzer which will be telling you "Batch execution completed 500 times" which means we have inserted 500 rows in our "Users" table.
To verify it let's run the select query on "Users" table and you will see the below screen after running it. I have just displayed the screen for few records so as to get it fit in this article.Let's start making a stored procedure for selecting the records from "Users" table based on the input. Here the searching will be done based on username column. User will type some keyword and based on that keyword records will be selected.
CREATE PROC [SelectUsers] @UserName NVARCHAR(100) AS BEGIN SELECT UserID , UserName , FirstName , LastName , MiddleName , EmailID FROM Users WHERE UserName LIKE ( @UserName + '%' ) END GO
The above portion was of database end. Now let's come to frontend portion. Let's start with making a business class for users. Create a class and name it "User.cs". Below is the code for it:
using System; [Serializable] public class User { public int UserID { get; set; } public string UserName { get; set; } public string FirstName { get; set; } public string LastName { get; set; } public string MiddleName { get; set; } public string EmailID { get; set; } }
Now we will be creating a webservice which will act as the middle man between the database and aspx (cliient side) . Lets create a new webservice and name it "Sample.asmx"
Below is the complete code for it:
using System; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Data; using System.Data.SqlClient; using System.Web.Services; /// <summary> /// Summary description for Sample /// </summary> [WebService(Namespace = "http://tempuri.org/")] [WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)] [System.ComponentModel.ToolboxItem(false)] // To allow this Web Service to be called from script, using ASP.NET AJAX, uncomment the following line. [System.Web.Script.Services.ScriptService] public class Sample : System.Web.Services.WebService { [WebMethod] public IEnumerable<User> FindUsers(string userName) { Collection<User> users = new Collection<User>(); string connectionString = "Data Source=YourServerName; Initial Catalog=YourDatabase; User ID=YourUserName; Password=YourPassword"; using (SqlConnection connection = new SqlConnection(connectionString)) { using (SqlCommand command = new SqlCommand()) { command.Connection = connection; command.CommandText = "SelectUsers"; command.CommandType = CommandType.StoredProcedure; SqlParameter paramUserName = new SqlParameter("@UserName", SqlDbType.NVarChar, 50); paramUserName.Value = userName; command.Parameters.Add(paramUserName); connection.Open(); using (SqlDataReader dataReader = command.ExecuteReader()) { User user; if (dataReader != null) while (dataReader.Read()) { user = new User(); user.UserID = (int)dataReader["UserID"]; user.UserName = Convert.ToString(dataReader["UserName"]); user.FirstName = Convert.ToString(dataReader["FirstName"]); user.LastName = Convert.ToString(dataReader["LastName"]); user.MiddleName = Convert.ToString(dataReader["MiddleName"]); user.EmailID = Convert.ToString(dataReader["EmailID"]); users.Add(user); } } } } return users; } }
Note that the webservice should be marked with [System.Web.Script.Services.ScriptService] attribute. From http://msdn.microsoft.com/en-us/library/system.web.script.services.scriptserviceattribute(v=VS.90).aspx ScriptServiceAttribute Class indicates that a Web service can be invoked from script. This class cannot be inherited.To invoke a Web service method from ECMAScript (JavaScript), you must apply the ScriptServiceAttribute attribute to the related Web service class. When you apply ScriptServiceAttribute to a Web service class definition that contains one or more methods with WebMethodAttribute applied, the proxy generation script creates a proxy object that corresponds to the Web service class.Also the method should be marked with [WebMethod] attribute. From http://msdn.microsoft.com/en-us/library/system.web.services.webmethodattribute.aspx Adding this attribute to a method within an XML Web service created using ASP.NET makes the method callable from remote Web clients. This class cannot be inherited. From client we are going to call "FindUsers" method of this webservice with "username" of string type as the input parameter. This method will hit the database and bring the results based on the input parameter and return them to the client in JSON format. Why JSON? From http://msdn.microsoft.com/en-us/library/bb515101.aspx: Call Web services by using the HTTP POST verb. A POST request has a body that contains the data that the browser sends to the server. It does not have a size limitation. Therefore, you can use a POST request when the size of the data exceeds the intrinsic size limitation for a GET request. The client serializes the request into JSON format and sends it as POST data to the server. The server deserializes the JSON data into .NET Framework types and makes the actual Web service call. During the response, the server serializes the return values and passes them back to the client, which deserializes them into JavaScript objects for processing.Now let's come to the client side, caller page aspx one. Lets create a aspx page and name it "Sample.aspx". Below is the complete code for it:
<html xmlns="http://www.w3.org/1999/xhtml"> <head id="Head1" runat="server"> <title></title> <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.4.2/jquery.min.js"> </script> <script type="text/javascript"> $(function () { $('#<%= btnFoo.ClientID %>').click(function () { $('#foo').html('Loading...') $.ajax({ type: 'POST', url: 'Sample.asmx/FindUsers', data: '{userName: \'' + $('#<%= txtTest.ClientID %>').val() + '\'}', contentType: 'application/json; charset=utf-8', dataType: 'json', success: function (response) { if (response != null && response.d != null) { successHandler(response.d); } } }); return false;//Prevent postback }); function successHandler(data) { var html = buildHtml(data); $('#foo').html(html); } function buildHtml(data) { var html = '<table><tr><th>UserID</th><th>UserName</th>\ <th>FirstName</th><th>MiddleName</th><th>LastName</th><th>EmailID</th></tr>'; for (var i = 0; i < data.length; i++) { html = html + '<tr>\ <td>' + data[i].UserID + '\ </td>\ <td>' + data[i].UserName + '\ </td>\ <td>' + data[i].FirstName + '\ </td>\ <td>' + data[i].MiddleName + '\ </td>\ <td>' + data[i].LastName + '\ </td>\ <td>' + data[i].EmailID + '\ </td>\ </tr>'; } html = html + '</table>'; return html; } }); </script> </head> <body> <form id="form1" runat="server"> <asp:TextBox ID="txtTest" runat="server"></asp:TextBox> <asp:Button ID="btnFoo" runat="server" Text="Fill" /> <br /> <div id="foo"> </div> </form> </body> </html>
Above when the user clicked the button after typing some keyword, an ajx request is made to the server and records are brought back based on the input text. The following code acts as the template which is to applied on the incoming data:
function buildHtml(data) { var html = '<table><tr><th>UserID</th><th>UserName</th>\ <th>FirstName</th><th>MiddleName</th><th>LastName</th><th>EmailID</th></tr>'; for (var i = 0; i < data.length; i++) { html = html + '<tr>\ <td>' + data[i].UserID + '\ </td>\ <td>' + data[i].UserName + '\ </td>\ <td>' + data[i].FirstName + '\ </td>\ <td>' + data[i].MiddleName + '\ </td>\ <td>' + data[i].LastName + '\ </td>\ <td>' + data[i].EmailID + '\ </td>\ </tr>'; } html = html + '</table>'; return html; }
There are many other ways for templating purpose but that discussion is beyond this article so I have just covered the basic way of doing it. Below are the two screenshots of the Firebug's Console's tab after I typed "a" and "b" and clicked the button.
That's it above we are done with the topic on how to call the webservice using jQuery. Do let me know your feedback, comments.