On Joomla’s Core Hacks

Note: In this post, by “core file” we mean a Joomla file that cannot be overridden at the template level.

We have a somehow hawkish attitude when it comes to optimizing Joomla: we are not afraid of using core modifications (e.g. core hacks) to optimize/secure Joomla websites. For that, we are often criticized by some members of the Joomla community; these people state that it is always better to use overrides instead of core hacks. We don’t disagree, but like in everything else in life, a balance must be struck between what’s ideal and what’s realistic.

Ideally, we should have the ability to override any file on a Joomla website. Realistically, this is practically impossible, and we have an experiment that backs our statement. A few months ago, we were assigned to a project that consisted of optimizing a large Joomla website. We decided to use an extension called Joomla Override (the extension is actually referred to in Joomla’s official documentation) in order to do the optimization. At the end of the day, we discovered that many important files cannot be overridden with that extension (and any extension, for that matter), mainly because these files are loaded before anything else. By the end of the optimization mess work, we ended up with 4 overridden files, and 6 Joomla files with core modifications. Naturally, we decided that the whole thing was counterproductive, and we switched the file overrides to core modifications. A substantial part of this (failed) experiment was documented here.

But what if itoctopus developers don’t know how to properly override core files?

If you are an avid read of our blog, then you should have an idea of our level of expertise in Joomla. We know what we are talking about: there are many files that cannot be overridden on a Joomla website, and a quick example is session related files, as initial session activities must take place before loading any Joomla extension.

The only way to have the ability to override all Joomla files is for Joomla to implement the mechanism to do so. For example, Joomla can have a folder called userdefined in its main directory, and, before loading any Joomla file, it will check if a file with the same path exists under the userdefined directory. For example, if someone wants to override the includes/framework.php file, then he should create a file called framework.php under userdefined/includes. Adding such ability to Joomla is not an easy task, as all the requires / includes functions must be replaced with jrequires / jincludes functions. The latter functions will be wrappers (that must be defined in the index.php file) and will first attempt to require/include a file from the userdefined folder, and, if the file doesn’t exist, then they must require it/include it from its normal location.

Here is an example implementation of the jrequire function:

function jrequire($path, $once = false){
	if (file_exists('userdefined/'.$path)){
		if ($once)
			require_once('userdefined/'.$path);
		else
			require('userdefined/'.$path);
	}
	else{
		if ($once)
			require_once($path);
		else
			require($path);
	}
}

The above function could be written more elegantly, but you get the idea. This will allow Joomla developers to override any Joomla (PHP) file, with the exception of the index.php file in a very clean way that will sustain the test of time.

Unfortunately, at the moment jrequire and jinclude do not exist, so we have to work with what we have, and what we have (we know, that’s the third what we have in the same sentence) is core hacks, which are extremely necessary on large Joomla websites (mainly for performance reasons). Clearly, core hacks are not ideal because they get wiped out with future updates, but, if you document the changed files, then you should be OK.

Now, if you, our dear reader, would like to modify a core file that cannot be modified at the template level and you need help, then please contact us. We would love to do that for you, you will love our work, and you will love our prices!

3 Responses to “On Joomla’s Core Hacks”
  1. Comment by Michael — February 15, 2017 @ 10:43 am

    It’s a bad idea to allow ANY PHP class to be overloaded. Joomla should be focusing on a service based architecture that makes it cleaner/easier to subclass core classes and use those subclasses versus having to resort to changes like this or registering custom classes to the autoloader before the system has a chance to load the real one. It is very hard to build if you can’t rely on classes being in a known state with a known set of behaviors.

    Not to mention, extensions relying on this practice of overloading core classes can cause unexpected issues on upgrades. redCOMPONENT had an override for JFormField that broke with the rendering changes for forms in 3.5 to allow fields to use layouts. RegularLabs overrides JModuleHelper to make Advanced Module Manager work correctly. It’s great that these extensions can add their functionality through overrides like this, but at the end of the day, we should be making the API more flexible so these core class overrides aren’t necessary.

    Ya, I’m one of those people who hates the fact that you’re so quick to promote core hacks, but my feeling on the matter is that the hacking or custom defined classes path is really the wrong approach as a core solution. A service driven architecture is a cleaner solution and would improve the overall API by loosening some of the hardcoded constructs and forces the project to move away from bad practices like procedural static method calls (like the entire JModuleHelper class) into an object oriented approach where a dependency can be replaced with either a subclass or a new class meeting an interface’s requirements (if core ever starts using proper class interfaces).

  2. Comment by Fadi — February 15, 2017 @ 11:02 am

    Hi Michael,

    Our problem with Joomla’s core is its performance issues on large websites. The issues are caused by heavy queries in many core files, including session files (there is an activity on the session table for each page load), tag related files (the most unoptimized Joomla feature, and there will be soon a post on this website about it), and content related files.

    Essentially, Joomla’s core does not take into consideration that the CMS may be used on large websites, and so the queries are not tested on large datasets, and subqueries are often used (e.g. SELECT * FROM ... WHERE ... IN (SELECT ...)). Note that subqueries are our biggest problem with Joomla’s core.

    We currently manage very high traffic websites – and it would have been impossible for the clients to use Joomla if we didn’t do the necessary core optimizations.

    I definitely see your point, and I agree with you, and if you can make a large Joomla website (+50K articles) work smoothly without core modifications then please advise how. We weren’t able to do it – hence the core hacks.

  3. Comment by Michael — February 15, 2017 @ 1:43 pm

    I get right now that hacks are needed in many cases for larger scale deployments. I can’t argue that, I’ve had my own fights with it and the data modeling is constantly in the back of my mind as we plan out the next phases of deployment for the Joomla Downloads site. I just don’t think the path forward for Joomla to fix this or make it easier for service providers to fix it is to support class overloading is all. Shifting the API to a service based approach where you can subclass the models in com_content to adjust the queries (and no this should not be done through plugin events; query manipulation that’s wide open like this is a massively bad idea… even Doctrine’s ORM only has hook points for updating an entity object on create/update, nothing for general SELECT queries and nothing for manipulating generated SQL) fixes your problem of the default structure not being suitable for the types of deployments you make and my issue of providers hacking the core system because there is no simple way to do this right now.

    With any luck, 4.0 will at least loosen the requirement for the session table’s read/write activity – https://github.com/joomla/joomla-cms/pull/13322

Leave a comment