A few weeks back, @Michael_Morris posted a topic where he suggested that creating/destroying objects on each HTTP request was wasteful. I posted a way of getting around that in the thread, I’ve built on that a little and come up with what I think is quite a nice implementation
The basic thought process behind this is that:
- When you connect to the webserver all that does is run a very minimal script, it doesn’t create database connections, construct large object graphs, render HTML or do anything complicated at all
- It connects to the running Application server which already has all that stuff running in memory. This forgoes all that bootstrap code for each request and allows the request to connect to an existing, running application.
Currently this supports:
- Multithreading (A server will get run on each thread)
- Load Balancing (When someone connects they get placed on a specific server instance, the first one available to handle the request)
It’s up on github here:
In its simplest manner you can create an application by implementing the \Aphplication\Aphplication interface and then starting the server:
require_once '../Aphplication/Aphplication.php';
class MyApplication implements \Aphplication\Aphplication {
private $num = 0;
public function accept($appId, $sessionId, $get, $post, $server, $files, $cookie) {
$this->num++;
return $this->num;
}
}
$server = new \Aphplication\Server(new MyApplication());
if (isset($argv[1]) && $argv[1] == 'stop') $server->shutdown();
else $server->start();
The accept
method takes all the superglobals from the current request as arguments as well as a session ID to allow you to identify specific users.
The return value of the accept
method is what is returned to the client (in most cases this will be the HTML). In this case, all the application is doing is acting like a hit counter (remember those?) and tracking the number of times the server has been accessed using the $num variable. You’ll notice it doesn’t need sessions, databases, memcached or any other storage mechanism to achieve this, it’s just all stored in the running PHP server process.
The server can only be run from command line presently as apache doesn’t allow forking processes! The client, however can be run from a normal web server.
> php example1-persistence.php
Once the server is running, you can connect to it using the client script (From command line use the Client-CLI.php rather than Client.php) by running the client script from the same directory the server was started from:
> php ../Aphplication/Client-CLI.php
In this example, all the application is doing is incrementing the number, but the output is useful:
> php ../Aphplication/Client-CLI.php
1
> php ../Aphplication/Client-CLI.php
2
> php ../Aphplication/Client-CLI.php
3
> php ../Aphplication/Client-CLI.php
4
To stop the server, re-run the server script with the stop
argument:
php example1-persistence.php stop
If you make any changes to the code in the server, you must restart it before the changes show.
Obviously this a proof-of-concept so it’s not production ready, use at your own risk, yada yada!
This was quite a fun exercise but the result is quite cool. In a non-trivial application with database connections, template systems, lots of includes, etc I get a 500% performance increase (obviously without any kind of caching layer).