Archive for the ‘PHP’ Category.

Doing Things the Hard Way

Every now and then I discover something that makes me feel like I’ve been doing things the hard way. The feeling is an interesting combination of excitement and embarrassment. I experienced this today while browsing PHP documentation. I discovered two function that will make my life a lot easier in the future: debug_backtrace and debug_print_backtrace. As someone who has written his fair share of Java, I’m very accustomed to stack traces. The fact I’ve made it as far as I have with PHP without them leaves me feeling amazed. The fact that I’ve had access to them all along leaves me feeling ashamed.

I guess you learn something new everyday.

Apparatus 0.4

A new version of Apparatus is available. Previously I wrote about several new features that would be included in this version, however rather than further postpone a release, I’ve decided to hold off on those features until the next version. Version 0.4 incorporates a new theme, the latest version of tab override (which should resolve any browser compatibility issues), and various improvements and modifications.

PHP Overloading

The lack of function overloading is one of my biggest complaints about PHP. If you’re not familiar with overloading, its a feature of some languages that allows you to defined multiple methods (or functions) with the same name, but taking different paramenters. In Java, for instance, methods are not identified solely by their name. Instead, functions are distinguished by their signature: their name, return type, number of parameters and their types. This allows you to do things like define multiple constructors for a class.

PHP not being a typed language, using parameter types and return types as part of a method or function signature is out of the question. You could, however, use the number of parameters. In my opinion, you should be able to do something like this:

class Foo {

	function __construct()
	{
		//constructor that takes no parameters
	}

	function __construct($param1)
	{
		//constructor that takes 1 parameter
	}

	function __construct($param1, $param2)
	{
		//constructor that takes 2 parameters
	}
}

If you did this, however, you would get an error message reading something like this: Fatal error: Cannot redeclare Foo::__construct. As unfortunate as this is, it is possible to devise a simple workaround, due to the fact that a method can be written to take an arbitrary number of parameters. The solution is to create a method that can take any number of parameters and have that method delegate to ‘helper’ methods:

class Foo {

	public function __construct()
	{
		$args = func_get_args(); //any function that calls this method can take an arbitrary number of parameters
		switch(func_num_args())
		{
			//delegate to helper methods
		case 0:
			$this->construct0();
		break;
		case 1:
			$this->construct1($args[0]);
		break;
		case 2:
			$this->construct2($args[0], $args[1]);
		break;
		default:
			trigger_error('Incorrect number of arguments for Foo::__construct', E_USER_WARNING);
		}
	}

	private function construct0()
	{
		//constructor that takes no parameters
	}

	private function construct1($param1)
	{
		//constructor that takes 1 parameter
	}

	private function construct2($param1, $param2)
	{
		//constructor that takes 2 parameters
	}

}

It might not be pretty, but using this method you will be able to call the constructor of Foo as if it were actually overloaded:

$x = new Foo();
$y = new Foo(1);
$z = new Foo(1, 2);

An alternative to this would be to use default parameters to determine what action to perform, but this method gets increasingly clumsy as the number of arguments grows.

Apparatus Update Preview

I’ve been making some progress on the next version of Apparatus. Along with some bug fixes there are a few new features. One new thing is the option to attach a database to allow for more advanced functionality. For now this includes something I’m calling examples generation, which allows you to store your code and output and allow others to view it. This is done without giving them access to the Apparatus interface. Apparatus can still operate in lite mode (without a database), but some features will not be available.

Also in the works is a new template which will serve as the default Apparatus template (the 0.3 template can still be selected). Here is a small preview:

Apparatus Template

Apparatus 0.4.0 login screen viewed in Opera 10.5

Hopefully the new version should be ready for release by the end of the month. For now version 0.3 is available. If you haven’t yet, give it a try; it is not too late for any suggestions you may have to make it into version 0.4.

PHP Confirmation Emails

If you are implementing your own user management system you may want to ensure that emails associated with users’ accounts are valid. The most straightforward way of doing this is to send an email to this account and verify that the user received it. Obviously we don’t want to do this manually so the solution is to write a script that automates the process.

High Level Concept
What we will need to do is:

  1. Generate a confirmation code for our users are registration time
  2. Store that code and track which users are not yet confirmed
  3. Send an email containing the confirmation code to the user
  4. Facilitate the user in using the code to activate their account

Confirmation Codes

The easiest way to generate a confirmation code is to take a piece of information about the user and hash it. What we don’t want to do however, is reveal how this hash is generated or make it easy for a user to generate this hash on their own. I find that the easiest way to approach this problem is to use the current timestamp in the hash; unless the user knew the time that their hash was generated down to the second they could not generated one on their own. Here is the code:

$hash = md5( $username . time() );

Notice that I assume you already have the username.

Storing Your Confirmation Code

In order to confirm a user, both the user and the server need to know the code. This means you’ll have to store the code once it is generated. You’ll also need to track which users are confirmed and which aren’t. Fortunately we can do both these things at once. You’ll need to either add another column to your `users` table or use another method to associate the code with the user. I’ll assume that you have a column called `status` in your `users` table.

Once you’ve generated your confirmation code store it in the database. We’ll worry about determining which users are confirmed later.

Sending the Email

Now that we have generated our code we will need to send it to the user. The easiest way for a user to confirm their account is to just click a link that has the code encoded into the url:

//the link
$link = "http://yoursite.com/confirm.php?user=$username&code=$hash";

Notice that I use the page confirm.php. We will write the script in the next step, you may call it something different if you like. Also notice that I include the username and hash in the url.

Now we need to create the rest of the email and send it. One thing you’ll want to do is keep things simple. Some email clients filter out any html so it is best to use plain text when possible.

$link = 'http://yoursite.com/confirm.php?code=' . $hash;
ob_start();
?>
Confirmation Required:
Please copy and paste the following link into your browser to confirm your account
<?php echo $link; ?>
If you did not register an account just ignore this message
<?php
$message = ob_get_clean();
$headers = 'From: you@yoursite.com' . "\r\n" .
    'Reply-To: you@yoursite.com' . "\r\n" .
    'X-Mailer: PHP/' . phpversion();

mail($userEmail, 'Confirmation Required', $message, $headers);

I used an output buffer to write the message, if you are not familiar with this approach you may want the read the output buffering section Here. Notice the $headers variable. It is important that you include the From header whenever sending email. Even though the headers parameter is optional, the from header is not. I highly recommend that you take a close look at the mail documentation.

Confirming Users

Now that the user has their confirmation url we need to write the confirm.php script I mentioned earlier. I will leave comments whenever a database transaction is needed:

$userCode = $_GET['code'];
$user = $_GET['username'];

/* get the code stored in the database
if the user does not exist, or has already been
confirmed display an error message */
$serverCode;

if($serverCode == $userCode)
{
	//change the value of the status field in the database to 'confirmed' or something else if you prefer
}
else
{
	//Invalid code. Display an error message
}

In short, all we need to do is compare the user’s code with the one stored in the database. If the match change the value of the user’s status field in the database to some value that will indicated the user is confirmed. Anytime you need to check if a user is confirmed just use that field.

Additional Concerns

There are some additional concerns that I did not address that you may want to.

A user may need to have their confirmation email resent. This is just a matter of pulling the confirmation code out of the database and sending it again.

Some users or bots may register accounts that they never confirm. You may want to setup a crontab or some other means of periodically clearing out these accounts (ie if an account hasn’t been confirmed after a week, delete it).

Protect yourself from SQL Injections whenever sending user data to the database!!!

Apparatus (also Happy New Year!)

For a while now I’ve been working on a web-based PHP interpreter; an interface I can use to quickly test or develop code from my browser. Ultimately this resulted in Apparatus, an in-browser PHP read-evaulate-print loop. Give it a try: http://tinsology.net/scripts/apparatus/.

Note that this is currently a beta version. Any help with identifying bugs will be greatly appreciated.

P.S. Happy New Year!

PHP Iterators

If you’ve spent any significant amount of time coding in PHP you’re most likely familiar with PHP’s foreach loop syntax. In simple terms, a foreach loop is an easy way to iterate over the elements of an array. Chances are if you’re reading this you already know that. What you may not know, however, is that it is possible to iterate objects with a foreach loop. Assuming you have some collection class (an object that stores some number of elements in an organized manner) you can iterate over its elements just like you can the elements of an array.

$myCollection = new Collection(); //arbitrary collection class

foreach($myCollection as $element)
{
	//do something with $element
}

In order to do this however, you must design your class in such a way as to let PHP know that it supports iteration. As is the case with many other languages, you do this by implementing an interface. An interface is basically a class containing only abstract methods (constants are allowed as well). A class implementing a certain interface must provide the definitions for those abstract methods. The interface we need in this case is called Iterator and has 5 methods that must be implemented:

class MyIterator implements Iterator
{
	//Returns the current element
	function current()
	{

	}

	//Returns the current key (position in the iterator)
	function key()
	{

	}

	//Moves to the next element (returns void)
	function next()
	{

	}

	//Resets the iterator
	function rewind()
	{

	}

	/*Returns true of the current position in the
	   iterator exists. False otherwise */
	function valid()
	{

	}
}

From these methods you can derive that the underlying implementation of a PHP foreach loop is something like this:

$i = new MyIterator();

//make sure the iterator is in the starting position
$i->rewind();
while($i->valid())
{
	//get the current element and key
	$value = $i->current();
	$key = $i->key();

	//iterator to the next element
	$i->next();
}

//equivalent foreach loop
foreach($i as $key => $value)
{

}

Now that we know what the methods do it is time to implement them. The class we’ll implement will be a stripped down version of a linked list that supports only an add method (plus the iterator methods):

class LinkedList implements Iterator
{
	private $head;
	private $last;
	private $count;
	private $curr; //iterator counter
	private $currNode; //iterator position

	function __construct()
	{
		$this->head = null;
		$this->last = null;
		$this->count = 0;
		$this->curr = 0;
		$this->currNode = $this->head;
	}

	function add($v)
	{
		$newNode = new Node();
		$newNode->value = $v;

		if($this->head == null)
		{
			$this->head = $newNode;
			$this->last = $this->head;
		}
		else
		{
			$this->last->next = $newNode;
			$this->last = $this->last->next;
		}
		$this->count++;
	}

	function current()
	{
		echo "LinkedList::current \n";
		return $this->currNode->value;
	}

	function key()
	{
		echo "LinkedList::key \n";
		return $this->curr;
	}

	function next()
	{
		echo "LinkedList::next \n";
		$this->currNode = $this->currNode->next;
		$this->curr++;
	}

	function rewind()
	{
		echo "LinkedList::rewind \n";
		$this->currNode = $this->head;
	}

	function valid()
	{
		echo "LinkedList::valid \n";
		if($this->curr >= $this->count)
			return false;

		return true;
	}
}

class Node
{
	public $value;
	public $next;

	function __construct()
	{
		$this->value = null;
		$this->next = null;
	}
}

Notice that I’ve added an echo to each iterator method in the LinkedList class; I’ll explain why later. In case you’re unaware, a linked list is just a series of ‘nodes’. Each node contains a value and a reference to the next node in the list. This pseudo code demonstrates how to traverse a linked list, outputting the values as we go:

Node current := head;

while current != null
	print current->value
	current := current->next
endwhile

Since, however, our linked list class implements Iterator we can traverse it using a foreach loop:

$list = new LinkedList();
$list->add('a');
$list->add('b');
$list->add('c');

foreach($list as $key => $value)
{
	echo $key . ' : ' . $value . "\n";
}

Here is the output for the above code:

LinkedList::rewind
LinkedList::valid
LinkedList::current
LinkedList::key
0 : a
LinkedList::next
LinkedList::valid
LinkedList::current
LinkedList::key
1 : b
LinkedList::next
LinkedList::valid
LinkedList::current
LinkedList::key
2 : c
LinkedList::next
LinkedList::valid

The above shows the position and value of each element in our list, as well as the order each iterator method is called.

P.S.

This is the first part in a three part series. The next part will be published soon.

A Supplement

I’ve just added a section about session management to Creating a Secure Login System the Right Way.

Check it out

Easy PHP Search with Opera

If you use Opera you’re probably aware that it supports shortcuts in the address bar that allow you to run a search on various search engines and websites. For example, if I type g tinsology in the address bar, you’ll get the Google search results for the keyword tinsology. You can do similar things with yahoo, amazon, ask and other sites that come preconfigured in Opera.

Personally, I find myself frequently using this shortcut to Google PHP documentation. For example if I’m looking up documentation for the implode function, I’ll type g PHP implode. More often than not the first result is what I’m looking for and it is just a matter of waiting for the search results to load, clicking the first result, and waiting for the php.net page to load.

Ideally, however, I would want to be able to go directly from typing my search in the address bar to the php.net results page. It just so happens that Opera allows you to do this by adding a custom search engine. What we want to do is to be able to type p [my search] in the address bar. To begin we need to open the Search Preferences pane:

  • In Opera click Tools -> Preferences... or press Ctrl+F12
  • In the resulting window select the Search tab.
  • Click the Add... button.

In the add window there are three fields we are interested in: Name, Keyword, and Address (if you don’t see the address field click the details button). Name is just the name of this search shortcut; I named it PHP, but it doesn’t really matter what you name it. Keyword is the keyword you type in the address bar before your search query. For a Google search it is g. I chose p, but once again you can choose anything you’d like. Also, the keyword doesn’t have to be a single letter, for instance you could use php. The address field tells Opera what to do with your search query. Without explaining too much I’ll just say that the value we want to use is: http://us2.php.net/manual-lookup.php?pattern=%s. The %s token will be replaced by our search query. For instance typing p implode will cause Opera to open http://us2.php.net/manual-lookup.php?pattern=implode

That’s it; leave all of the remaining field blank. You can now use Opera’s address bar to instantly search the PHP documentation. You can use similar methods for running searches on other sites, the hardest part is finding the correct search URL (its even harder if the search query cannot be URL encoded, that’s when the Use Post option comes in handy).

Unlimited PHP Function Parameters

If you’ve ever used PHP’s library functions you’ve most likely noticed that several function such as array() can take an indeterminate number of arguments. Normally when defining a function you specify each argument in the function declaration. Obviously it would be impossible to define an infinite number of arguments in such a way. PHP does, however, allow you to accomplish this through the function func_get_args().

func_get_args() returns an array consisting of all of the arguments passed to a function. Using this method you can bypass the conventional method of defining parameters in the function definition all-together. Here is an example:

function add()
{
	$total = 0;
	$args = func_get_args();

	foreach($args as $arg)
	{
		if(is_numeric($arg))
			$total += $arg;
	}
	return $total;
}

echo add(1, 2, 3); //will return 6

If for whatever reason you need to know the total number of arguments passed to a function, PHP provides the func_num_args() function.

When retrieving arguments in this manner it is important to remember that func_get_args only returns an array of arguments passed by the user. It does not account for default values.