Installing ClusterControl with an existing cluster and Nginx
ClusterControl is a comprehensive tool for managing and monitoring MySQL and MongoDb clusters, more information can be found here.
ClusterControl comes with some great scripts for automating deployment, however there are a number of hard coded dependencies (like Apache) which make it a rather more painful process to integrate with your existing systems.
Background info:
There are 3 components that make up ClusterControl:
ClusterControl UI: A CakePHP based GUI
CMON: A daemon process which monitors servers and writes to a MySQL database
CMON API: A PHP based API which reads data from the CMON database
ClusterControl UI and CMON API can be on the same or different hosts and the UI can talk to multiple instances of the CMON API (hence multiple CMON daemons).
The UI also makes AJAX calls to the API via a script in the path /access which simply sends the same request to the API with the addition of the API token.
There are several .htaccess files that rewrite requests to the UI, the access script and the API.
Installation process:
CMON can be installed by following this guide.
The guide contains a section at the end to install the UI/API, this does install and configure Apache, but you can simply remove it again.
Making it work with Nginx:
After a bit of tinkering I've put together a config which works nicely for both the ClusterControl UI and CMON API:
server {
listen 1.2.3.4:80;
server_name mydomain.com;
access_log /var/log/nginx/mydomain.com-access.log;
error_log /var/log/nginx/mydomain.com-error.log;
root /var/www;
index index.php;
location ~ \.htaccess {
deny all;
}
location ~ \.php$ {
fastcgi_pass 127.0.0.1:9000;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include /etc/nginx/fastcgi_params;
}
# Handle requests to /clustercontrol
location /clustercontrol {
alias /var/www/clustercontrol/app/webroot;
try_files $uri $uri/ /clustercontrol/app/webroot/index.php;
}
# Equivalent of $is_args but adds an & character
set $is_args_amp "";
if ($is_args != "") {
set $is_args_amp "&";
}
# Handle requests to /clustercontrol/accesss
location ~ "^/clustercontrol/access/(.*)$" {
try_files $uri $uri/ /clustercontrol/app/webroot/access/index.php?url=$1$is_args_amp$args;
}
# Handle requests to /cmonapi
location ~ "^/cmonapi/(.*)$" {
try_files $uri $uri/ /cmonapi/index.php?url=$1$is_args_amp$args;
}
}
Making the UI work is straight forward, however the access script and API require the partial URL and the equivalent of the mod_rewrite [QSA] flag as the ? in the try_files directives stops Nginx from auto-appending the query string from the request, hence the need for the regex and appended args.
At the time of writing a small code change is also required to the library used by the access script which is located in /clustercontrol/app/Lib/Access.php as the API token header uses an underscore rather than a dash which results in Nginx ignoring it (which I think is correct behaviour, probably an RFC floating around somewhere which will clarify this).
Replace both instances of:
$headers[0] = "CMON_TOKEN: {$token}";
With:
$headers[0] = "CMON-TOKEN: {$token}";
Everything should now work!