Make AJAX Easy with Model-Glue - Joe Rinehart

Published February 1, 2007 on adamfortuna

    Notes from Joe Rinehart's talk on Ajax and Model Glue at Frameworks 2007.

    Ajax in this context is using an out of bound information in javascript allowing multiple page requests within a single page. Joe's going over some ajax basics and how it's changed our html workflow. We no longer get an entire request back, now we just update accordingly on success/failure based on the response. This can be validation response or just something that signifies that it worked.

    Two types of Ajax – Structured and Unstructured. Unstructured Ajax doesn't return any structured data. It's just returning already rendered html which is replaced in the calling javascript. It's the easiest to implement, and the javascript as well as a cf which generates the html are straightforward. Doesn't require any major changes in architecture — no service layer, model, xml/json rendering engine is required. This approach isn't the most flexible though. The receiving page can typically only do one thing with the result, which doesn't allow for much functionality.

    Structured ajax doesn't automatically replace screen regions with request responses. Instead it has structured data; maybe xml, json, or delimited lists. This is pure data coming back from the server, allowing the structured ajax to work well with existing service tiers. It's more difficult to implement structured ajax and requires javascript and dom scripting knowledge. This makes dealing with multiple browsers more difficult. There's also no standard mechanism for structured data – xml, soap, json and now spry are all common.

    Creating ajax calls depends on which browser you're using. You might use ActiveXObject in IE or XMLHTTPRequest in Firefox. This is repetitive code that's usually in the javascript framework. Joe will be talking about Prototype and Scriptaculous using unstructured ajax.

    Prototype hides the implementation of XMLHttpRequest making ajax requests cross browser. It does have a structured Ajax features, but it's custom to prototype and relies on a special HTTP header indicating a Json response. Script.aculo.us is the UI and effects library built on Prototype. Model-Glue will be used along with the Generic methods.

    Model-Glue can return just plain javascript wrapped in a <script/> tag containing all javascript you want to return.

    In this presentation Joe's going over a basic todo list where users can add, edit and delete tasks as well as mark them as completed. You can view uncompleted tasks or all tasks. For this presentation Joe's going to go over deleting a single task. Adding a Model Glue event of task.delete.ajax and using a ModelGlue.GenericDelete message, Joe added an ajax version of the delete. This will not return anything or show anything to the user. This can be called in a browser and it'll delete the record you include in the url that matches your GenericDelete method. After including the required js files, an onclick method can be added to the onclick method of the delete link. Instead of a link to a page that will delete the task, joes changed it to call a deleteTask() function. Here's the deleteTask() function.

    function deleteTask(taskID) {  
     new Ajax.Request(”index.cfm?event=task.delete.ajax&taskID = ” + taskID);  
     new Effect.Fade(”taskRow”+taskID);  
    }
    

    Next step is to create an ajaxified way of adding new tasks. Start off by adding a template row to the html containing the form. It doesn't have to have a submit, just a button whose action will be mapped in javascript with an onclick(). The modelglue xml addition to this has both a GenericCommit which will add the values filled out and the GenericList. Instead of getting back just the row that's added, it gets back everything all tasks. Now the entire list will be updated each time something is added.

    function addTask() {  
     new Ajax.Update(”listOfTasks”,”index.cfm?event=task.commit.ajax&name=” + $('newTaskName').value);  
    }
    

    Last example will be returning xml and using it in Spry. Start off with a task.list.xml which gets the same GenericList of tasks. Instead of the view being an html page, the view will be a file that transforms the query to XML. Creating a custom dspAsXML.cfm page which converts it based on the column names. This could be expanded to convert arrays, structures or beans to XML data to be remixed by spry or elsewhere. There's also a custom tag available, cfjson, which converts an object to json.