Сейчас идёт тестирование: код на GitHub будет открыт после завершения.

Протокол — сервер ↔ сервер (кластер)

Протокол peer RPC, используемый только в режиме кластера. Узлы разделяют единое состояние блокировок через консенсус Raft — каждое изменение состояния блокировки (захват, освобождение, истечение) применяется только после того, как проходит путь предложение лидера → репликация большинству → commit, поэтому взаимное исключение сохраняется даже во время разделения сети или переключения при отказе. Концептуальное объяснение смотрите в Как это работает.

Поток — путь одного захвата до commit

Клиент
Leader
Follower 1
Follower 2
A · acquire (key)
AppendEntries (Grant)
AppendEntries (Grant)
OK
большинство достигнуто → commit, применяется на всех узлах
A · acquired (token)
запросответRPC консенсуса (Raft)

Лидер оформляет команду блокировки как команду репликации и отправляет её через AppendEntries; как только её записывает большинство, включая самого лидера, происходит commit (при 3 узлах достаточно лидера + follower 1 — ответа от остальных не ждут). Ответ клиенту уходит только после commit, поэтому если ответ получен — эта блокировка уже зафиксирована большинством.

Правила портов и адресов

  • Peer RPC использует выделенный Raft-порт = клиентский порт + 1000 (например, 52256225). Он выводится автоматически, без отдельного ключа настройки, и слушается только в режиме кластера. В брандмауэре нужно открыть оба порта.
  • В настройках (cluster_self/cluster_peers) указывается клиентский адрес. Порт +1000 добавляется только при обращении (dial) к пирам, а адрес редиректа M (перемещено), передаваемый клиенту, остаётся клиентским адресом как есть.
  • Роль определяется портом — в самом протоколе нет процедуры различения клиента и пира. Порядок установления соединения и правила аутентификации/TLS смотрите в Установление соединения · аутентификация.

Содержание

Смотрите также