Varnish: Кастомная страница с ошибкой

Date October 19th, 2012 Author Vitaly Agapov

— Они ненавидят меня, потому что я лучше их.
— Нет, они ненавидят тебя потому, что ты ведёшь себя так, как будто считаешь себя лучше их.

Джордж Р. Мартин «Игра Престолов»

 

По умолчанию в случае возникновения каких-либо ошибок Varnish выдаёт классическое окно с сакраментальной фразой "Service Unavailable. Guru Meditation". Все это, конечно, интересно. Особенно интересна история этой фразы, берущей начало из операционки AmigaOS, в которую она попала из одной из амиговских игр под контроллер Joyboard. Суть этой игры заключалась в том, чтобы как можно дольше сидеть в позе лотоса и не шевелиться. Если же игрок шевелился, то возникала ошибка "Guru Meditation Error". В общем, можно с уверенностью сказать, что разработчики и пользователи Amiga познали-таки дзен. Завидую.

Однако в production-среде совсем не хочется, чтобы пользователи видели подобные сбивающие с толку сообщения.

Само собой, можно подредактировать дефолтную функцию vcl_error в конфиге Varnish и прописать там свою собственную html-вёрстку вроде такой:

01.sub vcl_error {
02.    set obj.http.Content-Type = "text/html; charset=utf-8";
03.    set obj.http.Retry-After = "5";
04.    synthetic {"
05.<?xml version="1.0" encoding="utf-8"?>
06.<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
08.<html>
09.  <head>
10.    <title>My Error</title>
11.  </head>
12.  <body>
13.    <h1>Oops</h1>
14.    <p>Error occured</p>
15.    <h3>Sorry</h3>
16.  </body>
17.</html>
18."};
19.    return (deliver);
20.}

Но это не очень удобно (точнее – очень не удобно), если у нас есть нормальная большая свёрстанная заглушка. В конфиге её держать неправильно, править неудобно, а использовать совместно, скажем, с тем же Apache так и вообще невозможно.

На помощь придёт модуль std (речь о Varnish версии 3 и старше) и метод std.fileread, которым можно считать файл с диска, а потом отдать его уже synthetic'у:

01.import std;
02.sub vcl_error {
03.  if ( obj.status >= 500 && obj.status <= 505) {
04.      set obj.http.Content-Type = "text/html; charset=utf-8";
05.        set obj.http.error50x = std.fileread("/var/www/site-closed/index.html");
06.        synthetic obj.http.error50x;
07.        unset obj.http.error50x;
08.        return(deliver);
09.  }
10.}

Есть ещё способ считать файл inline'овым кодом на C. Но этот метод дик, ужасен и костылен. В Гугле можно найти.

Tags:
Category: Varnish | No comments »

Comments

Leave a comment

 Comment Form 

Rich Text Editor, comment