Just the weekly tutorials.

Make an Ajax call using jQuery

TABLE OF CONTENTS - In This Edition:

When you talk about using Ajax with jQuery, you can either say little or you can say a lot. I'd like to think that the latter is a more generous choice for the readers of my newsletter! I like to go in detail.

I'm not going to bore you with all the details and syntax of every single parameter you can possibly use. And in the spirit of my previous tutorials, I'd like to focus on practical usage of making Ajax calls.

Let's face it, most things you will do with ajax are about making a GET or POST request and returning the result. The result is the data returned by whatever script file you have chosen to make a call to.

This result is simply the text version of the outcome of executing that file. For example, if you have a PHP file that prints "Hello" and exits, then this "Hello" is what will appear in the result of your Ajax call.

You can pass parameters to an Ajax call just as you would to a web page. An Ajax merely executes a script file, in the same exact way as you would if you typed the URL of that script directly into the address bar in your browser.

First things first. Let me just put it out there that in order to make an Ajax call, jQuery has a special function that looks like this:

$.ajax("script.php");

Really, it's that simple. But as you may know the devil is in detail. This will merely call the file script.php (note, it can be script.asp, data.txt, an image, XML file or any other file that your browser can open).

What's important is the return value. The example above ignores the return value completely. Luckily, jQuery allows us to capture it. In order for us to see this in action, we need to use a slightly different syntax shown below:

$.ajax( { url: "script.php", type: "post", success: function(result) { alert(result); } });

Still the same function. The only difference is that now we are using an array of named objects: url, type and success. This function takes many other parameters, separated by comma. They can be a string, or a function closure.

A function closure is a nameless function that has no reference to itself. (That name would be the reference, but we don't have it). This means that we cannot refer to this function by its address in memory.

Note that the "result" parameter passed to the success function is the data received from the script. You are the one to decide what that returned data should be within your "script.php" file. Again, it can be XML, plain text or any other kind of data, depending on the purpose of your asynchronous HTTP request.

You can format the function above in any way you wish, but the point is that you specify either the POST or GET type using the "type" parameter.

Remember that everything in Javascript is an object? This is what makes it possible to assign a function closure to the success parameter in the example above. Even "script.php" and "post" values are actually objects of type String!

Using Ajax to retrieve values from an HTML form

<b>Forms:</b> jQuery Ajax is incredibly helpful when dealing with HTML web forms. Using selectors it is possible to collect and send all values from all fields of the form directly to your form processing script... without explicitly retyping the id's, names or values of the form elements.

Let's take a look at how you can use jQuery selectors along with Ajax to submit information from an arbitrary form.

Let's say we have a form like this:

<div id = "form"> <input type = "text" id = "name"><br/> <input type = "text" id = "email_address"><br/> <input type = "text" id = "number"><br/> <input type = "submit" onclick = "$.ajax({url:'submit.php' + getform('input', '#form'), type:'post'})"> </div>

Please note that there is no need to use the form tag at all, unless you think you have to, or can't help it. We are avoiding the regular browser-way HTML form submit and overriding it with our own <i>onclick</i> attribute.

There is one curious thing about this code. What is this getform('input', '#form') function?

As you can see, this function returns the parameters we are passing to submit.php, but where does it get them from? It gets them directly from the input elements in our form. The second parameter is '#form' - it is the context. We already discussed context in my previous jQuery tutorial called How to speed up jQuery selectors. Head there to refresh your memory.

The first parameter "input" lets us specify a jQuery selector. In this case, we only have input fields. But if we had textareas for example, I could also say:

$.ajax({url:'submit.php' + getform('textarea,input', '#form'), type:'post'});

Let's take a look at the definition of <i>getform</i> function:

function getform(input, form) { <span style = "color:#859cc2">/* Copyright Greg Sidelnikov - www.learnjquery.org - greg.sidelnikov@gmail.com You can use it in your own projects, retain this line, if you wish to give me credit. */</span> var ret = "?"; var Length = $(element, parent).length; var idnamelist = new Array(); var idvaluelist = new Array(); for (var i = 0; i < Length; i++) { idnamelist[i] = $(element, parent)[i].id; idvaluelist[i] = $(element, parent)[i].value; ret = idnamelist[i] + '=' + idvaluelist[i]; if (i < Length - 1) ret += "&"; } }

You can further simplify this function, but the point is that I broke it down into variables to make sure it's easy to see what's going on.

The <i>getform</i> function goes through all elements of type which is specified in the first parameter. As we just discussed you can use just one element "input" in this parameter, or you can add others. You just have to separate them by comma as in "input,textarea". This will be passed on to the dollar sign function as a jQuery selector. The second selector is just the context. We don't want to look at all input fields on the page, only those within the DIV element with id = "form".

That's it! When the Submit button is clicked, jQuery fires an asynchronous ajax call to execute "script.php" file, effectively passing all id's and values of every single input element in our form. You don't have to do anything else. There is no more Javascript code to write, and it will work even if you add more input fields into this form, or even textareas. Just make sure they all reside within the DIV with the id = "form".

This was one example of how you can use jQuery Ajax in practice. With little code, we can accomplish so much.

Inserting Form Values into MySQL Database on Submit

The form example wouldn't be complete without us knowing how to insert this form data into the MySQL database.

In the previous part of this tutorial, using jQuery we were able to effectively collect all input IDs and VALUEs associated with those IDs, and put them into a neat submit script.

No matter what input elements you place into this form, they will be automatically passed to the submit.php script, thank goodness for the getform(selector, context) function. You can add new input elements or delete existing ones. It will still work as long as each input element is assign an ID attribute with a unique name.

But how do we insert this data into a MySQL database? Well, that's the responsibility of our submit.php script. This is the script that is being called by our jQuery ajax function.

But before we look at submit, I'd like to intoduce a PHP helper function that will allow us to do basic things with MySQL database. Let's take a look at what's inside:

<?php <span style = "color:#859cc2"> /* Copyright Greg Sidelnikov - www.learnjquery.org - greg.sidelnikov@gmail.com You can use it in your own projects, retain this line, if you wish to give me credit. */ /* Database manipulation class - place it into a separate file such as "Classes/class.Database.php" Include it from any other file that needs database access functionality, using the "include" directive */</span> final class MysqlDatabase { <span style = "color:#859cc2"> /* Define the configuration vars: database hosting server address, username, password and database catalog name */</span> private $HOST = "127.0.0.1"; <span style = "color:#859cc2">// Replace with your own</span> private $USER = "some_user"; private $PASSWORD = "MyPassword123!"; private $CATALOG = "form_data"; <span style = "color:#859cc2">// Name of the catalog to access</span> public $m_connected; public $m_objDatabase; private $m_container; <span style = "color:#859cc2">// Constructing this class will connect to the database</span> function __construct() { //print "constructing database connection. . ."; // Connection status $this->m_connected = false; <span style = "color:#859cc2">// Attempt a database connection</span> if (($this->m_objDatabase = mysql_connect( $this->$HOST, $this->$USER, $this->$PASSWORD )) != FALSE) { <span style = "color:#859cc2">// Choose character set to be UTF8, this is best for most things</span> mysql_set_charset('utf8', $this->m_objDatabase); <span style = "color:#859cc2">// Are we able to select the catalog?</span> if ( !mysql_select_db( $this->CATALOG ) ) { $this->disconnect(); print "MysqlDatabase::~ctor() -> mysql_select_db(); error: " . mysql_error(); exit; } } else <span style = "color:#859cc2">// Unable to Connect to database?</span> { print "MysqlDatabase::~ctor() -> mysql_connect(); error: " . mysql_error(); exit; } $this->m_connected = true; <span style = "color:#859cc2">// If we are still here, we must be connected</span> } function __destruct() { $this->disconnect(); } <span style = "color:#859cc2">// func isReady // Returns true if a connection to the database has been successfully established, // and the main database has been selected</span> public function isReady() { return $this->m_connected; } <span style = "color:#859cc2">// func disconnect // Terminate connection</span> public function disconnect() { $this->m_connected = false; if ($this->m_objDatabase) { mysql_close($this->m_objDatabase); $this->m_objDatabase = NULL; } } <span style = "color:#859cc2"> // This function allows us to easily insert data into the database, // It returns last insert ID from this transaction</span> static public function insertTableData($table, $columns, $values) { if (!$table || !$columns || !$values) { print "MysqlDatabase::insertTableData($table, $columns, $values); has failed! insufficient parameters"; return false; } <span style = "color:#859cc2">// Convert columns and values array parameters to strings - // The acceptable format for MySQL queries</span> $cols = array_to_list($columns,"`"); $vals = array_to_list($values,"'"); $query = "INSERT INTO $table ($cols) VALUES ($vals)"; if (mysql_query($query) != FALSE) return mysql_insert_id(); return false; } } ?>

Place this code into a separate file, say class.Database.php and put it in a convenient place on your server.

The above class uses a utility function called array_to_list. This function takes two parameters, the array of data (usually of type string because it contains names of table columns like first_name, last_name, email_address, etc.) and the second parameter is the quote character you want to use in the resulting string.

The result value is a string of names separated by a comma. Each name is wrapped with whatever quote you specify as second parameter. The default is the ` quote, not ' or ". I find that this is the best quote character to use in MySQL queries for wrapping a column name in. Of course you can use ' or " by overriding the second parameter of this function, but it's up to you.

<span style = "color:#859cc2"> // Convert values of an array to a list "quoted" by the character specified as the second $quote parameter. // This function allows us to convert arrays of data (of type string) into MySQL query parameters // This way we can pass an array of values, rather than typing them out ourselves and typing quotes around them.</span> function array_to_list($ar,$quote="`") { $l = ""; if (is_array($ar)) { $ac = count($ar); if ($ac>0) for ($i=0; $i<$ac; $i++) { $l .= $quote.$ar[$i]; if ($i + 1 < $ac) $l .= "$quote,"; else $l .= "$quote"; } return $l; } return false; }

Put this function into a file and name it "utility.php", or whatever you think is best.

Now... Let's look at submit.php, which will conveniently include our utility function array_to_list, used by our database manipulation class:

include("utility.php"); <span style = "color:#859cc2">// add array_to_list() first because class.Database.php requires it.</span> include("class.Database.php"); <span style = "color:#859cc2">// now add the main database manipulation class.</span> <span style = "color:#859cc2">// We know that the results from the form will be stored in $_POST.</span> <span style = "color:#859cc2">// Go through each id/value pair, and store them in arrays</span> foreach($_POST as $k => $v) { $names[count($names)] = $k; $vals[count($vals)] = addslashes($v); } <span style = "color:#859cc2"> // We now have two sets of data, in one we have names (gathered from ID of the input element), // In the other we have the value: which is whatever the user typed into that input box. // The database __assumes__ that you already have columns named with the same names as your input element ID // If you want to make this function even better, you can auto-create these columns right below this comment // First, you would check if such a column exists in your database. // If it doesn't, you would create it. If it does, you do nothing and proceed to the "insert" part below. // Mysql query language offers easy ways to do both of these things easily, just figure out what they are :) // Now open database connection, and insert these arrays into your table with just a single function call:</span> $Connection = new MysqlDatabase(); <span style = "color:#859cc2">// connect to the database</span> if (isset($Connection) && $Connection->isReady()) { MysqlDatabase::insertTableData("myform", $names, $values); }

I like code that you can "read" by just reading through it. Like a poem :) It just makes sense.

Notice a peculiarity in the foreach loop when I am enumerating the $_POST array we just received from our ajax call. Why am I using count($names) and count ($values) as an index to insert the value to instead of counting things using something like $++ or a similar indexing variable?

Well, the count function will return 0 for arrays that don't exist. Once we add one entry, it will return 1, then 2... and so on. The size of the array always points to its "next" placeholder available to us. So there isn't a need to use an $index variable at all. Moreover, this makes code look less cluttered and more <i>elegant</i>.

I have to also use the addslahes function, because we will be wrapping our resulting strings in our own quotes. This, however, depends on your database configuration. You will either have to add "magic quotes" or leave the input raw. You'll have to look into your database config files on the host server.

Ajax: Conclusion

Submitting forms is not the only use of Ajax, but in combination with PHP and MySQL it can be a powerful tool for making your form submitting easy.

In the future I'm likely to add even more practical examples of using ajax here. Who said that we have to stop here?

<b>Web development</b> is all about combinations of different languages, platforms and technologies. That's why it's difficult to talk about one without mentioning the others... and be complete.

I hope that this code can be re-used by others, or at least it could give you an idea of how combinations of different languages can effectively make your scripts really great. Don't stop here at just learning Ajax and jQuery, learn other languages as well.

Please note that I often revise my tutorials. And sometimes I even add extra content that wasn't there before. This usually happens when inspiration strikes me. Sometimes the right time to write about a subject is not the same time when you begin a new article. Your feedback can be helpful at times like these :)

Just the weekly tutorials.