You will be redirected in 30 seconds or close now.

ColdFusion Authors: Yakov Fain, Jeremy Geelan, Maureen O'Gara, Nancy Y. Nee, Tad Anderson

Related Topics: ColdFusion

ColdFusion: Article

Server to Client WDDX

Server to Client WDDX

The Web Distributed Data Exchange (WDDX) is an XML-based technology that allows different Web technologies to exchange data. One function of WDDX is to send ColdFusion queries to JavaScript for use on the client. This article details how to use this functionality with HTML SELECT statements, and assumes you're familiar with ColdFusion and HTML forms but not with WDDX and JavaScript.

WDDX, HTML forms, ColdFusion queries and JavaScript are combined to create a single page providing SELECT statements that are dynamically populated. In addition, one SELECT statement can be filled based on an earlier user selection on the same Web page. In essence, this makes queries that were traditionally available only on the server side now available on the client.

ColdFusion and HTML forms can be used together to dynamically populate SELECT controls from a ColdFusion query. When a user views this form, the query is performed; the SELECT statement contains the latest options from the table that was queried. To enhance this process you may want to populate a second SELECT statement based on a selection the user made from an earlier one. For instance, the first SELECT statement offered options for Colors and Trees (see Figure 1).

If the user selected Colors from the first SELECT control, the second will be populated with the options green, orange and red (see Figure 2).

If the user selected Trees, then the second SELECT will be populated with the options Fir, Hemlock and Pine (see Figure 3).

A common way to implement this behavior is on two separate pages since the first selection wouldn't be known until the user submitted the form. This article shows how to pass the second set of options to the client so the process can take place on a single page.

The first step in implementing this process is the conversion of a ColdFusion query to a JavaScript array (technically, the query is converted into a JavaScript recordset structure). Since you don't know which option a user will select from the first SELECT statement, you'll have to pass all queries that may be needed for options in the second SELECT statement. To do this you'll use WDDX.

WDDX allows you to exchange data between ColdFusion and JavaScript. The following steps are necessary:

1. Perform a ColdFusion query.
2. Use WDDX to convert the query into a JavaScript array.
3. Place the JavaScript array definition in the JavaScript section of the page.

You may then use the data as you would a JavaScript array.

Step 1, performing queries, is familiar to any ColdFusion developer. For this example consider two queries - qryColor and qryTree. Each query reads three rows of data containing a primary key value, a color name or primary key value, and a tree name.

Step 2 uses WDDX to convert the ColdFusion queries to JavaScript usable variables. This is a two-step process, but we'll use a shortcut and make it a one-step process. You need to convert the ColdFusion query into a WDDX packet, then convert the packet into a JavaScript variable. This process uses the <CFWDDX> tag. Without using the shortcut the two lines of code are:



The first statement uses the attribute ACTION="CFML2WDDX". This converts or, in WDDX lingo, serializes the ColdFusion query into a WDDX packet stored under the name jsTreeTemp. It isn't necessary to understand the actual contents of the packet in order to use it, but, for the curious, see Listing 1 for the query containing the tree primary keys and names converted to WDDX. The indentation used in the packet is for readability only; the actual packet output contains no line breaks.

The second statement uses the ACTION="WDDX2JS" attribute to change the WDDX packet to a JavaScript variable, i.e., deserializes from WDDX to JavaScript. The actual variable type is defined in a file named wddx.js that you'll reference on the page that's installed with ColdFusion. In the code for this page the reference looks like:

<SCRIPT TYPE="text/javascript"

If this isn't included, you'll probably see an error:

'WddxRecordset' is undefined.

The input for the tag is the WDDX packet created in the first CFWDDX tag. The OUTPUT attribute holds the definition of the JavaScript variable that we'll use in the JavaScript section of the code. The TOPLEVELVARIABLE attribute defines the name of the variable to be used in the JavaScript code.

You need only one tag to perform both these steps using the CFWDDX tag:


This converts the ColdFusion query directly into the JavaScript variable and Step 2 is completed.

Step 3 is quite simple. You simply need to start the script section of the page using:


and then use CFOUTPUT to put the JavaScript variable definitions into the script section of the page. When you use the code:


you place the JavaScript variable definition on the page. As with the actual format of the WDDX, it's not essential to understand the format of the variable declaration. But again, for the curious, the qryTree query becomes the JavaScript variable defined by:

jsTreeTLV=new WddxRecordset();
_t2=new Array(); _t2[0]=1;_t2[1]=3;_t2[2]=2;

In the actual code there are no line breaks, just as in the WDDX packet.

To help you understand how to use this definition, think of the query being converted into an array of the general form TopLevelVariableName.columnname[i]. Specifically, the query qryTree generates:

jsTreeTLV.tree_id[0]=1 (the primary key value) and
jsTreeTLV.tree_id[1]=3 (the primary key value) and
jsTreeTLV.tree_id[2]=2 (the primary key value) and

Since JavaScript is case sensitive, it's important to note that in the deserialization process the TOPLEVELVARIABLE attribute value of the CFWDDX tag keeps its case, and the field names from the query become lowercase; the case of the columns from the query doesn't matter. Note that the index for the array starts at 0 and not 1.

With the ColdFusion queries converted into JavaScript variables, it's time to look at the JavaScript that uses these variables.

The goal of the page now is to make these events occur:

1. When the user selects an option from the Select1 form control, a JavaScript function called choosenext() is called.

2. The choosenext() function decides which option the user selected.

3. The choosenext() function fills the DynamicSelect form control with the appropriate query information passed into the JavaScript.

To accomplish Step 1, a SELECT statement is created with the form using HTML:

<SELECT NAME="Select1" onChange=choosenext()>

The statement uses the JavaScript onChange event handler. This means that when a selection is made from the SELECT box, an event occurs (onChange) and the function called choosenext() is called (defined in the SCRIPT section of the page). This happens as soon as the user makes a change in the SELECT statement before the form is even submitted.

The job of the choosenext() function is to populate the SELECT statement that was created with HTML:

<SELECT NAME="DynamicSelect">

Nonbreaking spaces are used because Navigator won't dynamically enlarge the width of the box, but if this isn't done the options won't display correctly .

Now Step 2 needs to be completed, i.e., deciding which selection was made in the Select1 form control. This can be done by using the JavaScript "if" statement in the form.

if (document.TestForm.Select1.selected
if (document.TestForm.Select1.selected
if (document.TestForm.Select1.selected

This statement takes advantage of the Document Object Model (DOM). The document object is the entire page with the "TestForm" form that contains the "Select1" SELECT control. This object, which can be referenced by the name "document.TestForm.Select1", has a property called selectedIndex. Then it's all put together to see which option the user chose from the SELECT control and guides the program flow into the appropriate section of the choosenext() function.

Now it's time to get Step 3 done: filling the "DynamicSelect" SELECT control with the needed query results (which, as you recall, have been converted into JavaScript variables). First you need to delete any options in the SELECT control by setting the number of options to 0. Again, we need to take advantage of the DOM and use the code:


This sets "DynamicSelect's" length to 0. All SELECT controls have a length property just as they have a selectedIndex property, which we used earlier.

Next, a loop will be used to put the correct number of options into the SELECT statement. The number of times to loop will be determined by the statement:

for (var RowNum=0; RowNum<jsTreeTLV.tree_id.length; RowNum++)

This creates a loop counter called RowNum that starts at 0 since the index of the array starts at 0. The loop will stop when RowNum exceeds the length of the array, which is equivalent to the number of records read in the ColdFusion query. This number is retrieved from a property of a JavaScript array called length and is referenced by the code:


The last part of the loop statement, RowNum++, increments RowNum by one each time through the loop.

Finally, the code that creates the options and puts them into the DynamicSelect form control is used. To accomplish this we use the following lines of code:

NewOpt=new Option;

Each time through the loop a new option is created using the JavaScript operator new. This creates a new instance of an option to be placed within the SELECT control. Then the option needs to be given a value for the VALUE attribute and text to be displayed to the user. This is accomplished using the code:


This code uses the DOM and the value and text properties of the options, which is itself a property of the SELECT statement. Each time through the loop the next values from the JavaScript array are taken and assigned to an option. The last line of code:


assigns the new option created to the list of previous options. The options property is actually an array that holds the options. That's why the loop will generate code that will fill the array using options[0], options[1], options[2], etc.

Just before the choosenext() function is exited, the DynamicSelect statement needs to have the first option selected so it'll appear in the list of options. Otherwise a blank option will be used. This is done with the code:

options[0].selected = true;

This code makes another reference to the DOM and sets the Boolean property selected (of the options property) to true. This puts the first option in the SELECT control. Remember that the first element of the array has an index of zero.

With the selection of an option from the first SELECT control, the second SELECT control is dynamically populated.

More Stories By Matthew Boles

Matthew Boles has been doing ColdFusion training for Allaire for nearly two years and has worked with ColdFusion since version 1.5. He is also a certified Novell and Microsoft instructor, although he now devotes his professional time to ColdFusion training and consulting. [email protected]

Comments (0)

Share your thoughts on this story.

Add your comment
You must be signed in to add a comment. Sign-in | Register

In accordance with our Comment Policy, we encourage comments that are on topic, relevant and to-the-point. We will remove comments that include profanity, personal attacks, racial slurs, threats of violence, or other inappropriate material that violates our Terms and Conditions, and will block users who make repeated violations. We ask all readers to expect diversity of opinion and to treat one another with dignity and respect.

IoT & Smart Cities Stories
Nicolas Fierro is CEO of MIMIR Blockchain Solutions. He is a programmer, technologist, and operations dev who has worked with Ethereum and blockchain since 2014. His knowledge in blockchain dates to when he performed dev ops services to the Ethereum Foundation as one the privileged few developers to work with the original core team in Switzerland.
René Bostic is the Technical VP of the IBM Cloud Unit in North America. Enjoying her career with IBM during the modern millennial technological era, she is an expert in cloud computing, DevOps and emerging cloud technologies such as Blockchain. Her strengths and core competencies include a proven record of accomplishments in consensus building at all levels to assess, plan, and implement enterprise and cloud computing solutions. René is a member of the Society of Women Engineers (SWE) and a m...
Andrew Keys is Co-Founder of ConsenSys Enterprise. He comes to ConsenSys Enterprise with capital markets, technology and entrepreneurial experience. Previously, he worked for UBS investment bank in equities analysis. Later, he was responsible for the creation and distribution of life settlement products to hedge funds and investment banks. After, he co-founded a revenue cycle management company where he learned about Bitcoin and eventually Ethereal. Andrew's role at ConsenSys Enterprise is a mul...
Whenever a new technology hits the high points of hype, everyone starts talking about it like it will solve all their business problems. Blockchain is one of those technologies. According to Gartner's latest report on the hype cycle of emerging technologies, blockchain has just passed the peak of their hype cycle curve. If you read the news articles about it, one would think it has taken over the technology world. No disruptive technology is without its challenges and potential impediments t...
If a machine can invent, does this mean the end of the patent system as we know it? The patent system, both in the US and Europe, allows companies to protect their inventions and helps foster innovation. However, Artificial Intelligence (AI) could be set to disrupt the patent system as we know it. This talk will examine how AI may change the patent landscape in the years to come. Furthermore, ways in which companies can best protect their AI related inventions will be examined from both a US and...
In his general session at 19th Cloud Expo, Manish Dixit, VP of Product and Engineering at Dice, discussed how Dice leverages data insights and tools to help both tech professionals and recruiters better understand how skills relate to each other and which skills are in high demand using interactive visualizations and salary indicator tools to maximize earning potential. Manish Dixit is VP of Product and Engineering at Dice. As the leader of the Product, Engineering and Data Sciences team at D...
Bill Schmarzo, Tech Chair of "Big Data | Analytics" of upcoming CloudEXPO | DXWorldEXPO New York (November 12-13, 2018, New York City) today announced the outline and schedule of the track. "The track has been designed in experience/degree order," said Schmarzo. "So, that folks who attend the entire track can leave the conference with some of the skills necessary to get their work done when they get back to their offices. It actually ties back to some work that I'm doing at the University of San...
When talking IoT we often focus on the devices, the sensors, the hardware itself. The new smart appliances, the new smart or self-driving cars (which are amalgamations of many ‘things'). When we are looking at the world of IoT, we should take a step back, look at the big picture. What value are these devices providing. IoT is not about the devices, its about the data consumed and generated. The devices are tools, mechanisms, conduits. This paper discusses the considerations when dealing with the...
Bill Schmarzo, author of "Big Data: Understanding How Data Powers Big Business" and "Big Data MBA: Driving Business Strategies with Data Science," is responsible for setting the strategy and defining the Big Data service offerings and capabilities for EMC Global Services Big Data Practice. As the CTO for the Big Data Practice, he is responsible for working with organizations to help them identify where and how to start their big data journeys. He's written several white papers, is an avid blogge...
Dynatrace is an application performance management software company with products for the information technology departments and digital business owners of medium and large businesses. Building the Future of Monitoring with Artificial Intelligence. Today we can collect lots and lots of performance data. We build beautiful dashboards and even have fancy query languages to access and transform the data. Still performance data is a secret language only a couple of people understand. The more busine...