Тщательно изучите серию статей etcd (9): etcd compact и watch API

задняя часть облачный носитель

0 Обзор альбома

etcd является важным базовым компонентом облачной архитектуры, которая инкубируется и размещается CNCF. etcd можно использовать не только для регистрации и обнаружения сервисов в микросервисах и кластерах Kubernetes, но и как промежуточное ПО для хранения ключей и значений.

"Понимание статей серии etcd" познакомит с etcd с точки зрения базовой функциональной практики etcd, интерфейса API, принципа реализации, анализа исходного кода и опыта преодоления ям в реализации. Ожидается, что статей будет около 20, автор будет обновлять каждую неделю, прошу обратить внимание.

1 Компактный метод

Метод Compact сжимает историю событий в хранилище ключей и значений etcd. Хранилище ключей-значений следует периодически сжимать, иначе история событий будет бесконечно расти.

rpc Compact(CompactionRequest) returns (CompactionResponse) {}

Тело сообщения запроса — это запрос CompactionRequest, который сжимает пары ключ-значение, хранящиеся в данной версии. Все ключи с ревизиями меньше сжатой ревизии будут удалены:

message CompactionRequest {
  // 键值存储的修订版本,用于比较操作
  int64 revision = 1;

  bool physical = 2;
}

Если для параметра Physical установлено значение true, RPC будет ждать, пока сжатие не будет физически применено к локальной базе данных, после чего сжатые элементы будут полностью удалены из серверной базы данных. Тело ответа CompactionResponse определяется как:

message CompactionResponse {
  ResponseHeader header = 1;
}

CompactionResponse имеет только один общий заголовок ответа.

2 Служба часов

Watch API предоставляет интерфейс на основе событий для асинхронного мониторинга ключевых изменений. Сторожевой таймер etcd3 работает, постоянно отслеживая изменения ключей для данной версии (текущей или исторической) и передавая обновления ключей обратно клиенту.

мероприятие

Каждое изменение ключа представлено сообщением о событии. Сообщение о событии будет предоставлять как данные обновления, так и тип обновления.Тело сообщения mvccpb.Event определяется следующим образом:

message Event {
  enum EventType {
    PUT = 0;
    DELETE = 1;
  }

  EventType type = 1;

  KeyValue kv = 2;

  // prev_kv 持有在事件发生前的键值对
  KeyValue prev_kv = 3;
}

тип - тип события. Если тип PUT, это означает, что новые данные были сохранены в ключе, если тип DELETE, это означает, что ключ был удален.

kv содержит KeyValue для события. Событие PUT содержит текущую пару ключ-значение kv. Событие PUT с kv.Version=1 указывает на создание ключа. События DELETE/EXPIRE содержат удаленный ключ с модифицирующей ревизией, установленной на удаленную ревизию.

контролировать поток

Watch API предоставляет интерфейс на основе событий для асинхронного мониторинга ключевых изменений. Сторожевой таймер etcd ожидает изменения ключа, непрерывно отслеживая данную версию (текущую или историческую) и передавая обновления ключа обратно клиенту.

Мониторинг выполняется непрерывно и использует gRPC для потоковой передачи данных о событиях. Поток мониторинга является двунаправленным: клиенты пишут в поток, чтобы устанавливать события мониторинга, и читают, чтобы получать события мониторинга. Один поток наблюдения может мультиплексировать множество различных наблюдений, помечая события каждым идентификатором наблюдателя. Это мультиплексирование помогает уменьшить объем памяти и накладные расходы на соединения в кластерах etcd.

События просмотра имеют следующие три характеристики:

  • Упорядоченные, события сортируются в порядке редакции; если событие старше опубликованного, оно никогда не появится на часах.
  • Надежная последовательность событий никогда не отбрасывает какую-либо последовательность событий; если хронологический порядок a
  • Atomic гарантирует, что список событий содержит полную ревизию; обновления с помощью нескольких ключей в одной и той же ревизии не будут разбиты на несколько списков событий.

Смотреть определение службы

Служба Watch определена в rpc.proto следующим образом:

service Watch {
  rpc Watch(stream WatchRequest) returns (stream WatchResponse) {}
}

Часы наблюдают за событиями, которые вот-вот произойдут или уже произошли. И ввод, и вывод являются потоками; входные потоки используются для создания и отмены наблюдений, а выходные потоки отправляют события. RPC наблюдения может одновременно наблюдать за несколькими диапазонами ключей и передавать события для нескольких наблюдений. Всю историю событий можно просмотреть, начиная с последней сжатой ревизии. WatchService имеет только один метод Watch.

Тело сообщения WatchRequest запроса определяется следующим образом:

message WatchRequest {
  oneof request_union {
    WatchCreateRequest create_request = 1;
    WatchCancelRequest cancel_request = 2;
  }
}

request_union — это либо запрос на создание нового наблюдателя, либо запрос на отмену существующего наблюдателя. Запрос на создание нового наблюдателя WatchCreateRequest:

message WatchCreateRequest {
  // key 是注册要观察的 key
  bytes key = 1;

  bytes range_end = 2;

  // start_revision 是可选的开始(包括)观察的修订版本。不设置 start_revision 则表示 "现在".
  int64 start_revision = 3;

  bool progress_notify = 4;

  enum FilterType {
  // 过滤掉 put 事件
  NOPUT = 0;

  // 过滤掉 delete 事件
  NODELETE = 1;
  }

  // 过滤器,在服务器端发送事件给回观察者之前,过滤掉事件。
  repeated FilterType filters = 5;

  // 如果 prev_kv 被设置,被创建的观察者在事件发生前获取上一次的KV。
  // 如果上一次的KV已经被压缩,则不会返回任何东西
  bool prev_kv = 6;
}

range_end — это конец диапазона [key, range_end) для наблюдения. Если range_end не установлен, будет наблюдаться только ключ параметра; если range_end равен '\0', будут наблюдаться все ключи, большие или равные ключу параметра; если range_end больше заданного ключа на 1, то все ключи с заданным ключом будут наблюдаться.Ключи с префиксом будут наблюдаться.

Progress_notify установлен таким образом, что если нет недавних событий, сервер etcd будет периодически отправлять WatchResponse без каких-либо событий новым наблюдателям. Полезно, когда клиент хочет восстановить отключенный наблюдатель, начиная с последней известной ревизии. Сервер etcd будет решать, как часто он будет отправлять уведомления, в зависимости от текущей нагрузки.

Отмените WatchCancelRequest существующего наблюдателя:

message WatchCancelRequest {
  int64 watch_id = 1;
}

watch_id — это идентификатор наблюдателя, который необходимо отменить, чтобы больше не распространялись события. Тело ответа

message WatchResponse {
  ResponseHeader header = 1;
  // watch_id 是和应答相关的观察者的ID
  int64 watch_id = 2;

  bool created = 3;

  bool canceled = 4;

  int64 compact_revision  = 5;

  // cancel_reason 指出取消观察者的理由.
  string cancel_reason = 6;

  repeated mvccpb.Event events = 11;
}

created имеет значение true, если ответ был на запрос о создании наблюдателя. Клиенты должны регистрировать watch_id и ожидать получения событий из того же потока для созданных наблюдателей. Все события, отправляемые созданному наблюдателю, будут иметь один и тот же идентификатор watch_id; для параметра canceled установлено значение true, если ответом является отмена запроса наблюдателя. Отмененному наблюдателю больше не будут отправляться события.

compact_revision устанавливается на наименьший индекс, если наблюдатель пытается наблюдать сжатый индекс. Происходит, когда наблюдатель создается для сжатой ревизии или наблюдатель не может следить за ходом работы хранилища "ключ-значение". Клиенты ДОЛЖНЫ рассматривать наблюдатель как отмененный и НЕ ДОЛЖНЫ пытаться воссоздать какой-либо наблюдатель с той же start_revision.

3 Резюме

В этой статье в основном рассказывается о сжатии пары "ключ-значение" и API-интерфейсе просмотра, используемом в Etcd API. Это два часто используемых API, которые предоставляют внешние функции. Понимание сжатия пары "ключ-значение" и API просмотра очень полезно для нас, чтобы лучше использовать etcd.

Подписывайтесь на свежие статьи, приглашаю обратить внимание на мой публичный номер

Рекомендуемое чтение

  1. Сравнение etcd с другими компонентами k-v, такими как Zookeeper и Consul
  2. Тщательно изучите серию статей etcd (1): первое знакомство с etcd
  3. Тщательно изучите серию статей etcd (2): различные положения установки etcd
  4. Тщательно изучите серию статей etcd (3): эксплуатация и обслуживание кластера etcd, развертывание.
  5. Тщательно изучите серию статей etcd (4): безопасность etcd
  6. Тщательно изучите серию статей etcd (5): использование etcdctl
  7. Тщательно изучите серию статей etcd (6): etcd core API v3
  8. [Знакомство со статьями из серии etcd (7): API сервиса etcd gRPC

](блюз доступен empty.com/2020/08/27/…) 9. Тщательно изучите серию статей etcd (8): API транзакций etcd

Ссылаться на

etcd docs