Integrating FirePHP for Ajax Development
April 3, 2009

UPDATE: Oct 20, 2010

Since writing this article I have been working on FirePHP 1.0 and a new client tool to achieve the kinds of things I describe below much more easily. The new tool is called FirePHP Companion and aimed at streamlining the PHP development workflow. There is still a lot of work left to do, but you can already take a look at how the demo provided here can be implemented easily with FirePHP Companion.


As mentioned in a previous post I wrote a column for php|architect about how FirePHP can be used for Ajax development. I am re-publishing the complete article here. Enjoy!

FirePHP for Ajax Development

There are many integrated development environments and tools available to aid in building Web 2.0 AJAX applications with PHP, but nothing comes close to the ease of use and tight Firebug integration that FirePHP provides.
PHP: 5.2+
Other software: Firefox, Firebug
Useful/Related links:

My purpose in this column is to introduce you to FirePHP, the problem it solves, and how it is intended to work within your application for maximum benefit. I will present some useful high-level knowledge to make it easier for you to integrate FirePHP into your application.

This is not a step-by-step tutorial. I have made a complete demo available for download, along with some useful libraries illustrating all the concepts covered here. I want to emphasize that the demo is only one possible implementation. There are many other possibilities.

The Problem

Building AJAX applications brings some new challenges to PHP developers. Apart from the fact that you need to learn JavaScript, which is probably a good idea anyway, you need to figure out a way to debug your AJAX requests. There are primarily two ways to do that.

The more involved option is to use an IDE with an integrated debugger. While this may be the most powerful approach, it typically is also the most complex, expensive, time-consuming and cumbersome, especially when it comes to triggering the debugger for a specific request.

The second option is to simply print out debug information using var_dump() or print_r(). This approach requires you to examine the response of the request in Firebug, or to run it in its own browser tab. It also breaks your JavaScript AJAX code, because the response is no longer a valid XML or JSON structure.

The ideal solution would be something that is easy to set up and use; something that will allow you to view any PHP variable without breaking the response content, so that your JavaScript code can continue to execute as intended. This is precisely what FirePHP is designed to do — this, and more.

The FirePHP Solution

FirePHP solves the problem of AJAX debugging by sending debug information along with the response. To avoid breaking the response content, the debug information is placed into special HTTP response headers. This works for all types of requests, not just AJAX requests, which means you can even debug requests for images that are dynamically generated by a PHP script. You can use FirePHP in your development environment, or use it to track down bugs that only appear on your production site.

The FirePHP system requires two components to work. The first of these comes in the form of a Firefox Extension that extends Firebug. It reads the special response headers and presents the debug data in an intelligent way within Firebug. The second component is a PHP server library that provides the necessary functionality to encode PHP variables and sends them in the response headers.

Detailed information regarding how to install the FirePHP components and how to get started with their basic functionality is available on the FirePHP website, to which you will be directed when you install the FirePHP Firefox extension.

Persistent and Controllable

There is significant benefit in leaving debugging code in your application and being able to easily enable the desired debug output as and when required. This is primarily useful when working with object oriented code, where common components are re-used in different areas of the application and may become part of several iterations of debugging when tied into different end-user functionality. One such component, for example, would be a caching object.

When debugging such an object, you would typically want to be able to view information about the cache such as filenames, whether the data was created or fetched from the cache, and when the cache entry will expire. Going one step further, during debugging, you would want to be able to control the cache lifetime, force cache expiry, and conduct some analysis on the amount of resources used and time taken to create the data that is being cached.

Having debugging code in your application and being able to trigger it in a secure way may also come in extremely handy when something that worked fine during development is not working quite as it should in your production environment. In such a case, you’ll want to be able to easily view specific information about your backend without making it available to all.

Design Philosophy

FirePHP is designed to be non-intrusive so that you can decide how and where to use it within your application. It essentially provides a mechanism to send logging events to the Firebug Console without interfering with your application. There is no built-in security to safeguard the data you send, which means that you are in charge of security and in charge of deciding what to send, when to send it and to whom.

All data is sent in clear text in the response headers, unless the request was made via HTTPS in which case the entire response —including the headers— will be encrypted.

Although the chosen design may put the burden of security on you, it gives you complete freedom over how to use FirePHP within your application. The remainder of this discussion will focus on the best practices of how to integrate FirePHP into your application to implement some powerful debugging functionality while ensuring security and maintaining flexibility. A basic understanding of the FirePHP API will help, but is not essential.

Enabling FirePHP

As soon as you include the FirePHP server library in your application, FirePHP is enabled and you can log to Firebug:

FB::log('This is a log message');

This makes it very easy to get started, and provides a great alternative to using var_dump() or print_r() during development or ad-hock debugging. When you use FirePHP in this way, you would typically only log variables during development and remove all your logging statements before uploading your code to a production server.

If there are logging statements you want to keep in your code, to save you time in future, you can manually disable FirePHP with

FB::setEnabled(false);

before uploading your code. This will stop your logging messages from being sent. However, if you rely on this method, apart from the fact that it is cumbersome, there will likely come a time when you forget to disable it before uploading your code. In that case anyone who has FirePHP installed will be able to see your logging messages, which may or may not be a problem depending on the data you are logging. You probably don’t want that to happen.

A better approach would be to use a configuration setting to determine whether FirePHP should be enabled. Chances are your application already uses a configuration file you can use. Adhering to good security principles, you will want to disable FirePHP by default and only enable it if a setting is found that specifically overrides the default. The code could look something like this:

$settings = @parse_ini_file('settings.ini');
 
if ($settings['FirePHP'] == 'Enabled') {
  FB::setEnabled(true);
} else {
  FB::setEnabled(false);
}

When this is set up, all you will need to do is use different values in your configuration files in your development and production environments, and you will never need to worry about FirePHP being enabled by accident again.

If you want to enable FirePHP for specific users no matter which environment the application is running in, you can tie the above code into your user privilege or session system.

Selective Logging

To realize selective logging by allowing a user —or more specifically, a developer— to turn on and off specific groups of logging messages, requires a bit more work. Such a system typically consists of an administration interface allowing the developer to tweak logging options, and a wrapper object for FirePHP that is used in the application to intercept logging messages and only send them if requested.

The options defined in the administration interface will need to be accessible to the wrapper in the application. This can be done on the back-end via a shared session or cached file, or on the front-end via cookies. The approach you choose depends on how your application is structured and whether the administration system runs on the same domain as your application. The cookie approach is probably the easiest to set up, allowing the administration interface to be coded entirely in JavaScript.

Let’s say you implement the administration interface for the debugging options in JavaScript. The user interface could be tailored to look consistent with the rest of your administration system, and could be used to set, say, a cookie named Debug to a value of DisableCache when that option is selected.

Your wrapper on the application side would look something like this:

class Debug
{
  public static function getOption($name)
  {
    $options = @explode('|', $_COOKIE['Debug']);
    return(is_array($options) &&
    in_array($name, $options)) ? true : false;
  }
}

You can then ask the wrapper whether a specific option is enabled, and act accordingly:

if (Debug::getOption('DisableCache')) {
  // code to disable cache
  FB::info('Cache has been disabled!');
} else {
  // default code
}

Make sure that the debugging options always override default behaviour, and that the application will continue to function if no debug cookie or option is defined. You should always return FALSE for the debug options if the user is not authorized to use them.

I encourage you to look at the source code of the demo mentioned earlier, which illustrates the cookie and JavaScript-based administration interface approach. Rip out the code you like and make it your own.

An Eye to the Future

I have been toying around with development and debugging systems for a long time. FirePHP is my first public, stable and practical implementation to a problem area I find fascinating.

I have never been a real fan of interactive debuggers, primarily because they don’t support my write a little code, run it, write some more, re-run it development approach, which seems to be quite common when building Web applications with scripting languages. As FirePHP is coming into its own and I can observe how others use it, I see tremendous opportunity in evolving this type of development approach further. I’m not talking here about just the debugging aspect, but rather a system that can easily be tied into any application to provide the developer with a powerful user interface that can visualize the internals of an application. One that allows the developer to configure components for different environments and stages of the development cycle.

It would be much easier for a new developer to learn their way around a codebase if they could see the order of execution visually on one page without having to step through the code. It would be trivial to provide mock data to application objects where certain services or classes are not yet complete by defining the data in your browser.

I encourage you to look both at FirePHP and at the big picture it points to. FirePHP represents a humble beginning to a problem area that is desperate for attention, and provides an enormous opportunity to make all our lives easier.

UPDATE: Oct 20, 2010

Since writing this article I have been working on FirePHP 1.0 and a new client tool to achieve what I described above. There is still a lot of work left to do, but you can already take a look at how the demo provided here can be implemented much more easily with FirePHP Companion.

19 Comments
April 10, 2009

Hey Christoph, thanks for writing FirePHP its become an essential tool for Ajax development. I’ve written a PHP4 compatible library that is part of the DebugKit for CakePHP. You can find it at http://thechaw.com/debug_kit/source/vendors/fire_cake.php Thanks again for the great work :)

May 23, 2009

FirePHP is also embedded in Zend Framework > 1.6 so you can just use the class Zend_Log_Writer_Firebug to output data to the Firebug console.

- ck

June 13, 2009

thanks

this will help to edit sites very easy :)

keep going…

June 20, 2009

Thank you! You just developed a great product out of a great idea.

This is much appreciated in the web dev team I work.

August 3, 2009

AT LAST :D Thanks a million. This little tool drove away one of my worst nightmares… to quote you…

The second option is to simply print out debug information using var_dump() or print_r(). This approach requires you to examine the response of the request in Firebug, or to run it in its own browser tab. It also breaks your JavaScript AJAX code, because the response is no longer a valid XML or JSON structure.

Comments are closed.