Протокол Beanstalk

Материал из support.qbpro.ru

Это перевод официального протокола Beanstalk Резервная копия

переводчик Андрей Климов.

08-05-2014

Протокол

Протокол beanstalk работает поверх TCP используя кодировку ASCII. Клиенты могут устанавливать соединение, посылать команды и данные, а так же закрывать соединение. Для каждого соединения, сервер обрабатывает команды последовательно в порядке, в котором они были получены и посылает ответы в том же порядке. Все целые числа в протоколе отформатированы в десятичной форме и (если не указано иное) неотрицательны.

Названия в протоколе — строки в кодировке ASCII. Они могут содержать буквы (A-Z и a-z), цифры (0-9), знаки "-", "+", "/", ";", ".", "$", "_" и скобки "(" и ")", но не могут начинаться со знака "-". Названия разделяются символом пробел или символом конец строки. Каждое название должно быть длинной не менее одного символа.

Протокол содержит два вида данных: текстовые строки и неструктурированные куски данных. Текстовые строки используются для клиентских команд и ответов сервера. Части данных используются для передачи «тела» задачи и статистики. Каждое «тело» задачи является неразделенной последовательностью байтов. Сервер никогда не проверяет или изменяет «тело» задачи и всегда отправляет его обратно в его первоначальном виде. Это зависит только от клиентов, чтобы договориться о содержательной интерпретации «тел» задач.

Клиент может использовать команду «quit» или просто закрыть TCP соединение когда он больше не будет использовать сервер. Тем не менее, beanstalkd очень хорошо работает с большим количеством открытых соединений, поэтому обычно лучше для клиента, чтобы тот сохранил своё соединение открытым и использовал его как можно дольше. Это позволяет избежать расходов, связанных на установление новых сессий TCP.

Если клиент нарушает протокол (например, отправив не очень хорошо сформированный запрос или несуществующую команду) или в сервере произошла ошибка, сервер ответит одним из следующих сообщений об ошибке:

  • OUT_OF_MEMORY\r\n - Сервер не может выделить память для задачи. Клиенту нужно попробовать еще раз позже.
  • INTERNAL_ERROR\r\n - Эта ошибка сигнализирует о критической ошибке сервера. Такого не должно случиться никогда. Если такое произойдет, пожалуйста сообщите по адресу http://groups.google.com/group/beanstalk-talk.
  • BAD_FORMAT\r\n - Клиент послал неверно сформированную команду. Это может случится в случаях, если команда не заканчивается символом \r\n, если в позиции где ожидаются целое число, а находится иное, если неправильное количество аргументов или если командная строка неправильно формируется любым другим способом.
  • UNKNOWN_COMMAND\r\n - Клиент послал неизвестную для сервера команду

Эти ошибки не будут описаны в каждой команде индивидуально, но они неявно включены в описание всех команд. Клиенты должны быть готовы получать в ответ ошибку после любой команды.

В крайнем случае, если в сервере случилась критическая ошибка, которая приводит к прекращению обслуживания текущего клиента, сервер закроет соединение. (Прим переводчика. Далее по тексту клиенты, которые создают (генерируют) задачу будут называться генераторами задач, клиенты которые исполняют задачу, исполнителями задач).

Жизненный цикл задачи

Задачи в beanstalk создаются генераторами командой «put». На протяжении своей «жизни», задача может находится в одном из четырех состояний: "ready", "reserved", "delayed", или "buried". После создания командой "put", задача обычно переходит в состояние ready. Она ожидает в очереди ready до тех пор, пока не подключиться исполнитель и не даст команду "reserve" (прим переводчика: исполнитель может быть уже подключенным и просто дать команду "reserve" — зарезервировать за собой следующую в очереди задачу, находящуюся в состояние ready, как выполняемую. Можно перефразировать - зарезервировать следующую задачу в очереди ready. Состояние и очередь в данном случае одно и тоже). Если есть такая задача следующая в очереди, то она будет зарезервирована за исполнителем. Исполнитель выполняет задачу, после чего исполнитель посылает команду "delete", для её удаления.


На схеме типовой жизненный цикл задачи:

   put            reserve               delete
  -----> [READY] ---------> [RESERVED] --------> *poof*

На этой схеме приведены все возможные варианты:


   put with delay               release with delay
  ----------------> [DELAYED] <------------.
                        |                   |
                        | (time passes)     |
                        |                   |
   put                  v     reserve       |       delete
  -----------------> [READY] ---------> [RESERVED] --------> *poof*
                       ^  ^                |  |
                       |   \  release      |  |
                       |    `-------------'   |
                       |                      |
                       | kick                 |
                       |                      |
                       |       bury           |
                    [BURIED] <---------------'
                       |
                       |  delete
                        `--------> *poof*


Система имеет один или более каналов. Каждый канал состоит из очередей ready и delay. Каждое задание проводит всю свою «жизнь» в одном канале. Клиенты могут подписаться на канал, отправив команду "watch"; они могут отписаться от канала, отправив команду "ignore". Этот набор каналов, на которых осуществлена подписка, является как говорят, «watch list» клиента. Когда клиент посылает команду «reserve», задача может поступить из любого канала в «watch list».


Когда клиент подключается, его «watch list» он изначально подписан только на канал «default». Если он посылает команду «reserve» без предварительного использования команды «use», то все его задачи будут находится только в канале «default».


Каналы создаются по запросу, всякий раз когда на них ссылаются. Если канал пуст (это означает, что он не содержит задач со статусом «ready», «delayed» или «buried») и нет подписанных клиентов, канал будет удален.