vBulletin 4 and PHP 7, making it work.

Note: vBulletin has now released versions that support PHP 7+, I recommend doing a vBulletin upgrade instead of following this guide. If you do not want to upgrade your forum then you can still use this guide.

PHP 7 has been officially released on the 3rd of December.
It introduces a lot of new features, deprecates a bunch of functions and most importantly, its performance received a huge boost.

I personally used https://webtatic.com/packages/php70/ to upgrade my PHP from 5.4.45 to 7 on CentOS 6.7.
Make sure that you install PHP OPCache as well, it gives you a huge performance boost.

Now vBulletin 4 (<= 4.2.3 at the time of writing this post) does not support PHP 7 out of the box. A couple of changes have to be made in order to make it work smoothly with PHP 7.
There are 3 things we have to fix:
– Methods with the same name as their class may not be constructors.
– Function name must be a string.
– Redefinition of arguments are not allowed.

Step 1: configuration file
First be sure you have a backup of your forum files, this is very important in case the changes do not end up working for you.
Now open the /includes/config.php file and make sure that your datastore class is set to vB_Datastore_Filecache, APC/xCache/Memcached will not work since they do not support PHP 7 (yet) and it’s not necessary to use either of those anyway since OPCache does the job.

Step 2: fixing “function name must be a string”
First we edit /includes/class_bbcode.php. Look for the following:

$pending_text = $this->$tag_info['callback']($open['data'], $open['option']);

and change it to:

$function = $tag_info['callback'];
$pending_text = $this->$function($open['data'], $open['option']);

This will fix the “function name must be a string” error. It seems that PHP doesn’t like it when the value of a key in an array is directly being used as a function name. My fix first assigns it to a variable and then uses it as the function name.

Step 3: fixing /includes/class_datastore.php
Open the file /includes/class_datastore.php and find each of the following:

function vB_Datastore_Memcached(&$registry, &$dbobject)
function vB_Datastore_Filecache(&$registry, &$dbobject)

change them both to:

function __construct(&$registry, &$dbobject)

Now also find the following:

parent::vB_Datastore($registry, $dbobject);

and replace all occurrences to:

parent::__construct($registry, $dbobject);

Step 4: fixing /includes/class_hook.php
Open the file /includes/class_hook.php and find the following:

	function vBulletinHook()
	{
	}

and change it to:

	function __construct()
	{
	}

Step 5: fixing /includes/class_core.php
Open the file /includes/class_core.php and find each of the following:

function vB_Database(&$registry)
function vB_Datastore(&$registry, &$dbobject)
function vB_Input_Cleaner(&$registry)
function vB_Registry()
function vB_Session(&$registry, $sessionhash = '', $userid = 0, $password = '', $styleid = 0, $languageid = 0)

and change all of the function names to __construct:

function __construct(&$registry)
function __construct(&$registry, &$dbobject)
function __construct(&$registry)
function __construct()
function __construct(&$registry, $sessionhash = '', $userid = 0, $password = '', $styleid = 0, $languageid = 0)

Step 6: fixing /vb/exception/parser.php
This is probably a mistake by vBulletin, but we have to fix it in order to make it work.
Open the file /vb/exception/parser.php and find the following:

	public function __construct($message, $line = false, $code = false, $file = false, $line = false)
	{
		$message = $message ? $message : 'Parser Error';
		
		if (!empty($line))
		{
			$message .= "::$line";
		}
		
		parent::__construct($message, $code, $file, $line);
	}

and replace it by:

	public function __construct($message, $line = false, $code = false, $file = false, $line2 = false)
	{
		$message = $message ? $message : 'Parser Error';
		
		if(empty($line)){
			$line = $line2;
		}

		if (!empty($line))
		{
			$message .= "::$line";
		}
		
		parent::__construct($message, $code, $file, $line);
	}

And that’s it. Your vBulletin installation should now work correctly with PHP 7.
In case it does not, check the error logs of your web-server/PHP and make sure that none of your plugins or custom scripts are making use of deprecated functions.

Below is a comparison of vBulletin 4 and PHP 5.4, PHP 7 and PHP 7 with OPCache.
As you can see, vBulletin loads almost 2.5(!) times faster.

Before the upgrade (PHP 5.4.45)
Homepage
409.31 – 429.84 – 389.37 – 401.51 – 389.75 – 426.69
~407.75ms average loading time

Forum Category
518.51 – 491.49 – 447.64 – 491.94 – 433.52 – 543.93
~487.84ms average loading time

Thread
326.34 – 399.72 – 387.09 – 383.79 – 370.03 – 375.21
~373.70ms average loading time

—–

After the upgrade (PHP 7 WITHOUT OPCache)
Homepage
289.79 – 291.41 – 289.11 – 253.45 – 285.06 – 259.98
~278.13ms average loading time

Forum Category
281.83 – 333.31 – 293.23 – 276.73 – 268.91 – 281.63
~289.27ms average loading time

Thread
221.73 – 344.83 – 257.84 – 250.72 – 250.04 – 220.07
~257.53ms average loading time

—–

After the upgrade (PHP 7 WITH OPCache)
Homepage
225.63 – 200.26 – 219.48 – 181.72 – 199.93 – 177.55
~200.76ms average loading time

Forum Category
194.95 – 184.47 – 237.45 – 182.62 – 185.93 – 178.06
~193.91ms average loading time

Thread
207.83 – 156.41 – 146.43 – 143.13 – 155.13 – 142.61
~158.59ms average loading time

Comments

  1. Thank you for this guide!

    However, there are many more files in vBulletin 4 that use PHP-4-style constructors. You can automatically fix all of them using PHP-CS-Fixer (https://github.com/FriendsOfPHP/PHP-CS-Fixer) with level “none” and the fixer “php4_constructor”.

  2. thanks for that amazing roundup, finally someone talking about this and having progress=)

  3. It seems to solve an installation error with parser.php but unfortunetely another one pops up at 7%. No error though. Just some XML output saying the Administrator account was installed succesfull and that’s it.

    • If you’re trying to make changes so the installation/upgrade process works with PHP 7, try using the beta version of vBulletin instead. It supports PHP 7+.

  4. In step 5, your title mentions /includes/class_core.php but then the instructions say to open /includes/class_datastore.php. It should also state /includes/class_core.php under the title.

  5. Parse error: syntax error, unexpected ‘*’, expecting end of file in C:\xampp\htdocs\Foro\includes\config.php on line 165

    I have this error (vb4.2.3)

  6. I made the corrections but now I have this error not the one above

    Deprecated: Methods with the same name as their class will not be constructors in a future version of PHP; vB_XML_Parser has a deprecated constructor in C:\xampp\htdocs\Foro\includes\class_xml.php on line 52

    Deprecated: Methods with the same name as their class will not be constructors in a future version of PHP; vB_XML_Builder has a deprecated constructor in C:\xampp\htdocs\Foro\includes\class_xml.php on line 689

  7. Will your guide work for VB 4.1.12?? My VB is heavily modified and I am not planning on doing any further VB upgrades.

    I’m currently on Centos 5 PHP 5.3.29.
    I’d like to upgrade CentOS to at least 6.x and preferably 7.x and push PHP forward as much as possible with causing no more upgrade pain than you outline above. Any advice for how far I can upgrade??

    Thanks!!!

    • Yes, it should work on any vBulletin 4 version. However, there may be some additional errors that need to be fixed.
      Generally if you Google the error you should be able to find a fix for the common errors.

      Otherwise, feel free to send me an email using the contact form.

Leave a Reply

Your email address will not be published / Required fields are marked *