Exchanging WDDX Packets among Web Pages


If you've done any work with ColdFusion's <cfhttp> tag, you know that you can use it to fetch Web pages from any Web server on the Internet. Essentially, the <cfhttp> tag pretends to be a Web browser, supplying any parameters that would normally be supplied by form input, cookies, or CGI variables. ColdFusion developers already use this tag to have their applications automatically visit other Web pages programmatically.

For instance, a ColdFusion application might need to know the current temperature. By using <cfhttp> to fetch a page that includes the current temperatureperhaps the "current conditions" page of the local airport's Web sitethe application can obtain a document that has the necessary information in it. Then, using ColdFusion's string manipulation functions or some regular expressions, the application can parse through the page's source code and extract the few characters that represent the temperature.

NOTE

See Chapter 21, "Using Server-Side HTTP and FTP," for a complete discussion of using the <cfhttp> tag to fetch Web pages from other Web servers on the Internet, or from servers on your intranet or extranet.


The Concept of a Back-End Web Page

Okay, now imagine taking things a step farther. What if the airport's Web site has a special page that isn't meant to be looked at, but rather is meant only to supply information to other systems? That is, instead of including pictures, links, table and font tags, explanatory text, and so on, what if all the page contains is a WDDX packet with the temperature? Maybe the packet includes other information as well, such as the barometric pressure, runway conditions, and so on.

In that case, any ColdFusion application could use the <cfhttp> tag to pick up this packet and then use <cfwddx> to extract all the information from the packet into local variables. Just two lines of CFML code later, the application has the information it needs. You can imagine that other airports around the world might set up the same type of back-end Web pages to report the current conditions. The airports might even use these pages to get information about each other's current conditions to be able to tell customers what the weather is like at their destinations.

Suddenly, the airport's Web site is no longer just supplying information to people who happen to visit the Web site and click the "current conditions" page. It's now part of an ambitious information and automation network. No expensive communications channels were set up, and no complicated integration work was done. By using the infrastructures already in placenamely, the airport's Web server and Internet connectionthe airport can transform itself into a source of raw data for any application that knows how to fetch a Web page and deserialize a WDDX packet.

Back-End WDDX Pages vs. Web Services

If you're familiar with SOAP, XML-RPC, or the general concept of Web Services, you will recognize that my description of a back-end page is a very similar concept. Making back-end Web pages with WDDX as discussed in this section is a sort of roll-your-own approach to putting together pages that behave like formalized Web Services. You might prefer to just go ahead and adopt the official Web Services frameworks by using CFCs to create services, and <cfinvoke> to use services, as discussed in Chapter 24, "Creating and Consuming Web Services."

That said, here are some reasons why you might want to use a roll-your-own approach using WDDX rather than formalized Web services:

  • Perhaps you need to integrate legacy applications or systems that don't support Web services but that do support COM or Java. Since WDDX support is provided for COM and Java, you're all set.

  • Perhaps you like the idea of being able to very easily understand every aspect of what's going on. WDDX is simple and intuitive.

  • Perhaps you don't think the various Web Services frameworks are mature and proven enough for your particular needs. WDDX doesn't tie you to .NET, J2EE, or anything else.

Indeed, homegrown WDDX-enabled back-end Web pages (I often call them "robot" pages) make up many of the examples for the remainder of this chapter. I use them as examples because they are clear, and because they illustrate how easy it is to get different applications working together. As you read on, just keep in mind that any of the WDDX-related code and techniques used for the back-end page scenario (where packets are exchanged over the Web via HTTP) are just as relevant when you're using WDDX to exchange or save packets via other delivery or storage mechanisms, such as files, client variables, databases, or even email messages.

Creating a Back-End Web Page

Take a look at the FilmsRobot1.cfm template shown in Listing 16.13. This page selects information about films from the database and outputs the query results as a WDDX packet. It supports a few URL parameters to control which films are selected, and how much information about each film is included in the packet.

Listing 16.13. FilmsRobot1.cfmA Back-End Web Page That Exposes Film Data as WDDX Packets
 <!--- Name:        FilmsRobot1.cfm Author:      Nate Weiss and Ben Forta Description: Creates a back-end web page that              supplies data about films Created:     02/01/05 ---> <!--- URL Parameters to control what film data the page responds with ---> <cfparam name="URL.FilmID"          type="numeric"          default="0"> <cfparam name="URL.Details"          type="boolean"          default="No"> <cfparam name="URL.Keywords"          type="string"          default=""> <!--- Execute a database query to select film information from database ---> <cfquery name="FilmsQuery"           datasource="ows">   SELECT     <!--- If all information about film(s) is desired --->     <cfif URL.Details>       *     <!--- Otherwise, return the film's ID and title --->       <cfelse>       FilmID, MovieTitle      </cfif>   FROM Films   <!--- If a specific film ID was specified --->   <cfif URL.FilmID GT 0>     WHERE FilmID = #URL.FilmID#   <!--- If keywords were provided to search with --->     <cfelseif URL.Keywords NEQ "">       WHERE MovieTitle LIKE '%#URL.Keywords#%'        OR Summary LIKE '%#URL.Keywords#%'   </cfif>   ORDER BY MovieTitle </cfquery> <!--- Convert the query recordset to a WDDX packet ---> <cfwddx action="CFML2WDDX"         input="#FilmsQuery#"> 

If you visited this page normally with your browser, you'd probably see all the film titles and ID numbers smushed together on the page, because the browser doesn't know how to render the WDDX packet visually. On the other hand, if you view the source, you will see that the page is indeed responding with a packet fill of film data.

NOTE

I like to refer to this type of page as a "robot" because that term emphasizes the metaphor for a kind of automated process that is always waiting for requests and responding to them. Of course, any Web page can be considered robotic in nature, but something about the fact that the content is WDDX rather than HTML (and thus not designed to be read by humans) makes "robot" appropriate. If you prefer, think of this type of page as a "service." Just don't get this confused with official Web services as discussed in Chapter 24.


Listing 16.14 shows the packet returned by Listing 16.13 when visited normally (that is, without providing any URL parameters). For clarity, I have abbreviated the listing and added indention.

Listing 16.14. Response from FilmsRobot1.cfm When Visited with No URL Parameters
 <wddxPacket version='1.0'> <header/> <data>  <recordset   rowCount='23'   fieldNames='FILMID,MOVIETITLE'   type='coldfusion.sql.QueryTable'>    <field name='FILMID'>  <number>1.0</number>  <number>2.0</number>  <number>3.0</number>  <number>18.0</number>  ...and so on...  </field>    <field name='MOVIETITLE'>  <string>Being Unbearably Light</string>  <string>Charlie's Devils</string>  <string>Closet Encounters of the Odd Kind</string>  <string>Folded Laundry, Concealed Ticket</string>  ...and so on...  </field>    </recordset> </data> </wddxPacket> 

Now if you visit the page, this time supplying FilmID=3 and Details=Yes parameters in the URL, the robot will respond with the packet shown in Listing 16.15. Again, I have abbreviated the packet slightly to make it appear more clearly on the printed page.

Listing 16.15. Response from FilmsRobot1.cfm When Details for a Particular Film Are Requested
 <wddxPacket version='1.0'>  <header/>  <data>  <recordset   rowCount='1'   fieldNames='FILMID,MOVIETITLE,PITCHTEXT,AMOUNTBUDGETED,RATINGID,...'   type='coldfusion.sql.QueryTable'>    <field name='FILMID'>  <number>3.0</number>  </field>  <field name='MOVIETITLE'>  <string>Closet Encounters of the Odd Kind</string>  </field>  <field name='PITCHTEXT'>  <string>Some things should remain in the closet</string>  </field>  <field name='AMOUNTBUDGETED'>  <number>350000.0</number>  </field>  <field name='RATINGID'>  <number>5.0</number>  </field>  <field name='SUMMARY'>  <string>One man finds out more than he ever wanted to know...</string>  </field>  <field name='IMAGENAME'>  <string>f3.gif</string>  </field>  <field name='DATEINTHEATERS'>  <dateTime>2000-11-7T0:0:0-5:0</dateTime>  </field>  </recordset>    </data> </wddxPacket> 

Putting the Back-End Web Page to Use

Now that the back-end film robot page has been constructed, it's time to try incorporating the robot's responses into ordinary ColdFusion pages. Take a look at the simple code in Listing 16.16. It fetches the WDDX packet from the FilmsRobot1.cfm template (shown in Listing 16.14), and then deserializes the packet with <cfwddx>. Because the packet contains a recordset, the resulting FilmsQuery variable can be used just like the recordset returned by an ordinary <cfquery> tag. In this case, the query is used to display a list of movie titles (see Figure 16.7).

Figure 16.7. Film data is fetched over the Internet from the robot page, then displayed to the user.


NOTE

The RobotURL value used in this listing assumes that you are saving the listings for this chapter in a folder called 16 within a folder called ows-adv, which is within your server's document root. It's also assumed that you are running ColdFusion in stand-alone mode (thus, the :8500 part of the URL). You may need to adjust the URL slightly depending on where you are storing the listings.


Listing 16.16. UseFilmsRobot1a.cfmConnecting to a Back-End Robot Page
 <!--- Name:        UseFilmsRobot1a.cfm Author:      Nate Weiss and Ben Forta Description: Fetches a WDDX packet via              HTTP and uses the query              contained within Created:     02/01/05 ---> <!--- Location of the robot page ---> <!--- The URL could be anywhere in world, not just on this server ---> <cfset RobotURL="http://localhost:8500/ows_adv/16/FilmsRobot1.cfm"> <!--- Contact the robot page and retrieve the WDDX packet it returns ---> <cfhttp method="Get"         url="#RobotURL#"> <!--- Deserialize the packet, which we know holds a query recordset ---> <cfwddx action="WDDX2CFML"         input="#CFHTTP.FileContent#"         output="FilmsQuery">    <!--- We can now use the query object normally, just as if it came directly from a <cfquery> tag ---> <h2>Live data retrieved from robot page</h2> <cfoutput query="FilmsQuery">   <a href="UseFilmsRobot1b.cfm?FilmID=#FilmID#">#MovieTitle#</a><br> </cfoutput> 

When the user clicks on any of the links produced by this listing (see Figure 16.7), they are brought to the UseFilmsRobot1b.cfm page, which displays the details about the film (see Figure 16.8). Listing 16.17 shows the code needed to put together the detail page.

Listing 16.17. UseFilmsRobot1b.cfmConnecting to a Back-End Robot Page
 <!--- Name:        UseFilmsRobot1b.cfm Author:      Nate Weiss and Ben Forta Description: Fetches a WDDX packet via              HTTP and uses the query              contained within Created:     02/01/05 ---> <!--- We need a FilmID ---> <cfparam name="URL.FilmID"          type="numeric"> <!--- Location of the robot page ---> <!--- The URL could be anywhere in world, not just on this server ---> <cfset RobotURL="http://localhost:8500/ows_adv/16/FilmsRobot1.cfm"> <!--- Add parameters so the robot knows to return detailed information ---> <cfset RobotURL=RobotURL & "?FilmID=#URL.FilmID#&Details=Yes"> <!--- Contact the robot page and retrieve the WDDX packet it returns ---> <cfhttp method="Get"         url="#RobotURL#"> <!--- Deserialize the packet, which we know holds a query recordset --->   <cfwddx action="WDDX2CFML"         input="#CFHTTP.FileContent#"         output="FilmQuery">    <!--- We can now use the query object normally, just as if it came directly from a <cfquery> tag ---> <cfoutput query="FilmQuery">   <h2>#MovieTitle#</h2>   #PitchText#     <p><strong>Summary:</strong><br>   #Summary#<br>     <p><strong>Budget:</strong><br>   #LSCurrencyFormat(AmountBudgeted)#<br>   <p><strong>Date In Theaters:</strong><br>   #LSDateFormat(DateInTheaters)#<br> </cfoutput> 

Figure 16.8. The films robot is contacted again to get detailed information about individual films.


As you can see, this listing is quite similar to the one that came before it (Listing 16.16). The only real difference is that this listing passes FilmID and Details=Yes parameters to the robot page, which causes the robot to respond with a WDDX packet similar to Listing 16.15 instead of Listing 16.14. Once the packet has been fetched and deserialized, the data from the packet can once again be used just like the results of a normal <cfquery> tag.

Understanding the Possibilities

You've seen how WDDX can be used to quickly and easily allow one ColdFusion page to grab data from another ColdFusion page. The code is simple and elegant, and easy to put together and understand. But what, exactly, is the benefit of doing things this way?

For most ColdFusion pages, there probably isn't any benefit. <cfhttp> and <cfwddx> are fast, lightweight processes, but they do introduce a small amount of additional processing time and general overhead. In terms of raw performance, just querying the database directly with a <cfquery> and using it all in the same page is clearly more straightforward and efficient.

But suppose, for whatever reason, you have one ColdFusion server that can connect to the database, and another ColdFusion server that cannot (perhaps it's outside the firewall, or overseas, or is owned by a different company). In that case, this kind of WDDX setup makes a whole lot of sense. Just put a robot page (like Listing 16.13) on the database-enabled server, and then call the robot (using code like Listing 16.16 and Listing 16.17) using pages on the second server. It's a remarkably simple and easy way to integrate the two environments.

Additionally, neither of the two servers need be running ColdFusion in order to supply or use the WDDX packets. Any of the other technologies discussed in the second portion of this chapter (such as ASP, Java, or Perl) could be used to create the robot page or the pages that use the robot. Mix and match to your heart's content.

Like the airport scenario mentioned in the section "The Concept of a Back-End Web Page," you can create robotlike pages that make statistics or other real-time information publicly available as WDDX packets. Of course, you can also put a password or other security mechanism on the robot pages if you only want the information to be available to your company's partners.

In short, the ability to exchange WDDX packets over the Internet via HTTP is a simple and powerful means to integrate machines that are separated from one another in some way, either physically or in terms of the software they are running. As mentioned, this is really the same concept that is at the heart of the Web Services movement, and you might want to consider creating and consuming official Web services instead (as discussed in Chapter 24). But if you go the home-grown, WDDX-based route, you have the advantage of comprehension: WDDX's simplicity becomes pretty compelling in and of itself.



Advanced Macromedia ColdFusion MX 7 Application Development
Advanced Macromedia ColdFusion MX 7 Application Development
ISBN: 0321292693
EAN: 2147483647
Year: 2006
Pages: 240
Authors: Ben Forta, et al

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net