Веб-интерфейс OpenNebula'ы - Sunstone не имеет поддержки SSL из коробки, что требует использования реверс-проксирующего веб-сервера. В данной статье рассмотрим конфигурацию nginx для достижения максимальной скорости загрузки файлов и починим неработающую веб-консоль.
Взяв сперва простейший конфиг реверс-прокси nginx можно столкнуться с тем, что загрузка образов дисков через Sunstone либо становится очень медленной, либо прерывается после первых нескольких процентов. Это происходит из-за того, что для загрузки файлов используется механизм Chunked transfer encoding, представленный в HTTP/1.1, который не терпит буферизации, но таки буферизируется nginx'ом, потому что тот по умолчанию подключается к backend'у используя HTTP/1.0.
Для исправления этой проблемы нужно заставить nginx использовать HTTP/1.1 для подключения к проксируемому серверу и отключить буферизацию запросов и ответов:
proxy_request_buffering off;
proxy_buffering off;
proxy_http_version 1.1;
Также, для возможности загрузки больших файлов, следует увеличить значения таймаута для отправки и получения данных от бэкэнда, которые по умолчанию составляют 60 секунд, а также максимальный размер передаваемых от клиента данных.
client_max_body_size 8192M
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
Следующая проблема, с которой придётся столкнуться: неработающая веб-консоль виртуальных машин (VNC). Она связана с механизмом защиты от XSS-атак. Сервер, запрещающий обращения к себе с других сайтов, проверяет в поступающих HTTP-запросах совпадение доменного имени из Host с Origin.
Nginx при проксировании подставляет в заголовок Host домен (или IP-адрес) из proxy_pass. Заголовок Origin отправляется браузером и не модифицируется nginx'ом при проксировании. Это приводит к срабатыванию защиты XSS, встроенной в Sunstone.
HTTP-заголовки, отправляемые браузером:
Host: cloud-provider.tld
HTTP-заголовки, доходящие до Sunstone:
Host: 127.0.0.1:9869
Почему это случается только с VNC и не затрагивает другие запросы к Sunstone? Заголовок Origin подставляется только к так называемым CORS-запросам, т.е. отправляемым на другие Origin'ы. Графическая консоль Sunstone располагается на отдельном порту и подключения к ней попадают под это понятие и дополняются заголовком Origin:
Host: cloud-provider.tld:29876
Origin: https://cloud-provider.tld
Так как Nginx не проксирует подключения к VNC, до Sunstone доходят запросы с разными значениями Host и Origin: 127.0.0.1 и cloud-provider.tld.
Поправить это можно, заставив nginx сохранять оригинальное значение заголовка Host из запроса клиента:
proxy_set_header Host $http_host;
Конфигурационный файл nginx со всеми указанными исправлениями:
server {
listen 80 default_server;
server_name cloud-provider.tld;
location / {
return 301 https://$server_name:443;
}
}
server {
listen 443 ssl default_server;
server_name cloud-provider.tld;
ssl_certificate /etc/ssl/certs/cloud-provider.tld.crt;
ssl_certificate_key /etc/ssl/certs/cloud-provider.tld.key;
client_max_body_size 8192M;
proxy_request_buffering off;
proxy_buffering off;
proxy_http_version 1.1;
location / {
proxy_pass http://127.0.0.1:9869;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
proxy_set_header Host $http_host;
}
}