YOUR FEEDBACK
Jeremy Geelan wrote: In response to inquiries and suggestions from readers this lexicon has recently...
AJAXWorld RIA Conference
$300 Savings Expire August 29
Register Today and SAVE!


2008 East
DIAMOND SPONSOR:
Data Direct
Frontiers in Data Access: The Coming Wave in Data Services
PLATINUM SPONSORS:
Red Hat
The Opening of Virtualization
Intel
Virtualization – Path to Predictive Enterprise
Green Hills
IT Security in a Hostile World
JBoss / freedom oss
Practical SOA Approach
GOLD SPONSORS:
Software AG
The Art & Science of SOA: How Governance Enables Adoption
PlateSpin
Effective Planning for Virtual Infrastructure Growth
Fujitsu
Automated Business Process Discovery & Virtualization Service
Ceedo
Workspace Virtualization
Click For 2007 West
Event Webcasts

2008 East
PLATINUM SPONSORS:
Appcelerator
Think Fast: Accelerate AJAX Development with Appcelerator
GOLD SPONSORS:
DreamFace Interactive
The Ultimate Framework for Creating Personalized Web 2.0 Mashups
ICEsoft
AJAX and Social Computing for the Enterprise
Kaazing
Enterprise Comet: Real–Time, Real–Time, or Real–Time Web 2.0?
Nexaweb
Now Playing: Desktop Apps in the Browser!
Sun
jMaki as an AJAX Mashup Framework
POWER PANELS:
The Business Value
of RIAs
What Lies Beyond AJAX?
KEYNOTES:
Douglas Crockford
Can We Fix the Web?
Anthony Franco
2008: The Year of the RIA
Click For 2007 Event Webcasts
SYS-CON.TV
TOP COLDFUSION LINKS


JavaScript Without the Headaches
JavaScript Without the Headaches

Coding ColdFusion and coding JavaScript are about as far apart on the productivity spectrum as it's possible to be. CF tags are neat, easy to read, tolerant, and fun to write. JavaScript is none of that. It has all the drawbacks of traditional languages, with the added disadvantage of sitting somewhat awkwardly within the HTML document model.

Anything but the most trivial JavaScript is difficult to write, difficult to debug, and difficult for either the author or another developer to revisit, but, as much as I'd like to, it isn't possible to do without it for interactive Web site development. For all its faults, JavaScript remains the principal means of delivering client-side functionality.

For better or worse, we have to learn to live with it, and fortunately ColdFusion makes it easy to integrate JavaScript into your apps without having to code and debug chunks of JavaScript every time you want to extend the basic HTML form controls.

Making the Most of CFFORM and CFINPUT
The primary and most underrated way of integrating JavaScript with your CF apps is through simple CFFORM and CFINPUT tags. It's wrong to assume that just because you want to do advanced validation you need to start from scratch coding all your own routines. These tags form a great platform to start building more advanced validations.

Obviously, there are the REQUIRED and VALIDATE attributes that will do the most common validations without having to write or debug JavaScript, but the ONVALIDATE and ONERROR attributes can be used to do more advanced validations without necessarily having to get too involved either.

About OnValidate
ONVALIDATE is the more useful and more powerful. The value supplied to the attribute is simply the name of the JavaScript function to call to validate the field. The parameters passed to the routine are always the same: the form object, the field object, and the value of the field. For example, in a basic validation where you want a password field to be 6 letters or more, you'd use the following code:

This would then be called by a CFINPUT tag like this:

message="Please enter a password of at least than 6 letters"
onvalidate="validatePassword">

(See Listing 1 for complete listing. This also shows a neat trick for using a hidden cfinput to validate a textarea tag.)

On balance, the fact that the parameters are fixed like this is a help, although the drawbacks are obvious. What if you want to vary the required length? You can't pass the length as a parameter, so you end up altering your JavaScript - which is specifically what we want to avoid by using tags like CFINPUT.

This problem (which we'll look at later) is outweighed by the convenience of not having to code references to the form, field, and value each time. It doesn't, of course, limit you to only referencing that field - you can reference other fields quite simply, as in this check for a confirmation password field:

// Check that the confirm password field matches the first
function checkPasswordsMatch(form,field,value) {
if (value != form.pw.value) {
return 0;
}
else {
return 1;
}
}

Which you'd use in conjunction with a CFINPUT:

Confirm: onvalidate="checkPasswordsMatch">

(See Listing 2 for complete example.)

This again suffers from the problem that the validation script isn't parameterized - the name of the first password field is hardwired into the code, something that'd give the object purists palpitations.

About OnError
ONERROR can be used to override the default behavior of simply displaying an error message if the validation fails. You can use it to display different error messages for different validation failures (e.g., blank or not enough characters).

For instance, the following script could be used to validate the pw_check field shown previously in Listing 2.

function pw_check_error(form,field,value) {
if (value.length == 0) {
alert('Please confirm your password');
}
else if (value != form.pw.value) {
alert('The passwords do not match');
}


}

(See Listing 3 for complete example.)

NB the onerror script is called if required=yes and the field is blank, as well as when the onvalidate function returns false.

The Challenges of Generated Code
This now has made the problem of having parameters hardwired into the JavaScript even worse. The error messages should be parameterized or even dynamic if we're using a multilanguage setup.

Experienced developers looking at this will be thinking it might be best to start from scratch with their own validation routines, and when you look at code like Listing 3, you can see why.

The solution most developers would adopt is to write JavaScript routines that take things like the minimum length and the error messages as parameters and apply them either in onchange handlers for the fields or in onsubmit handler for the form. Something like this:

<input onchange="CheckPW(this.form, this,this.value, 6,
'Please confirm your password', 'The passwords do not match')">

(Note: Don't try this! It's just hypothetical.)

This is the first step on the familiar path of teeth-gnashing frustration that is coding your own JavaScript, and before we go down that road, let's look at another option for tidying up our code.

If you look at the code generated by CFFORM, you'll notice one thing very quickly - there's lots of it. Also you'll see that it isn't especially generic. The names of fields are hardwired into the code in much the same way as the examples here.

The same is true if you look at the JavaScript generated by several other automated systems. The developers of these systems have made a conscious decision to do it this way instead of trying to create completely reusable functions and objects. JavaScript just doesn't warrant effort spent on trying to make it neat and generic. You can waste hours trying to get it right and then find it doesn't work on one particular build of Mozilla.

Solving the Problem with Custom Tags
Instead, there's a different philosophy you can adopt - that it doesn't necessarily matter how neat the JavaScript is or how much of it there is, as long as it's generated automatically and the code that generates it is properly modular and reusable.

Say for instance we wanted to tidy up our password field. According to correct design principles, the only things we should be including in the page are the necessary details of the field - its name, its minimum length, the fact that it's a password, and that we want a "check" field, all of which can be neatly done with a ColdFusion custom tag:

(See Listing 4; also see the listing for cf_password.)

All the JavaScript and the cf input tags can then be generated by the custom tag, with the JavaScript placed correctly in the element with a CFHTMLHEAD. The fieldname "pw" may be hardwired into the JavaScript, but as long as it isn't hardwired into the CFML that generates the JavaScript, that doesn't matter. The same goes for the minimum length. This system is all correctly parameterized and reusable without having to waste hours coding JavaScript. It's also readable and easily understandable in the same way as CFML form tags.

Whenever you include client-side functionality you should always adopt this approach, either writing your own custom tags - or even better - using some of the many excellent tags in the developer's exchange. One of the most common requirements is for "related selects" - where selecting a value in one select list changes another list to show only related values.

If you aren't already, you should be using one of the many custom tags available to do this job. Cf_twoselectsrelated (see Figure 1) is a great, simple tag that can be customized quite easily to fit in with cfform rather than using its own validations. The hidden cfinput technique allows for easy validation. In Listing 5, the name of the second select is SUB_CATEGORY, and we can require this or validate it using:

 

Rather than modifying the tag itself to include this, I recommend creating a new tag that then calls Cf_twoselectsrelated; otherwise you can end up with versioning problems. (Of course, another option for providing these kinds of interfaces is Flash and Flash Remoting. For more information, see Ben Forta's November 2002 CFDJ article, "Data Entry Reformed," Vol. 4, issue 11. But there are clearly times when JavaScript alone may make more sense.)

Other useful custom tags include cf_swapbox (Figure 2, Listing 6), cf_cross_select, tags for picking dates or times, and tags for dividing forms up into "tabbed" controls.

 

If you look at the JavaScript generated by any of these tags, you'll find the same story - lots of JavaScript with hardwired field names and parameter values. It doesn't matter, as long as the ColdFusion generating it is properly modular. If you're going to start coding your own custom tags, you can spare yourself many hours of frustrating debugging by following the same philosophy.

And while this article presumes you're already skilled with JavaScript, if you're just getting started and could use some hand-holding, see Charlie Arehart's June 2000 CFDJ article, "Getting Focus(ed) - and a Quick JavaScript Overview," Vol. 2, issue 6.

Spend time on what's most productive: keep your ColdFusion pages neat, and don't lose any sleep over your JavaScript.

About Tom Peer
Tom Peer has been in electronic publishing of one sort or another for ten years, including a stint as manager of New Scientist Online (www.newscientist.com). He specializes in taking printed publications online and has recently completed the online edition of The World Handbook of Stock Exchanges (www.exchange-handbook.com).

CFDJ LATEST STORIES . . .
Two of the biggest launches in Rich Internet Application history took place in 2007/2008 when Adobe launched AIR 1.0 in February '08 and Microsoft launched Silverlight (September '07). At the 6th International AJAXWorld RIA Conference & Expo in October SYS-CON Events is delighted to be...
Red Hat CTO Brian Stevens, Citrix CTO Simon Crosby, Egenera CTO Pete Manca, Allen Stewart, Group Manager, Windows Virtualization at Microsoft, and Brian Duckering, Sr. Director of Products and Alliances at Symantec were the top industry executives who joined Jeremy Geelan in the 4th Fl...
Mike Neil is general manager for virtualization strategy in the Windows Server Division at Microsoft. Mike is focused on the delivery of the Windows virtualization technology, including Windows Server 2008 Hyper-V, Microsoft Hyper-V Server and Virtual PC 2007. Mike also directs the tec...
SQL Injection attacks are one of the easiest ways to hack into a website. One recent hack, using a script from verynx.cn, involves injecting sql into a web form that then appends some JavaScript code into fields in a database that then gets executed on the client side when a user views...
Recursion Software released a private beta version of their Voyager mobile platform, with powerful interoperability for Android, Microsoft .NET and Compact Framework (CF), all Java editions (JME CDC, JSE and JEE), and more than 15 embedded operating systems. The Voyager platform is a p...
2008 is going to be an important year for Rich Internet Applications. Most organizations are delivering or planning to deliver Rich Internet Applications; however, at the same time, most IT managers are facing a dilemma: which Rich Internet Application technology and platform to use? T...
SUBSCRIBE TO THE WORLD'S MOST POWERFUL NEWSLETTERS
SUBSCRIBE TO OUR RSS FEEDS & GET YOUR SYS-CON NEWS LIVE!
Click to Add our RSS Feeds to the Service of Your Choice:
Google Reader or Homepage Add to My Yahoo! Subscribe with Bloglines Subscribe in NewsGator Online
myFeedster Add to My AOL Subscribe in Rojo Add 'Hugg' to Newsburst from CNET News.com Kinja Digest View Additional SYS-CON Feeds
Publish Your Article! Please send it to editorial(at)sys-con.com!

Advertise on this site! Contact advertising(at)sys-con.com! 201 802-3021


SYS-CON FEATURED WHITEPAPERS

ADS BY GOOGLE