You normally wouldn’t run php-cgi scripts via a command line. After all, they’re a Common Gateway Interface used by webservers (such as Apache) to execute PHP-scripts. However, for debugging purposes, it may be useful to be able to run those php-cgi scripts via your command line instead of calling them directly via your web browser.
The way Apache (or any other webserver) passes a request on to a CGI is by creating environment variables that further describe the request. In those environment variables, you’ll commonly find the URL that is being requested, the path to the script, etc …
If you’re used to running scripts via CLI, you would normally use the ‘php’ command and give the script-name as an argument (such as ‘php mydir/script.php'). The same works for php-cgi as well, but the problem starts when you’re running applications via Zend Framework and rely on the routing-engine to map certain URLs to PHP code. If you just execute php-cgi, it would look like this.
$ php-cgi htdocs/index.php X-Powered-By: PHP/5.3.13 Content-type: text/html <HTML>...
So it gets tricky when you actually want to make a request to ‘http://site.tld/nl/page', since you can’t just simply call the PHP-script as the URL is an important factor. But that’s where environment variables come in.
To translate your request to a valid CGI request, call it as such.
$ REDIRECT_STATUS=200 REQUEST_METHOD=GET SCRIPT_FILENAME=htdocs/index.php SCRIPT_NAME=/index.php PATH_INFO=/ SERVER_NAME=site.tld SERVER_PROTOCOL=HTTP/1.1 REQUEST_URI=/nl/page HTTP_HOST=site.tld /usr/bin/php-cgi X-Powered-By: PHP/5.3.13 Expires: Thu, 19 Nov 1981 08:52:00 GMT Cache-Control: no-store, no-cache, must-revalidate, post-check=0, pre-check=0 Pragma: no-cache Content-type: text/html <HTML>...
In the example above, a few important environment variables come into play that are seperated by spaces. After the environment variables, the full path to the php-cgi binary is included (you can find this out with the ‘which php-cgi’ command at the CLI).
- REDIRECT_STATUS=200: this is important because most php-cgi’s are compiled with extra protection that won’t work without that variable.
- REQUEST_METHOD=GET: the HTTP method you’re using, for simulating POST requests you can of course change that.
- SCRIPT_FILENAME=htdocs/index.php: this needs to the path to the script that will process your request. For Zend Framework-like applications, that will be public/index.php most likely.
- SCRIPT_NAME=/index.php: the relative full path to the script according to the ‘document root’.
- PATH_INFO=/
- SERVER_NAME=site.tld: not really that relevant in this example.
- SERVER_PROTOCOL=HTTP/1.1: which HTTP protocol you want to support, can be HTTP/1.0 or HTTP/1.1.
- REQUEST_URI=**/nl/page**: the URL a browser would normally call, this triggers the routing in Zend Framework projects.
- HTTP_HOST=site.tld: the domain name of the URL you want, in the example of ‘http://site.tld/nl/page' this would be site.tld, the FQDN.
By calling the script as such, you can trigger “HTTP requests” via the CLI by pre-filling the environment variables. That example listed a few paragraphs higher is the CLI equivalent of browsing to ‘http://site.tld/nl/page' via a webserver that would pass along the request to php-cgi.