Thursday, October 24, 2013

Ajax with the Dojo Toolkit - Tutorial

Dojo
This article describes the usage of the Dojo toolkit for JavaScript programming. Dojo is an Ajax toolkit.

1. Ajax - Asynchronous JavaScript and XML

1.1. Overview

Ajax (Asynchronous JavaScript and XML) describes the possibility to communicate with the web server in the background and to update a webpage with information from the web server without re-loading the webpage.
Ajax can improve the usability of a webpage, e.g. a webpage can quickly be displayed while information is still loaded from the web server.
Ajax is based on the XMLHttpRequest and is considered to by a key technology to realize Web 2.0. For details on the XMLHttpRequest please see the resource section of this article.

1.2. Introduction to JavaScript

This article assume some familiarity with JavaScript. Please see Javascript - Tutorial for a introduction into JavaScript.

2. Installing Dojo

Download the "Dojo Toolkit" from http://dojotoolkit.org/ and extract the zip file. As of the time of writing this article the release of dojo is version 1.3.1. Rename the name directory to "dojoroot". Put this directory into a folder "web".

Tip

I recommend that you use the proposed folder names, this makes it easier to follow this tutorial.
The folder structure should look like the following.

3. Eclipse

The following examples work without Eclipse but Eclipse provides nice editors for html pages and css style sheets.
If you want you can use Eclipse Eclipse installation.
If you want to use Eclipse for the following examples, create a general project "de.vogella.dojo.client" via File-> New -> Project -> General -> Project. Create a folder "web" in this project and copy "dojoroot" in the folder "web".
The following will refer always to the folder "web". If you are using Eclipse use your project, otherwise use the file structure.

4. Your first Dojo pages

4.1. Table handling

In your directory "web" create a table.html file with the following content.

Tip

The following uses the dojo cascading style sheets (css). If you want to overwrite any of these style can assume that you also include another style sheet after the dojo css include and overwrite any style you like.
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html>
<head>
<script type="text/javascript" src="dojoroot/dojo/dojo.js"
djConfig="parseOnLoad: true, isDebug: false"></script>

<script language="JavaScript" type="text/javascript">
dojo.require("dijit.TitlePane");
dojo.require("dojo.parser");
</script>

<style type="text/css">
@import "dojoroot/dijit/themes/tundra/tundra.css";
</style>
</head>
<body class="tundra">
<div dojoType="dijit.TitlePane"
title="Title is displayed" style="width: 300px;">
Cool context
</div>
</body>
</html>
Load the created webpage in a browser. You get a table with can be minimized and maximized again.
This example shows the same table but is closed by default
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
<html>
<head>
<script type="text/javascript" src="dojoroot/dojo/dojo.js"
djConfig="parseOnLoad: true, isDebug: false"></script>

<script language="JavaScript" type="text/javascript">
dojo.require("dijit.TitlePane");
dojo.require("dojo.parser");
</script>

<style type="text/css">
@import "dojoroot/dijit/themes/tundra/tundra.css";
</style>
</head>
<body class="tundra">
<div dojoType="dijit.TitlePane"
title="This Title is closed by default" open="false" style="width: 300px;">
Context is at loading time not visible
</div>
</body>

</html>

4.2. Tooltip

This HTML file uses a tooltip on one element.
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN"
"http://www.w3.org/TR/html4/strict.dtd">
<html>
<head>
<title>Dojo Tooltip Widget Test</title>

<style type="text/css">
@import "./dojoroot/dijit/themes/tundra/tundra.css";
@import "./dojoroot/dojo/resources/dojo.css"
</style>

<script type="text/javascript" src="./dojoroot/dojo/dojo.js"
djConfig="parseOnLoad: true, isDebug: false"></script>

<script type="text/javascript">
dojo.require("dijit.Tooltip");
</script>

</head>
<body class="tundra">
<span id="s1">s1 text</span><br><br><br>

<span dojoType="dijit.Tooltip" connectId="s1">s1 tooltip</span>

</body>
</html>


5. Accessing the server

5.1. Reading a fixed file from a server

Dojo allows you to read data from the server. The following HTML page will connect the server and asynchronously load the content from the web server. In this example the loaded content is a static text page.
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
<html>
<head>
<script type="text/javascript" src="dojoroot/dojo/dojo.js"
djConfig="parseOnLoad: true, isDebug: false">
</script>


<script type="text/javascript">
function readFile() { //
dojo.xhrGet({ //
// The following URL must match that used to test the server.
url: "http://www.vogella.com/articles/AjaxwithDojo/download/includeTextFile.txt",
handleAs: "text",

timeout: 5000, // Time in milliseconds

// The LOAD function will be called on a successful response.
load: function(response, ioArgs) { //
dojo.byId("replace").innerHTML = response; //
return response; //
},

// The ERROR function will be called in an error case.
error: function(response, ioArgs) { //
console.error("HTTP status code: ", ioArgs.xhr.status); //
dojo.byId("replace").innerHTML = 'Loading the ressource from the server did not work'; //
return response; //
}
});
}
</script>
<script type="text/javascript">
dojo.addOnLoad(readFile);
</script>
</head>
<body>
<div id="replace" style="font-size: big"></div>
</body>
</html>

Tip

This example may not be running on a local file system. If you do not see something try to replace the URL http://www.vogella.com/articles/AjaxwithDojo/download/includeTextFile.txt with a path to a local file. This should then also work with a local running HTML page.
Start the HTML. The Dojo javascript will access the text file in the background and update the webpage with the information once the text file is read.
Welcome to the world of Ajax! You successfully loaded a content from a website and included the response into your existing HTML page.

5.2. Send data to the server and update the page with the response

Now you need a build a server side application. I'm going to use Java Servlets for this but you can use any other language on the server you like, e.g. Perl, PHP, etc.
Create the following Java servlet, compile it and deploy it to your server. I'm going to assume that the servlet will be running on the URL yourhomepage/servlets/ReturnParameters.
package testing;

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;


/**
* Servlet implementation class for Servlet: ReturnParameters
*
*/

public class ReturnParameters extends javax.servlet.http.HttpServlet implements
javax.servlet.Servlet {
static final long serialVersionUID = 1L;

/*
* (non-Java-doc)
*
* @see javax.servlet.http.HttpServlet#HttpServlet()
*/

public ReturnParameters() {
super();
}

/*
* (non-Java-doc)
*
* @see javax.servlet.http.HttpServlet#doGet(HttpServletRequest request,
* HttpServletResponse response)
*/

protected void doGet(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException {

String url = "";
String name = "";
boolean check = true;
url = request.getParameter("url");
name = request.getParameter("name");
if (url==null|| name == null){
check=false;
}
response.setContentType("text/html");
PrintWriter out = response.getWriter();

out.println("<head><title>Response</title>");
if (check == false) {
out.println("Missing Parameters");
} else {
out.println("You name is " + name + " and the supplied URL is "
+ url + ".");
}
out.println("</head>");
out.println("");
}
}
Now create the following HTML page which calls the servlet with two parameters and displays the result at a certain place in the application.
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">

<html>
<head>
<script type="text/javascript" src="dojoroot/dojo/dojo.js"
djConfig="parseOnLoad: true, isDebug: false">
</script>


<script type="text/javascript">
function readFile() { //
dojo.xhrGet({
// The following URL must match that used to test the server.
url: "http://www.jnerlich.de/servlets/ReturnParameters",
handleAs: "text",
timeout: 5000, // Time in milliseconds


// The LOAD function will be called on a successful response.
load: function(response, ioArgs) { //
// Search for the HTML tag with the ID "replace" and replace it with the answer of
// of the servlet call
dojo.byId("replace").innerHTML = response; //
return response; //
},

// The ERROR function will be called in an error case.
error: function(response, ioArgs) { //
console.error("HTTP status code: ", ioArgs.xhr.status); //
dojo.byId("replace").innerHTML = 'Loading the ressource from the server did not work'; //
return response; //
},

// Here you put the parameters to the server side program
// We send two hard-coded parameters
content: {name: "lars", url:"testing" }
});
}
</script>

<script type="text/javascript">
dojo.addOnLoad(readFile);
</script>
</head>
<body>

<!--This is the tag which will be replaced by the AJAX call -->
<div id="replace" style="font-size: big"></div>

</body>

</html>

1 comment: