Book Image

Django JavaScript Integration: AJAX and jQuery

By : Jonathan Hayward
Book Image

Django JavaScript Integration: AJAX and jQuery

By: Jonathan Hayward

Overview of this book

<p>You want to create an AJAX application. Why would you use Django? Why would you use jQuery? Why would you use both together? Enter <i>Django JavaScript Integration: AJAX and jQuery</i> &ndash; your comprehensive answer to all these questions and the only extensive, practical, and hands-on guide to developing any AJAX application with Django and jQuery.</p> <p>Gone are the days when you used to lament over the lack of official documentation on AJAX with Django. This book will teach you exactly why Django is called "<i>The web framework for perfectionists with deadlines</i>", how jQuery &ndash; the "<i>write less do more</i>" JavaScript library &ndash; is practically a virtual higher-level language, and why they both deserve to be integrated with AJAX.</p> <p>This hands-on-guide shows you how to put Django and jQuery together in the process of creating an AJAX application. In this book, they are brought together in a real-world scenario, with attention to usability, to build and develop an AJAX application.</p> <p>The first two chapters provide a short and necessary introduction to the world of Django, jQuery, and AJAX; and the remaining chapters are based on a case study that will make you realize the immense potential and benefits of integrating Django and jQuery with your AJAX application.</p> <p>By the time you are done with this book, you'll be developing your AJAX applications with Django and jQuery in less time than you can say "integrate".</p> <p>You will cover the basics of AJAX; use jQuery, the commonest JavaScript library, on the client side, and learn form validation with an eye to usability, build things with Django on the server-side, handle login and authentication via Django-based AJAX, and then dip into the rich jQuery plugin ecosystem to build in-place editing into your pages. You will add auto-complete functionality courtesy of jQuery UI, easily build forms with Django ModelForm, and then look at a client-side search implementation that can look things up without network access after initial download. You will learn to Implement a simple, expandable undo system, and offer more full-blooded account management, tinker, fix some bugs, offer a more usable way to handle password input, add local time support for people who are not in your time zone, look at usability, and finally take a look at debugging.</p> <p>After working through this book, you will have both an AJAX application and a deep understanding that you can use to customize, extend, and further develop it in your organization.</p> <p>This book has been written and tested for Django v 1.2.3 and jQuery v 1.4.4.</p>
Table of Contents (20 chapters)
Django JavaScript Integration: AJAX and jQuery
Credits
Foreword
About the Author
About the Reviewers
www.PacktPub.com
Preface
Index

Ajax and the XMLHttpRequest object


Ajax is not a technology like JavaScript or CSS, but is more like an overlaid function. So, what exactly is that?

Human speech: An overlaid function

Human speech is an overlaid function. What is meant by this is reflected in the answer to a question: "What part of the human body has the basic job of speech?" The tongue, for one answer, is used in speech, but it also tastes food and helps us swallow. The lungs and diaphragm, for another answer, perform the essential task of breathing. The brain cannot be overlooked, but it also does a great many other jobs. All of these parts of the body do something more essential than speech and, for that matter, all of these can be found among animals that cannot talk. Speech is something that is overlaid over organs that are there in the first place because of something other than speech.

Something similar to this is true for Ajax, which is not a technology in itself, but something overlaid on top of other technologies. Ajax, some people say, stands for Asynchronous JavaScript and XML, but that was a retroactive expansion. JavaScript was introduced almost a decade before people began seriously talking about Ajax. Not only is it technically possible to use Ajax without JavaScript (one can substitute VBScript at the expense of browser compatibility), but there are quite a few substantial reasons to use JavaScript Object Notation (JSON) in lieu of heavy-on-the-wire eXtensible Markup Language (XML). Performing the overlaid function of Ajax with JSON replacing XML is just as eligible to be considered full-fledged Ajax as a solution incorporating XML.

Ajax: Another overlaid function

What exactly is this overlaid function?

Ajax is a way of using client-side technologies to talk with a server and perform partial page updates. Updates may be to all or part of the page, or simply to data handled behind the scenes. It is an alternative to the older paradigm of having a whole page replaced by a new page loaded when someone clicks on a link or submits a form. Partial page updates , in Ajax, are associated with Web 2.0, while whole page updates are associated with Web 1.0; it is important to note that "Web 2.0" and "Ajax" are not interchangeable. Web 2.0 includes more decentralized control and contributions besides Ajax, and for some objectives it may make perfect sense to develop an e-commerce site that uses Ajax but does not open the door to the same kind of community contributions as Web 2.0.

Some of the key features common in Web 2.0 include:

  • Partial page updates with JavaScript communicating with a server and rendering to a page

  • An emphasis on user-centered design

  • Enabling community participation to update the website

  • Enabling information sharing as core to what this communication allows

The concept of "partial page updates" may not sound very big, but part of its significance may be seen in an unintended effect. The original expectation of partial page updates was that it would enable web applications that were more responsive. The expectation was that if submitting a form would only change a small area of a page, using Ajax to just load the change would be faster than reloading the entire page for every minor change. That much was true, but once programmers began exploring, what they used Ajax for was not simply minor page updates, but making client-side applications that took on challenges more like those one would expect a desktop program to do, and the more interesting Ajax applications usually became slower. Again, this was not because you could not fetch part of the page and update it faster, but because programmers were trying to do things on the client side that simply were not possible under the older way of doing things, and were pushing the envelope on the concept of a web application and what web applications can do.

The technologies Ajax is overlaid on

Now let us look at some of the technologies where Ajax may be said to be overlaid.

JavaScript

JavaScript deserves pride of place, and while it is possible to use VBScript for Internet Explorer as much more than a proof of concept, for now if you are doing Ajax, it will almost certainly be Ajax running JavaScript as its engine. Your application will have JavaScript working with XMLHttpRequest, JavaScript working with HTML, XHTML, or HTML5; JavaScript working with the DOM, JavaScript working with CSS, JavaScript working with XML or JSON, and perhaps JavaScript working with other things.

While addressing a group of Django developers or Pythonistas, it would seem appropriate to open with, "I share your enthusiasm." On the other hand, while addressing a group of JavaScript programmers, in a few ways it is more appropriate to say, "I feel your pain." JavaScript is a language that has been discovered as a gem, but its warts were enough for it to be largely unappreciated for a long time. "Ajax is the gateway drug to JavaScript," as it has been said—however, JavaScript needs a gateway drug before people get hooked on it. JavaScript is an excellent language and a terrible language rolled into one.

Before discussing some of the strengths of JavaScript—and the language does have some truly deep strengths—I would like to say "I feel your pain" and discuss two quite distinct types of pain in the JavaScript language.

The first source of pain is some of the language decisions in JavaScript:

  • The Wikipedia article says it was designed to resemble Java but be easier for non-programmers, a decision reminiscent of SQL and COBOL.

  • The Java programmer who finds the C-family idiom of for(i = 0; i < 100; ++i) available will be astonished to find that the functions are clobbering each other's assignments to i until they are explicitly declared local to the function by declaring the variables with var. There is more pain where that came from.

The following two functions will not perform the naively expected mathematical calculation correctly; the assignments to i and the result will clobber each other:

function outer()
    {
    result = 0;
    for(i = 0; i < 100; ++i)
        {
        result += inner(i);
        }
    return result
    }

function inner(limit)
    {
    result = 0;
    for(i = 0; i < limit; ++i)
        {
        result += i;
        }
    return result;
    }

The second source of pain is quite different. It is a pain of inconsistent implementation: the pain of, "Write once, debug everywhere." Strictly speaking, this is not JavaScript's fault; browsers are inconsistent. And it need not be a pain in the server-side use of JavaScript or other non-browser uses. However, it comes along for the ride for people who wish to use JavaScript to do Ajax. Cross-browser testing is a foundational practice in web development of any stripe; a good web page with semantic markup and good CSS styling that is developed on Firefox will usually look sane on Internet Explorer (or vice versa), even if not quite pixel-perfect. But program directly for the JavaScript implementation on one version of a browser, and you stand rather sharp odds of your application not working at all on another browser. The most important object by far for Ajax is the XMLHttpRequest and not only is it not the case that you may have to do different things to get an XMLHttpRequest in different browsers or sometimes different (common) versions of the same browser, and, even when you have code that will get an XMLHttpRequest object, the objects you have can be incompatible so that code that works on one will show strange bugs for another. Just because you have done the work of getting an XMLHttpRequest object in all of the major browsers, it doesn't mean you're home free.

Before discussing some of the strengths of the JavaScript language itself, it would be worth pointing out that a good library significantly reduces the second source of pain. Almost any sane library will provide a single, consistent way to get XMLHttpRequest functionality, and consistent behavior for the access it provides. In other words, one of the services provided by a good JavaScript library is a much more uniform behavior, so that you are programming for only one model, or as close as it can manage, and not, for instance, pasting conditional boilerplate code to do simple things that are handled differently by different browser versions, often rendering surprisingly different interpretations of JavaScript. We will be using the jQuery library in this book as a standard, well-designed, lightweight library. Many of the things we will see done well as we explore jQuery are also done well in other libraries.

We previously said that JavaScript is an excellent language and a terrible language rolled into one; what is to be said in favor of JavaScript? The list of faults is hardly all that is wrong with JavaScript, and saying that libraries can dull the pain is not itself a great compliment. But in fact, something much stronger can be said for JavaScript:If you can figure out why Python is a good language, you can figure out why JavaScript is a good language.

I remember, when I was chasing pointer errors in what became 60,000 lines of C, teasing a fellow student for using Perl instead of a real language. It was clear in my mind that there were interpreted scripting languages, such as the bash scripting that I used for minor convenience scripts, and then there were real languages, which were compiled to machine code. I was sure that a real language was identified with being compiled, among other things, and that power in a language was the sort of thing C traded in. (I wonder why he didn't ask me if he wasn't a real programmer because he didn't spend half his time chasing pointer errors.) Within the past year or so I've been asked if "Python is a real programming language or is just used for scripting," and something similar to the attitude shift I needed to appreciate Perl and Python is needed to properly appreciate JavaScript.

The name "JavaScript" is unfortunate; like calling Python "Assembler Kit", it's a way to ask people not to see its real strengths. (Someone looking for tools for working on an assembler would be rather disgusted to buy an "Assembler Kit" and find Python inside. People looking for Java's strengths in JavaScript will almost certainly be disappointed.)

JavaScript code may look like Java in an editor, but the resemblance is a façade; besides Mocha, which had been renamed LiveScript, being renamed to JavaScript just when Netscape was announcing Java support in web browsers, it is has been described as being descended from NewtonScript, Self, Smalltalk, and Lisp, as well as being influenced by Scheme, Perl, Python, C, and Java. What's under the Java façade is pretty interesting. And, in the sense of the simplifying "façade" design pattern, JavaScript was marketed in a way almost guaranteed not to communicate its strengths to programmers. It was marketed as something that nontechnical people could add snippets of, in order to achieve minor, and usually annoying, effects on their web pages. It may not have been a toy language, but it sure was dressed up like one.

Python may not have functions clobbering each other's variables (at least not unless they are explicitly declared global), but Python and JavaScript are both multiparadigm languages that support object-oriented programming, and their versions of "object-oriented" have a lot in common, particularly as compared to (for instance) Java. In Java, an object's class defines its methods and the type of its fields, and this much is set in stone. In Python, an object's class defines what an object starts off as, but methods and fields can be attached and detached at will. In JavaScript, classes as such do not exist (unless simulated by a library such as Prototype), but an object can inherit from another object, making a prototype and by implication a prototype chain, and like Python it is dynamic in that fields can be attached and detached at will. In Java, the instanceof keyword is important, as are class casts, associated with strong, static typing; Python doesn't have casts, and its isinstance() function is seen by some as a mistake, hence the blog posting "isinstance() considered harmful" at http://www.canonical.org/~kragen/isinstance/.

The concern is that Python, like JavaScript, is a duck-typing language: If it looks like a duck, and it quacks like a duck, it's a duck! In a duck-typing language, if you write a program that polls weather data, and there's a ForecastFromScreenscraper object that is several years old and screenscrapes an HTML page, you should be able to write a ForecastFromRSS object that gets the same information much more cleanly from an RSS feed. You should be able to use it as a drop-in replacement as long as you have the interface right. That is different from Java; at least if it were a ForecastFromScreenscraper object, code would break immediately if you handed it a ForecastFromRSS object. Now, in fairness to Java, the "best practices" Java way to do it would probably separate out an IForecast interface, which would be implemented by both ForecastFromScreenscraper and later ForecastFromRSS, and Java has ways of allowing drop-in replacements if they have been explicitly foreseen and planned for. However, in duck-typed languages, the reality goes beyond the fact that if the people in charge designed things carefully and used an interface for a particular role played by an object, you can make a drop-in replacement. In a duck-typed language, you can make a drop-in replacement for things that the original developers never imagined you would want to replace.

JavaScript's reputation is changing. More and more people are recognizing that there's more to the language than design flaws. More and more people are looking past the fact that JavaScript is packaged like Java, like packaging a hammer to give the impression that it is basically like a wrench. More and more people are looking past the silly "toy language" Halloween costume that JavaScript was stuffed into as a kid.

One of the ways good programmers grow is by learning new languages, and JavaScript is not just the gateway to mainstream Ajax; it is an interesting language in itself. With that much stated, we will be making a carefully chosen, selective use of JavaScript, and not make a language lover's exploration of the JavaScript language, overall. Much of our work will be with the jQuery library; if you have just programmed a little "bare JavaScript", discovering jQuery is a bit like discovering Python, in terms of a tool that cuts like a hot knife through butter. It takes learning, but it yields power and interesting results soon as well as having some room to grow.

XMLHttpRequest

The XMLHttpRequest object is the reason why the kind of games that can be implemented with Ajax technologies do not stop at clones of Tetris and other games that do not know or care if they are attached to a network. They include massive multiplayer online role-playing games where the network is the computer. Without having something like XMLHttpRequest, "Ajax chess" would probably mean a game of chess against a chess engine running in your browser's JavaScript engine; with XMLHttpRequest, "Ajax chess" is more likely man-to-man chess against another human player connected via the network. The XMLHttpRequest object is the object that lets Gmail, Google Maps, Bing Maps, Facebook, and many less famous Ajax applications deliver on Sun's promise: the network is the computer.

There are differences and some incompatibilities between different versions of XMLHttpRequest, and efforts are underway to advance "level-2-compliant" XMLHttpRequest implementations, featuring everything that is expected of an XMLHttpRequest object today and providing further functionality in addition, somewhat in the spirit of level 2 or level 3 CSS compliance. We will not be looking at level 2 efforts, but we will look at the baseline of what is expected as standard in most XMLHttpRequest objects.

The basic way that an XMLHttpRequest object is used is that the object is created or reused (the preferred practice usually being to reuse rather than create and discard a large number), a callback event handler is specified, the connection is opened, the data is sent, and then when the network operation completes, the callback handler retrieves the response from XMLHttpRequest and takes an appropriate action.

A bare-bones XMLHttpRequest object can be expected to have the following methods and properties.

Methods

A bare-bones XMLHttpRequest object can be expected to have the following methods:

  1. XMLHttpRequest.abort()

    This cancels any active request.

  2. XMLHttpRequest.getAllResponseHeaders()

    This returns all HTTP response headers sent with the response.

  3. XMLHttpRequest.getResponseHeader(headerName)

    This returns the requested header if available, or a browser-dependent false value if the header is not defined.

  4. XMLHttpRequest.open(method, URL),

    XMLHttpRequest.open(method, URL, asynchronous),

    XMLHttpRequest.open(method, URL, asynchronous, username),

    XMLHttpRequest.open(method, URL, asynchronous, username, password)

    The method is GET, POST, HEAD, or one of the other less frequently used methods defined for HTTP.

    The URL is the relative or absolute URL to fetch. As a security measure for JavaScript running in browsers on trusted internal networks, a same origin policy is in effect, prohibiting direct access to servers other than one the web page came from. Note that this is less restrictive than it sounds, as it is entirely permissible for the server to act as a proxy for any server it has access to: for developers willing to undertake the necessary chores, other sites on the public internet are "virtually accessible".

    The asynchronous variable defaults to true, meaning that the method call should return quickly in most cases, instead of waiting for the network operation to complete. Normally this default value should be preserved. Among other problems, setting it to false can lock up the visitor's browser.

    The last two arguments are the username and password as optionally specified in HTTP. If they are not specified, they default to any username and password defined for the web page.

  5. XMLHttpRequest.send(content)

    Content can be a string or a reference to a document.

Properties

A bare-bones XMLHttpRequest object can be expected to have the following properties:

  1. XMLHttpRequest.onreadystatechange,

    XMLHttpRequest.readyState

    In addition to the provided methods, the reference to one other method is supplied by the developer as a property, XMLHttpRequest.onreadystatechange, which is called without argument each time the ready state of XMLHttpRequest changes. An XMLHttpRequest object can have five ready states:

    • Uninitialized, meaning that open() has not been called.

    • Open, meaning that open() has been called but send() has not.

    • Sent, meaning that send() has been called, and headers and status are available, but the response is not yet available.

    • Receiving, meaning that the response is being downloaded and responseText has the portion that is presently available.

    • Loaded, meaning that the network operation has completed. If it has completed successfully (that is, the HTTP status stored in XMLHttpRequest.status is 200), this is when the web page would be updated based on the response.

  2. XMLHttpRequest.responseText, XMLHttpRequest.responseXML

    The text of the response. It is important to note that while the name "XMLHttpRequest" is now very well established, and it was originally envisioned as a tool to get XML, the job done today is quite often to get text that may or may not happen to be XML. While there have been problems encountered with using XMLHttpRequest to fetch raw binary data, the XMLHttpRequest object is commonly used to fetch not only XML but XHTML, HTML, plain text, and JSON, among others. If it were being named today, it would make excellent sense to name it "TextHttpRequest." Once the request reaches a ready state of 4 ("loaded"), the responseText field will contain the text that was served up, whether the specific text format is XML or anything else. In addition, if the format does turn out to be XML, the responseXML field will hold a parsed XML document.

  3. XMLHttpRequest.status, XMLHttpRequest.statusText

    The status field contains the HTTP code, such as 200 for OK; the statusText field has a short text description, like OK. The callback event handler should ordinarily check XMLHttpRequest.readyState and wait before acting on server-provided data until the readyState is 4. In addition, because there could be a server error or a network error, the callback will check whether the status is 200 or something else: a code like 4xx or 5xx in particular needs to be treated as an error. If the server-response has been transmitted successfully, the readyState will be 4 and the status will be 200.

This is the basic work that needs to be done for the XMLHttpRequest side of Ajax. Other frameworks may simplify this and do much of the cross-browser debugging work for you; we will see in the next chapter how jQuery simplifies this work. But this kind of task is something you will need to have done with any library, and it's worth knowing what's behind the simplified interfaces that jQuery and other libraries provide.

HTML/XHTML

HTML and XHTML make up the bedrock markup language for the web. JavaScript and CSS were introduced in relation to HTML; perhaps some people are now saying that JavaScript is a very interesting language independent of web browsers and using standalone interpreters such as SpiderMonkey and Rhino. However, HTML was on the scene first and other players on the web exist in relation to HTML's story. Even when re-implemented as XHTML, to do HTML's job while potentially making much more sense to parsers, a very early web page, the beginning of the source at http://www.w3.org/History/19921103-hypertext/hypertext/WWW/TheProject.html, is still quite intelligible:

<HEADER>
<TITLE>The World Wide Web project</TITLE> 
<NEXTID N="55"> 
</HEADER>
<BODY> 
<H1>World Wide Web</H1>The WorldWideWeb (W3) 
is a wide-area
<A NAME=0 HREF="WhatIs.html"> 
hypermedia</A> information retrieval
initiative aiming to give universal
access to a large universe of documents.<P> 
Everything there is online about
W3 is linked directly or indirectly
to this document, including an <A NAME=24 HREF="Summary.html">executive
summary</A> of the project, <A NAME=29 HREF="Administration/Mailing/Overview.html">
Mailing lists</A> ,
<A NAME=30 HREF="Policy.html">Policy</A> , November's  <A NAME=34 HREF="News/9211.html">W3  news</A> ,
<A NAME=41 HREF="FAQ/List.html">Frequently Asked Questions
</A> .
<DL>
…

At the time of this writing, HTML 5 is taking shape but is not "out in the wild", and so there are no reports of how the shoe feels after the public has worn it for a while. Code in this book, where possible, will be written in XHTML 1.0 Strict. Depending on your situation, this may or may not be the right decision for you; if you are working with an existing project, the right HTML/XHTML is often the one that maintains consistency within the project.

XML

eXtensible Markup Language (XML) is tied to an attempt to clean up early HTML. At least in earliest forms, HTML was a black sheep among specific markup languages derived from the generalized and quite heavy Standard Generalized Markup Language (SGML). Forgiving web browsers meant, in part, that early web hobbyists could write terrible markup and it would still display well in a browser. The amount of terrible markup on the web was not just an issue for purists; it meant that making a parser that could make sense of early "Wild West" web pages in general was a nearly impossible task. XML is vastly simplified from SGML, but it provides a generic space where an HTML variant, XHTML, could pick up the work done by HTML but not present parsers with unpredictable tag soup. XHTML could be described as HTML brought back into the fold, still good for doing web development, but without making machine interpretation such a hopeless cause. Where early HTML was developed with browsers that were meant to be forgiving, XML requested draconian error handling, and validated XML or XHTML documents are documents that can be parsed in a sensible way.

XML works for exchanging information, and it works where many of its predecessors had failed: it provides interoperability between different systems after a long history of failed attempts at automating B2B communication and failed attempts at automated conversion between text data formats. Notwithstanding this, it is a heavy and verbose solution, with a bureaucratic ambiance, compared in particular to a lean, mean JSON. XML-based approaches to data storage and communication are increasingly critiqued in discussions on the web. If you have a reasonable choice between XML and JSON, we suggest that you seriously consider JSON.

JSON

JavaScript Object Notation (JSON) is a brilliantly simple idea. While formats like XML, ReStructuredText, and so on share the assumption that "if you're going to parse this from your language, your language will need to have a parser added," JSON simply takes advantage of how an object would be specified in JavaScript, and clarifies a couple of minor points to make JSON conceptually simpler and cross-browser friendly. JSON is clear, simple, and concise enough that not only is it a format of choice for JavaScript, but it is gaining traction in other languages, and it is being used for communication between languages that need a (simple, added) parser to parse JSON. The other languages can't use eval() to simply run JSON, and in JavaScript you should have JSON checked to make sure it does not contain malicious JavaScript you should not eval(). However, JSON is turning out to have a much broader impact than the initial "in communicating with JavaScript, just give it code to declare the object being communicated that can simply be evaluated to construct the object."

CSS

Cascading Style Sheets (CSS) may have introduced some new possibilities for presentation, but quite a lot of presentation was already possible beforehand. CSS did not so much add styling capabilities, as it added good engineering to styling (good engineering is the essence of "separating presentation from content"), and make the combination of semantic markup and attractive appearance a far more attainable goal. It allows parlor tricks such as in-place rebranding of websites: making changes in images and changing one stylesheet is, at least in principle, enough to reskin an extensive website without touching a single character of its HTML/XHTML markup. In Ajax, as for the rest of the web, the preferred practice is to use semantic, structural markup, and then add styles in a stylesheet (not inline) so that a particular element, optionally belonging to the right class or given the right ID, will have the desired appearance. Tables are not deprecated but should be used for semantic presentation of tabular data where it makes sense to use not only a td but a th as well. What is discouraged is using the side effect that tables can position content that is not, semantically speaking, tabular data.

The DOM

As far as direct human browsing is concerned, HTML and associated technologies are vehicles to deliver a pickled Document Object Model (DOM), and nothing more. In this respect, HTML is a means to an end: the DOM is the "deserialized object," or better, the "live form" of what we really deliver to people. HTML may help provide a complete blueprint, and the "complete blueprint" is a means to the "fully realized building." This is why solving Ajax problems on the level of HTML text are like answering the wrong question, or at least solving a problem on the wrong level. It is like deciding that you want a painting hung on a wall of a building, and then going about getting it by adding the painting to the blueprint and asking construction personnel to implement the specified change. It may be better to hang the painting on the wall directly, as is done in Ajax DOM manipulations.

document.write() and document.getElementById().innerHTML() still have a place in web development. It is a sensible optimization to want a static, cacheable HTML/XHTML file include that will only be downloaded once in the usual multi-page visit. A JavaScript include with a series of document.write() may be the least Shanghaiing you can do to technologies and still achieve that goal. But this is not Ajax; it is barely JavaScript, and this is not where we should be getting our bearings. In Ajax, a serious alternative to this kind of solution for altering part of a web page is with the DOM.

As the book progresses, we will explore Ajax development that works with the DOM.

iframes and other Ajax variations

Ajax includes several variations; Comet for instance, is a variation on standard Ajax in which either an XMLHttpRequest object's connection to a server is kept open and streaming indefinitely, or a new connection is opened whenever an old one is closed, creating an Ajax environment in which the server as well as the client can push material. This is used, for instance, in some instant messaging implementations. One much more essential Ajax variation has to do with loading documents into seamlessly integrated iframes instead of making DOM manipulations to a single, frame-free web page.

If you click around on the page for a Gmail account, you will see partial page refreshes that look consistent with Ajax DOM manipulations: what happens when you click on Compose Mail, or a filter, or a message subject, looks very much like an Ajax update where the Gmail web application talks with the server if it needs to, and then updates the DOM in accordance with your clicks. However, there is one important difference between Gmail's behavior and a similar Ajax clone that updates the DOM for one frameless web page: what happens when you click the browser "Back" button. Normally, if you click on a link, you trigger an Ajax event but not a whole page refresh, and Ajax optionally communicates with a server and updates some part of the DOM. This does not register in the browser's history, and hitting the Back button would not simply reset the last Ajax partial page update. If you made an Ajax clone of Gmail that used DOM manipulations instead of seamlessly integrated iframes, there would be one important difference in using the clone: hitting Back would do far more than reverse the last DOM manipulation. It would take you back to the login or load screen. In Gmail, the browser's Back button works with surgical accuracy, and the reason it can do something much better than take you back to the login screen is that Gmail is carefully implemented with iframes, and every change that the Back button can undo is implemented by a fresh page load in one of the seamlessly integrated iframes. That creates browsing history.

For that matter, a proof of concept has been created for an Ajax application that does not use client-side scripting or programming, instead using, on the client side, a system of frames/iframes, targets, links, form submissions, and meta refresh tags in order to perform partial page updates. Whether this variant technique lends itself to creating graceful alternatives to standard Ajax implementations, or is only a curiosity merely lending itself to proofs of concept, it is in principle possible to make an Ajax application that loses nothing if a visitor's browser has turned off scripting completely.

Comet and iframes are two of many possible variations on the basic Ajax technique; what qualifies as Ajax is more a matter of Python- or JavaScript-style duck-typing than Java-style static typing. "Asynchronous JavaScript and XML" describes a reference example more than a strict definition, and it is not appropriate to say "if you replace XML with JSON then, by definition, it isn't really Ajax." This is a case of, "the proof of the pudding is in the eating," not what technologies or even techniques are in the kitchen.

JavaScript/Ajax Libraries

This book advocates taking advantage of libraries, and as a limitation of scope focuses on jQuery. If you only learn one library, or if you are starting with just one library, jQuery is a good choice, and it is widely used. It is powerful, but it is also a much easier environment to get started in than some other libraries; in that way, it is somewhat like Python. However, it is best not to ask, "Which one library is best?" but "Which library or libraries are the right tools for this job?", and it is common real-world practice to use more than one library, possibly several.

JavaScript libraries offer several advantages. They can reduce chores and boilerplate code, significantly lessening the pain of JavaScript, and provide a more uniform interface. They can also provide (for instance) ready-made widgets; we will be working with a jQuery slider later on in this book. And on a broad scale, they can let the JavaScript you write be higher-level and a little more Pythonic.

Server-side technologies

Many of the "usual suspects" in client-side technologies have been mentioned. The list of client-side technologies is generally constrained by what is available in common web browsers; the list of available server-side technologies is only constrained by what will work on the server, and any general-purpose programming language can do the job. The question on the server is not "What is available?" but "Which option would you choose?" Python and Django make an excellent choice of server-side technology, and we will work with them in this book.