Creating a custom error page for your Joomla site

I've decided that it was time to improve some parts of our site. I had a look at the Redirect component in Joomla and unfortunately people are landing way too often on 404 not found page. And often there is no redirect that I can make. The resource no longer exist on our site and the user has to see a 404 page. Sadly for the past few years he was presented with this:

As you know this is the default Joomla 404 page - it gets the message across, but it is anything else than pretty and relaxing. So, today I decided that it was time to improve this! Since neither Yves or I are good designers I decided to find a good 404 template, change it a little and add it to our template. After some searching I found this: http://themeforest.net/item/wordsearch-responsive-404-error-pack/6531230 - the template could be used with 400 or 500 errors, so I decided that it was a good fit for compojoom.com.

After downloading the template I unzipped it, removed all .DS_Store files (as they were sadly in the package) and uploaded the folders into templates/cj2013/errors/ (cj2013 - is the name of the template that we use here on compojoom.com). Now how do we tell Joomla that it has to use this template whenever there is a 404 error, or 500 error? Joomla is looking for an error.php file in your template directory. If it doesn't find an error.php file it takes the error.php file from the system template. So, the only thing we have to do here is to create an error.php file in our template directory!

<?php
// No direct access.
defined('_JEXEC') or die;

$code = 0;

if(isset($this->error)) {
$code = $this->error->getCode();
}

$errorFile = __DIR__ . '/errors/' . $code . '/index.php';

if(JFile::exists($errorFile)) {
// load our custom template
require_once $errorFile;
} else {
// fallback to the default joomla error template if we don't have a template for this error
require_once JPATH_ROOT . '/templates/system/error.php';
}

defined('_JEXEC') or die; will make sure that the file cannot be executed directly.

After that we set the code to 0 and if we have $this->error instance we will use it to update the code number. The wordsearch 404 template that we use has an index.php file for each 400, 404, 500 error. The index.php file is located in the respective folder 400, 404, 500. The $errorFile variable just maps to this folder structure. After that we just check if the $errorFile for this particular number exists. If it does, then we load it. If it doesn't then we fall back to the default Joomla error message. And there we go! Now we have our own beautiful error page!

Want to see the result live? Then click here.

Caveats!

Now if you've got the same 404 template as the one we use and you've followed this tutorial, you'll see that the 404 page doesn't have any styling. That's because the css & js files cannot be found. You'll have to modify each error index.php file and change the code that includes the css & js to:

	<link rel="stylesheet" type="text/css" href="/templates/<?php echo $this->template ?>/errors/css/style.css" />
<link rel="stylesheet" href="/templates/<?php echo $this->template ?>/errors/font-awesome/css/font-awesome.min.css">
<script type="text/javascript" src="/templates/<?php echo $this->template ?>/errors/js/jquery.js"></script>
<script type="text/javascript" src="/templates/<?php echo $this->template ?>/errors/js/wordsearch-resize.js"></script>

Now when you reload the page the proper styling should be loaded.

Another issue that we have with this solution. Your custom text and menus are hardcoded in each index.php error file. This would mean that you'll have to edit all 5 index.php files whenever you need to make a change to either the text or menu. Why use Joomla, when you are going to edit text in files all the time??? What we could do here is to use a custom html module and publish each module in a "dummy" error position. For example your 404 message would be published in error_404, a 500 error would be published in error_500 position. Then we could modify our code to check if we have a module for this particular error message:

$module = JModuleHelper::getModules('error_'.$code);
if(isset($module[0])) {
    $module = $module[0];
}

After that just render the module in the appropriate position:

<h1><?php echo $module->title; ?></h1>
        <?php echo JModuleHelper::renderModule($module); ?>

If we don't have a module for that particular error, we could again fall back to the Joomla's default error page.

So, that's it! I hope that you also managed to get a better error page for your users! They deserve it :)