문제

Basically, one of the greatest questions of all time: What are some ways you're using settings.php in your development/staging workflow?

Right now, I have my settings.php file set up like the following, and I base my development on the server's $HOST directive—meaning I can work on dev.example.com for the development (shared) server, local.example.com for my local computer (and other dev's local code checkouts), and www.example.com (or just example.com) for the live site.

(This code is in the 'Database settings' section of settings.php):

$host = $_SERVER['HTTP_HOST'];
$base_url = 'http://'.$host;
$cookie_domain = $host;

switch($host) {
  case 'example.com': # Production server
    $db_url = 'mysqli://prod_sql_user:password@127.0.0.1/prod_db';
    $update_free_access = FALSE;
    $conf = array (
      // Set production config options here...
      'example_setting' => 0,
    );
    break;

  case 'dev.example.com': # Development server
    $db_url = 'mysqli://dev_sql_user:password@127.0.0.1/dev_db';
    $update_free_access = FALSE;
    $conf = array (
      // Set production config options here...
      'example_setting' => 0,
    );
    break;

  case 'local.example.com': # Local server
    $db_url = 'mysqli://local_sql_user:password@127.0.0.1/local_db';
    $update_free_access = FALSE;
    $conf = array (
      // Set production config options here...
      'example_setting' => 0,
      // Turn off most core caching.
      'cache_inc' => 'includes/cache.inc',
      'cache' => CACHE_DISABLED,
    );
    break;

}
?>

This works pretty well for most purposes, but it means we have a lot of extraneous code sitting around in our shared settings.php file... is there a better way?

도움이 되었습니까?

해결책

What I do is separating that file into a settings.php and a local.settings.php.

At the end of settings.php is the following code:

if (file_exists(dirname(__FILE__) . '/local.settings.php')) {
  include dirname(__FILE__) . '/local.settings.php';
}

The local file is then excluded from whatever VCS you are using. The advantage is that you can put settings which are common over all instances in settings.php and have that versioned/distributed automatically and keep the local stuff in local.settings.php.

다른 팁

This seems like you're reinventing Drupal's built in multisite functionality.

Personally, I keep all standard themes and modules for the site in sites/all, and then have sites/dev.example.com and sites/example.com.

As an added bonus you can then have different files folders for each site, and you can add any development modules to sites/dev.example.com/modules as well.

I prefer to ignore the file locally (using a .gitignore file in git) and then keep separate versions if the file on each host.

I tend to always set up DNS or host file entries and use

dev.example.com
staging.example.com

and

example.com

Then I have completely separate settings file directories with differing files directories. For instance ./sites/dev.example.com/files

Why not have a few folders based on the development host name?

Example

  • sites/dev1.domain.com
  • sites/dev2.domain.com
  • sites/dev3.domain.com
  • sites/www.domain.com

Each with their own settings file and db_url.

If the only things changing are the database credentials, then you can set environment variables in your local (and staging/production) virtual host config or in a .htaccess a folder above your web root. Here's a simple example:

/var/www/example.com/drupal-resides-here

I can then create a .htaccess file here:

/var/www/example.com/.htaccess

which has the following code:

SetEnv DB1_USER my_local_user
SetEnv DB1_PASS my_local_pass
SetEnv DB1_HOST my_local_host
SetEnv DB1_NAME my_local_dbname

Then in /var/www/example.com/drupal-resides-here/sites/default/settings.php (or whatever) you can grab the db credentials like:

$db_url = "mysql://{$_SERVER['DB1_USER']}:{$_SERVER['DB1_PASS']}@{$_SERVER['DB1_HOST']}:{$_SERVER['DB1_PORT']}/{$_SERVER['DB1_NAME']}";

This lets multiple developers run things locally and you can push to staging / production while still tracking settings.php (there are more things in there than just the database credentials...). You also wouldn't have to keep track of multiple settings.php files.

Simplest and most efficient solution that is just one line is the following. Just include it in the last line of your settings.php file:

@include('settings.local.php');

The @ symbol in the front just means don't display any error even if it doesnt find that file. Typical setup's like this involve a conditional to check if the file is there. This accomplishes it in one line without it.

http://php.net/manual/en/language.operators.errorcontrol.php

Also known as the STFU PHP operator.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 drupal.stackexchange
scroll top