I
I
Ivan2014-05-10 22:54:15
PHP
Ivan, 2014-05-10 22:54:15

How to achieve DRY in nginx configuration for many sites of the same type?

When switching from nginx+apache to nginx+php-fpm, there was a problem with nginx configs.
There are ~5 users on the server, each with several sites.
Half of the sites have a simple structure:

/home/user_name/sites/example.com/log/...
/home/user_name/sites/example.com/tmp/...
/home/user_name/sites/example.com/www/...

The other half is written in yii, has a backend and the structure is as follows:
/home/user_name/sites/example.com/backend/log/...
/home/user_name/sites/example.com/backend/tmp/...
/home/user_name/sites/example.com/backend/www/...

/home/user_name/sites/example.com/frontend/log/...
/home/user_name/sites/example.com/frontend/tmp/...
/home/user_name/sites/example.com/frontend/www/...

Structure of nginx configs:
/etc/nginx/nginx.conf
/etc/nginx/sites/default.conf
/etc/nginx/sites/andrey/site.ru.conf
/etc/nginx/sites/andrey/example.com.conf
/etc/nginx/sites/ivan/example.ru.conf
...

/etc/nginx/nginx.conf:
...
http {
    ...
    include sites/default.conf;
    include sites/andrey/*.conf;
    include sites/ivan/*.conf;  
}

I want to make the config of any site (for example /etc/nginx/sites/ivan/example.ru.conf) look like this:
set $user_name ivan;
set $site_name example.ru;

include  sites/basic_server.conf; # конфиг сервера для первой схемы
# или 
include  sites/advanced_server.conf; # конфиг сервера для второй схемы с бекэндом

For example, sites/basic_server.conf:
listen 80;
server_name $site_name www.$site_name;

access_log /home/$user_name/sites/$site_name/log/nginx_access.log main;
error_log /home/$user_name/sites/$site_name/log/nginx_error.log;

root /home/$user_name/sites/$site_name/www;
index index.php index.html;

if ($host = 'www.$site_name') {
    rewrite ^/(.*)$ http://$site_name/$1 permanent;
}

location ~ \.php$ {
    include conf.d/fastcgi.conf;
}

Questions:
1. You cannot declare variables (set) outside the server { } section. How to be?
2. Construction server_name $site_name www.$site_name; does not work (or rather, the variables in this line do not work and instead of the desired site, nginx returns default). If you change the variables to normal values ​​- everything is ok.
3. I am still haunted by a much more DRY option from the realm of fantasy: no separate configs, only a single nginx.conf in which we set an associative array ala:
set $sites array(
array('user' => ivan, 'name' => 'example.com', 'type' => 'basic'),
array('user' => andrey, 'name' => 'example.ru', 'type' => 'advanced'),
);

Which nginx processes and connects the required config (basic or advanced) using if.
Maybe nginx can work with arrays and is this possible?
4. How did you achieve dry in the nginx configuration? What is your website structure and connection scheme for new ones?

Answer the question

In order to leave comments, you need to log in

2 answer(s)
G
grossws, 2014-05-11
@0neS

You can not bother and generate with a template engine from SCM (such as chef/puppet/ansible/salt/cfengine/bcfg2)

E
Eugene, 2014-05-10
@Nc_Soft

It seems to me that it is necessary to resolve root and other hosts in default.
But in general, isp does not take a steam bath and prescribes each site, there is nothing terrible here, but it is flexible.

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question