Now we need a module to enable users to join the new network: that’s Example 21-5, signup.php. This is a slightly longer program, but you’ve seen all its parts before.
Let’s start by looking at the end block of HTML. This is a simple
form that allows a username and password to be entered. But note the use
of the empty <span>
given the
id
of 'info'
. This will be the destination of the Ajax
call in this program that checks whether a desired username is available.
See Chapter 17 for a complete description of how this
works.
Now go back to the program start, and you’ll see a block of
JavaScript that starts with the function checkUser
. This is called by the JavaScript
onBlur
event when focus is removed
from the username field of the form. First it sets the contents of the
<span>
I mentioned (with the
id
of 'info')
to an empty string, which clears it in
case it previously had a value.
Next a request is made to the program checkuser.php, which reports whether the
username user
is available. The
returned result of the Ajax call, a friendly message, is then placed in
the 'info'
span.
After the JavaScript section comes some PHP code that you should
recognize from the discussion of form validation in Chapter 16. This section also
uses the sanitizeString
function to
remove potentially malicious characters before looking up the username
in the database and, if it’s not already taken, inserting the new
username $user
and password $pass
.
Upon successfully signing up, the user is then prompted to log in. A more fluid response at this point might be to automatically log in a newly created user, but as I don’t want to overly complicate the code, I have kept the signup and login modules separate from each other. I’m sure you can easily implement this if you want to.
This file uses the CSS class fieldname
to arrange the form fields, aligning
them neatly under each other in columns. When loaded into a browser (and
in conjunction with checkuser.php,
shown later) this program will look like Figure 21-2, where you can see that the Ajax call has
identified that the username Robin is available. If
you would like the password field to show only asterisks, change its
type from text
to password
.
<?php // signup.php include_once 'header.php'; echo <<<_END <script> function checkUser(user) { if (user.value == '') { O('info').innerHTML = '' return } params = "user=" + user.value request = new ajaxRequest() request.open("POST", "checkuser.php", true) request.setRequestHeader("Content-type", "application/x-www-form-urlencoded") request.setRequestHeader("Content-length", params.length) request.setRequestHeader("Connection", "close") request.onreadystatechange = function() { if (this.readyState == 4) if (this.status == 200) if (this.responseText != null) O('info').innerHTML = this.responseText } request.send(params) } function ajaxRequest() { try { var request = new XMLHttpRequest() } catch(e1) { try { request = new ActiveXObject("Msxml2.XMLHTTP") } catch(e2) { try { request = new ActiveXObject("Microsoft.XMLHTTP") } catch(e3) { request = false } } } return request } </script> <div class='main'><h3>Please enter your details to sign up</h3> _END; $error = $user = $pass = ""; if (isset($_SESSION['user'])) destroySession(); if (isset($_POST['user'])) { $user = sanitizeString($_POST['user']); $pass = sanitizeString($_POST['pass']); if ($user == "" || $pass == "") $error = "Not all fields were entered<br /><br />"; else { if (mysql_num_rows(queryMysql("SELECT * FROM members WHERE user='$user'"))) $error = "That username already exists<br /><br />"; else { queryMysql("INSERT INTO members VALUES('$user', '$pass')"); die("<h4>Account created</h4>Please Log in.<br /><br />"); } } } echo <<<_END <form method='post' action='signup.php'>$error <span class='fieldname'>Username</span> <input type='text' maxlength='16' name='user' value='$user' onBlur='checkUser(this)'/><span id='info'></span><br /> <span class='fieldname'>Password</span> <input type='text' maxlength='16' name='pass' value='$pass' /><br /> _END; ?> <span class='fieldname'> </span> <input type='submit' value='Sign up' /> </form></div><br /></body></html>
On a production server, I wouldn’t recommend storing user passwords in the clear as I’ve done here (for reasons of space and simplicity). Instead, you should salt them and store them as MD5 or other one-way hash strings. See Chapter 12 for more details on how to do this.