views:

177

answers:

8

I'm trying to determine the best way of having a PHP script determine which server the script/site is currently running on.

At the moment I have a switch() that uses $_SERVER['SERVER_NAME'] . ':' . $_SERVER['SERVER_PORT'] to determine which server it's on. It then sets a few paths, db connection parameters, SMTP paramters and debug settings based on which server it's on. (There maybe additional parameters depending on the site needs.)

This means that I can simply drop the site onto any of the configured servers without having to change any code (specifically the configuration). If it's a new server, then I simply add a new case and it's ready from then on.

We have done loading config files based on the same SERVER_NAME:SERVER_PORT combination, but found that it's another file you have to maintain, plus we weren't sure on the speed of parsing ini files, (although having extra cases for each server may be just as slow).

Another problem we have is when a site is often moved between 2 servers, but we use the same SERVER_NAME and SERVER_PORT on each. This means we need to temporarily comment one case and ensure it doesn't get into the repo.

Another other ideas? It needs to be available on all servers (sometimes SERVER_NAME and SERVER_PORT are not). It would also be nice if it worked with the CLI PHP.

+2  A: 

How about using $_SERVER['SERVER_ADDR'] and base your identity off the IP address of the server.

UPDATE: In a virtual host situation, you might also like to concatenate the IP with the document root path like so:

$id = $_SERVER['SERVER_ADDR'] . $_SERVER['DOCUMENT_ROOT'];
Adam Pierce
Because we use shared servers a lot and sometimes don't use SSL, we might have the same site more than once on the same server, therefore same IP.
Darryl Hein
Maybe you'll have to combine the server IP or host name with the document root path in that case. Hopefully that will be unique enough for you.
Adam Pierce
This doesn't work for CLI scripts, since $_SERVER vars will not be defined...
wimvds
+2  A: 

We use the $_SERVER['HTTP_HOST'] variable to create the filename of a PHP include file which contains all the vhost-specific information (we deploy the same software to a lot of vhosts)

I like this technique, as you can get clever with it to build hierarchies of configurations, e.g. for www.foo.com,

  • try to load com.config.php
  • try to load foo.com.config.php
  • try to load www.foo.com.config.php

Doing it this way lets you set options for all your live sites globally, and tweak individual sites on as as-needed basis. We have our own internal root domain name for developer sandboxes too, so we can enable all the developer level options in internal.config.php

You can also do this in reverse, i.e. try to load www.foo.com.config.php, and only if not found would you try to load foo.com.config.php, and so on. More efficient, but a little less flexible.

Paul Dixon
+2  A: 

Here are some variables you can check:

$_SERVER['HTTP_HOST'];

I use this one for checking which server I'm on when php is running through apache.

$_SERVER['USER'];
$_SERVER['LOGNAME'];

I use these two for when I know I'm running from the console. One of those invariably resolves to a usable username. There seem to be no other host-defining variables in console mode.

This might not help you enough; If you find you still have a hard time being able to uniquely identify what server you are on you can give it a little bit of a "push." In my situation I have a small config file which is unique to each server, basically setting a php variable defining which environment I'm running in (e.g. development or production.) This way you only need to maintain one small, easy to recreate file outside of your source control.

MDCore
+1  A: 

Ive always kept a config.php on my sites, storeing such infomation which may be percificic to that server.

  • Being php parseing it is nearly (eg the file needs to be opened, closed, etc) as fast as having the code at the top of each script, and much faster than ini and xml config solutions
  • Centralised location for the sites configuration on each server, so easy to keep upto date (server doesn't change that oftern, updateing the config is simple with an update script).
  • Can be generated by the script, all my sites have a function that rebuilds the config file useing the $config[] assoc array.
  • Updates that effect the config file are as simple as "$config['key'] = 'new value';config_update()"
Fire Lancer
A: 

Why don't you have configuration files for each host stored outside of the project directory and read it from the php code?

Having host specific code is not really a good practice.

Czimi
A: 
$posix_uname   = function_exists('posix_uname') ? posix_uname() : null;
$this_hostname = !empty($_SERVER["HOSTNAME"]) ? $_SERVER["HOSTNAME"] : $_ENV["HOSTNAME"];
$this_hostname = !empty($this_hostname) ? $this_hostname : $posix_uname['nodename'];
duckyflip
+1  A: 

I have been using the following mechanism:

if(__FILE__ === '/Sites/mywebsite.com/includes/config.php')
    define('SERVER', 'DEV');
else
    define('SERVER', 'PRODUCTION');

My development environment has a rather distinct path structure so this works well, and I don't need to worry if additional domains are added to $_SERVER[HTTP_HOST], or a client that provides an incorrect HTTP_HOST value (although that would be rare ...).

too much php
A: 

We use environment variables for this (ENVPHP environment variable which will contain the specific server environment - ie. development/test/production). This approach works very well for CLI scripts as well (for CLI you set the OS environment variables, for Apache you can use SetEnv switches in the host configuration). In PHP you access this environment variable using getenv('ENVPHP')...

wimvds