This article may contain URLs that were valid when originally published, but now link to sites or pages that no longer exist. To maintain the flow of the article, we've left these URLs in the text, but disabled the links.


MIND


This article assumes you're familiar with ASP, DHTML and JScript.
Download the code (14KB)
View Figure 10.

Do Real World Data Analysis With Internet Explorer 4.0 Data Binding
Jason Esser

HTML can be severely limited in its ability to display dynamic data. By combining ASP with the data-binding features of Internet Explorer 4.0, you can overcome this roadblock to create a reliable, compelling data analysis tool.
When's the last time you visited your favorite Web site, found the search page, performed a search, and then sorted through the result set until you actually found the item you were looking for?
      Since the very beginning of the World Wide Web, developers have been trying to get a handle on the best way to link a Web client to the back-end database. Think of what the typical developer has to take into consideration when developing a system that allows users to interact with data. There are several obstacles—limitations of HTML itself, browser bandwidth considerations that limit the amount of data that can be sent to the client in a reasonable period of time, and transactional issues in determining how interactive the data can be. And let's not even get into all of the service issues that can exist on the Web and database servers themselves!
      In fact, if you've ever tried to develop anything for a Web browser that tied into a back-end database, then you probably know that developers have traditionally been very limited by what they can do within the browser. A typical example is the process of searching a list of items stored in a relational database, then sorting and refining the results until the desired item is found. Sounds simple enough, right? Nope.
      In this scenario, the user usually uses some sort of HTML form to specify search criteria. The form is then submitted to the server, which then structures a query, passes it off to some data store, receives the results, and then passes those results back to the Web browser. Subsequent interaction with the data will require the same chain of events to repeat themselves. This process is a typical lowest-common-denominator HTML 2.0 solution. By today's standards, this is ugly.
      What I'll focus on here are how the limitations of HTML itself can, to a large extent, be overcome though the use of Active Server Pages (ASP) and Dynamic HTML (DHTML) data binding to rapidly develop a reliable and compelling data analysis tool.

The Business Problem
      I'm currently working for a consulting company that focuses on developing multitier applications for our clients using Microsoft® technologies almost exclusively. A client recently came to us with an urgent request. They had a database that their employees needed to access on a read-only basis. Access to the data had to be secure and was to exist within their enterprise (intranet) environment only. Employees throughout the United States and Canada needed to be able to search the data according to their own criteria and have useful and speedy interaction with the result set. The application had to be easy to maintain, yet extensible and flexible enough to allow for future enhancements. There was also a strong potential for redeploying the tool within the context of future applications. And, by the way, could we have it done in two weeks time for the national sales meeting? No problem.
      Fortunately for us, the company had an infrastructure and mindset that made this tall order, for the most part, realistic.

  • The client had almost complete control of all 6,000-plus desktops in the enterprise. Windows® 95 was installed on just about every desktop. Different client configurations would not be a major issue.
  • The client's browser was Microsoft Internet Explorer 4.0.
  • Microsoft Internet Information Server (IIS) was their Web server of choice. Because IIS has Windows NT® Challenge/Response as an authentication option, client authentication could be tied directly to the enterprise logon of each user. As a result, security concerns became almost a nonissue.
  • The client had long ago adopted the concept of the browser as a "universal client" for much of their internal application development.

The Business Solution
      Very quickly, it became clear that the logical choice to solve the client's business need was Internet Explorer 4.0 using ASP on the server and DHTML data binding on the client. In addition to the four factors listed previously, there are a couple of other significant reasons why we chose this route. First, ASP and DHTML are relatively easy to learn and use. For each of these technologies, all that the developer needs to be familiar with are object models and how

Figure 1: Microsoft Press Catalog System
Figure 1: Microsoft Press Catalog System

to appropriately script against them. This meant that once the application was deployed, the client's developers could easily maintain and modify the application themselves.
      Second, the Internet Explorer 4.0 data binding features are conducive to online data analysis. Data comes to the browser asynchronously. This means that progressive rendering of data can be done as it is received, which alleviates some of the frustration that users experience while waiting for Web pages to download. An even more attractive feature of data binding in this secure, read-only scenario is the capability to filter or sort the data on the client—within the Web page itself—without having to make round-trips to the server.
      This article does not present a behind-the-scenes view of data binding. For an introductory look at the data binding features of Internet Explorer 4.0, see Rich Rollman's article, "Data Binding in Dynamic HTML" (MIND, July 1997). There are other good sources as well, including the books Inside Dynamic HTML by Scott Isaacs (Microsoft Press, 1998), and Professional IE4 Programming (Wrox Press, 1997).


Figure 2: Sample App

      For the purposes of this article, I've hooked up the solution that we delivered to one of the sample databases that comes with Site Server 3.0 Commerce Edition. The Microsoft Press® database is a good example of a relational database with the same sort of catalog system that was used in the actual client application (see Figure 1).
      The sample application has only four pages: Book Search, Search Results, Search Results Data, and More Information (see Figure 2). I'll focus on the pages that provide the search results listing and how data binding is used in the context of these pages.

rendering of data can be done as it is received, which alleviates some of the frustration that users experience while waiting for Web pages to download. An even more attractive feature of data binding in this secure, read-only scenario is the capability to filter or sort the data on the client—within the Web page itself—without having to make round-trips to the server.
      This article does not present a behind-the-scenes view of data binding. For an introductory look at the data binding features of Internet Explorer 4.0, see Rich Rollman's article, "Data Binding in Dynamic HTML" (MIND, July 1997). There are other good sources as well, including the books Inside Dynamic HTML by Scott Isaacs (Microsoft Press, 1998), and Professional IE4 Programming (Wrox Press, 1997).


                    Figure 3: Book Search Page

The Book Search and More Information Pages
      The first page a user interacts with in this application is the Book Search page (see Figure 3). From this page the user can select from a list of available subjects or authors, as well as search for books by their titles or ISBN. The bottom of the page contains some advanced search options that allow the user to specify how to present the Search Results page. The user can select how they would like to have the results sorted and how many results to display per page.
This is fairly typical search stuff. Once the user has completed entering the data, the Book Search page then sends its form data via a GET to the Search Results page. See Figure 4 for the code that generates the Book Search page.

Figure 5: More Information Page

Figure 5: More Information Page

      The More Information page (see Figure 5) displays details about an item in the result set. It displays all relevant information from Abstract to Publication Date. See Figure 6 for the accompanying code.
      Both the Search Results and More Information pages rely on traditional methods for getting data to the user. The client uses forms to request items from the Web server which, in turn, talks to the database and renders them in the HTML that's returned to the browser. The Search Results pages are a different story.

The Search Results Data Page
      Like the Book Search and More Information pages, this page is also ASP-produced with no DHTML elements on it. Completely unlike those pages, though, this page exists only for the purpose of generating a set of tabular data. The Search Results Data page generates a result set based on the user query and for manipulation by the Search Results page. This is basically a recordset that lives in the form of a dynamically generated text file that can be manipulated on the client-side. The code for this page and its sample output can be seen in Figures 7 and 8.
      The recordset that this page generates is contained in the Tabular Data Control (TDC) Data Source Object (DSO). The TDC, an ActiveX® control that ships with Internet Explorer 4.0, allows developers to embed a recordset based on any text file. This data can be accessed by a URL in any HTML page by specifying the correct <OBJECT> tag to tie into the back-end datasource. In this application, I'm using


 <OBJECT CLASSID="clsid:333C7BC4-460F-11D0-BC04-0080C7055A83" 
     ID="tdcItems" HEIGHT="0" WIDTH="0">
 <PARAM NAME="DataURL"
     VALUE="searchresultsdata.asp?<%=Request.QueryString%>">
 <PARAM NAME="UseHeader" VALUE="True">
 </OBJECT> 
in the Search Results page. In this example, the tabular data is being generated on the fly by the Search Results Data page and is based on the request sent to the Search Results page from the Book Search page. Now let's look at the meat and potatoes behind this application—the Search Results page itself.

The Search Results Page
      The Search Results page allows the user to interact with the data and provides a link back to the Book Search page, as well as a link to find out more information about each line item. You start out with a static HTML page that consists of only an ActiveX control, a header with some information about the page, and a table to display your tabular data.
      Before I dive into the example, I need to point out a couple of things about the Internet Explorer 4.0 data binding architecture. First, there is the concept of a repetition agent. In this case, I'm using an HTML table as a template for the data, which is generated by the repetition agent. It's very easy to set this up. At its simplest, as long as I've specified the correct attributes within my HTML and have a valid recordset (via the TDC DSO), the DHTML data binding agent will handle the work of rendering each row of the repetition agent for each item in the recordset. Again, in this case, the Search Results Data page is generating the recordset.
      The HTML for the table looks something like this:


 <TABLE>
 <TR ID="boundTable" CLASS="rowItem">
     <TD ALIGN="LEFT" CLASS="cellItem">
 <SPAN DATAFLD="Subject"></SPAN>
 </TD>

       <TD ALIGN="LEFT" CLASS="cellItem"> <SPAN DATAFLD="Title" DATAFORMATAS="HTML"></SPAN> </TD> <TD ALIGN="LEFT" CLASS="cellItem"> <SPAN DATAFLD="LastName"></SPAN>, <SPAN DATAFLD="FirstName"></SPAN> </TD> <TD ALIGN="RIGHT" CLASS="cellItem"> <SPAN DATAFLD="PriceDisplay"></SPAN> </TD> <TD ALIGN="CENTER" NOWRAP CLASS="cellItem"> <A DATAFLD="ViewDocUrl">more info...</A> </TD> </TR> </TABLE>
Along with the HTML extensions for data binding, this is the skeleton for a Search Results page. Each <SPAN> and <A> is a data consumer. The DATAFLD attribute within each <SPAN> (or <A>) specifies which column from the TDC-supplied dataset will be displayed in each table cell. You'll also notice a <SPAN> that has a DATAFORMATAS="HTML" attribute. This is another one of the HTML extensions provided by the Internet Explorer 4.0 implementation of DHTML. This tells the browser how to render the data from the TDC. In this case, the Title field contains HTML that needs to be rendered instead of displayed as plain text. This will cause "Microsoft&reg;" to be displayed properly as "Microsoft®". The code for a basic Search Results page is shown in Figure 9. Figure 10 contains the code for a Search Results page that uses ASP.

Binding the Data
      There is one big problem with the previous HTML snippet. There is no link specified between the table and the TDC and, as a result, only an empty table will be displayed (see Figure 11).
Figure 11: Unsuccessful Search
Figure 11: Unsuccessful Search

To link the table to the TDC, you have to specify a data source for the table. In this case, if you substitute <TABLE DATASRC="#tdcItems"> for the <TABLE> tag, the table will render all of the data attached to and contained in the TDC. (#tdcItems refers to the ID of the TDC.) The DATASRC attribute is another HTML extension for data binding. For reasons that I'll get into soon, I'm not going to use this technique to bind my table to the TDC. Instead, I'm going to use JScript to call the Internet Explorer 4.0 binding agent, which binds the data when the page loads with the following statement:


 document.all.item("boundTable").dataSrc = "#tdcItems"; 
(These are two paths to the same result—they both drive the same binding agent.) Again, as soon as I tie the table to the TDC, either through the HTML extensions for data binding or through script, all of the data will be rendered within the page (see Figure 12).

Figure 12: Complete List
Figure 12: Complete List

Adding a UI
      Let's make the data more interactive. If you're like most people, there are very few things worse than sitting on the wrong end of a 28.8 modem connection to some search engine that never seems to give you the results that you want in the first page of data. Wouldn't it be nice if you could receive the data into your page one row at a time and, as soon as the transfer has completed, sort or filter the data according to your needs? After all, that's the very nature of a data analysis tool—allowing the user to manipulate the data on their own terms. This is almost the exact opposite of the typical Web data analysis experience today.
      As a developer, you want your users to have a good experience with the tools you're providing. You can do a few things to enhance the user experience within the browser. DHTML allows for manipulation of just about every element within an HTML page. For example, user feedback items such as status messages and DHTML progress bars can be displayed and removed as needed. What I'm going to look at next is how to add buttons to navigate through a recordset as well as how to add sorting—all with the appropriate visual cues.
      One of the first issues in developing the Search Results page that had to be resolved was how to load the data in the background and sort it quickly before displaying it to the user. (I hinted at this problem earlier.) This is why I'm using JScript for the document.onload event to dynamically bind the data to the table. Before I ever display the data to the user, the data has been sorted, the appropriate visual cues have been turned on and off, and the data about the recordset has been inserted into the HTML. You can see this in the startPage function in Figure 13.
      In this script, I first sort the recordset by the search criteria that the user chose in the Book Search page. If you have any experience with data analysis development, you might think that this should have been done on the server for the sake of speed and efficiency. In most cases, you'd be right. In this situation, the back-end might not sort the data in the same way that the DSO would, and you might not even be dealing with a back-end that has sort capabilities. So, for the sake of consistency, the sort is being done on the client.
      Next, I call the Reset method on the TDC DSO to do the sorting and rerender the table. The table is bound to the TDC and the correct arrow for the initial sort order of the page is displayed. Then the table containing all of these elements (and the data) is made visible. I now have a databound table that renders my entire result set in the browser. Now let's handle the data sorting by each column.
      I'm going to add an onclick event handler to the <TR> for the header row so that the tag looks like this:


 <TR onclick="sortItem(window.event.srcElement)"> 
The sortItem function that handles this event can be found in Figure 14. You'll notice that this function serves two primary purposes. First, it takes the ID of the <TH> that raised the event and compares the current sort state (column and direction) to the requested sort state. Based on this, the data is then sorted. Second, SortItem turns the appropriate arrows on and off to indicate that the sort is ascending or descending for the <TH> that raised the event. Again, after calling the Reset method on the DSO, the data is rerendered within the page in the order that the user has specified.

Flipping the Page
      One of the problems you may run into in developing a solution like this is the rendering speed of the table on the initial load of the page and any subsequent sorts. The problem here is that all of the sorting and rendering is being done by the user's machine, so the sorting and rendering of the data will only be as fast as the machine running the browser. Another issue that has lingered ever since the inception of the <TABLE> tag (again, in HTML 2.0) has been the browser's painstakingly slow rendering of large or complex tables. You've probably seen it yourself—the first 50 to 100 rows render quickly; each row after that seems to take a little bit longer than the previous row. This is a problem with all browsers and can be a huge source of frustration for the user. Besides some of DHTML's visual tricks, there is one more major element to data binding that increases the perceived speed of the page and provides some good functionality for user data navigation—pagination.
      Data pagination (or table paging) is another HTML data binding extension. It allows for only a certain number of items from the recordset to be displayed within a table at any one time. The way to do this is to specify the DATAPAGESIZE for the bound table and then use the nextPage or previousPage methods on the databound table to move through the recordset. For example, if my recordset has 101 items and I specify a DATAPAGESIZE of 10, I will only see 10 items at a time, but I will have what appears to be 11 different pages of data as I use the nextPage and previousPage methods to move through the recordset.
      If you take a look at the final version of the page in Figure 10, you'll notice that I've added the following code to the startPage function:


 var oRecordSet = tdcItems.recordset;
 totalItems = oRecordSet.recordCount; 
and

 if (totalItems > <%=itemsPerPage%>) {
     document.all.item("boundTable").dataPageSize = <%=itemsPerPage%>;
     for (i=0;i< document.all.item("recordSetButtons").length;i++) {
         document.all.item("recordSetButtons")(i).style.visibility =
             "visible";
     }
 }
In the first snippet of code I created a client-side ADO recordset, then figured out how many records it contains. From this point on, I can determine if I need to use data paging and how many pages of data I may need based on the user's request.
      In the second piece of code, I am determining whether to turn on data paging. You might remember the option on the Book Search page for the user to specify how many results to display per page. That value gets passed to the Search Results page, which then uses that value (via the ASP value <%=itemsPerpage%>) to determine if the data paging is needed. If there are more items than can be displayed on a single page, the DATAPAGESIZE is set and buttons to navigate the recordset become visible.
      I've also added a new function called pageCount. This function handles movement through the recordset, as described earlier, as well as filling in areas of the page with information such as current page number, total page numbers, and current record numbers in the recordset. Again, this is all calculated based on the total number of records in the recordset when the document.onload event fires.
      The pageCount function has also been added to sortItem. The statistics about the recordset navigation always need to be reset whenever the Reset method is called on the TDC DSO because every time Reset is called, the page rerenders itself.
      So I've ended up with a page that allows for some pretty powerful user interaction of a type not previously seen in Web pages (see Figure 15).

Figure 15: Partial Results
Figure 15: Partial Results

Taking it Further
      Data binding can help you build extensible, easily accessible, user-centric data analysis tools for the Web. These kinds of tools have previously only been found in traditional desktop applications.
      It's not a far stretch from here to use ASP, DHTML, and data binding to extend this tool to include other items that users typically demand, like graphing and filtering of the results. Even something like a master-detail report would not be difficult to implement. Each of these additions is only as complicated as you choose to make it.
      I hope this example has gotten you excited about the possibilities of data binding as well as demonstrated a couple of cool techniques that will let your users interact with their data on their own time and on their own terms.

From the September 1998 issue of Microsoft Interactive Developer.