relayer 2.2.19 исправляет подсчёт пересекающихся фильтров
NIP-45 требует объединять несколько фильтров COUNT через OR в один результат. relayer раньше считал каждый фильтр отдельно и складывал итоги, поэтому одно событие могло попасть в результат дважды. Версия 2.2.19 добавляет интерфейс хранилища для точного подсчёта объединения.
Nostr WoT Newsroom
Материал подготовлен редакцией Nostr WoT на основе указанных первоисточников и опубликован автоматически, без индивидуальной проверки человеком.
NIP-45 позволяет клиенту спросить у relay, сколько событий соответствует запросу, не загружая сами события. Клиент отправляет сообщение COUNT с одним или несколькими фильтрами, а relay возвращает одно целое число. Важная деталь касается нескольких фильтров: спецификация требует объединять их через OR и выдавать единый результат.
relayer 2.2.19 меняет реализацию этого правила для хранилищ, способных вычислить объединение нескольких фильтров. До этой версии relayer вызывал CountEvents отдельно для каждого фильтра, а затем складывал ответы. Такой расчёт верен, если фильтры не могут найти одно и то же событие. При пересечении итог получается завышенным.
Представим два фильтра в одном запросе. Первый запрашивает события kind 1. Второй запрашивает kinds 1 и 7. Событие kind 1 удовлетворяет обоим фильтрам, но по правилу OR из NIP-45 оно должно попасть в итог один раз. Сумма двух независимых подсчётов включает его дважды.
Разница между 2.2.18 и 2.2.19 добавляет интерфейс FiltersCounter с методом CountEventsFilters. Реализовавшее его хранилище получает полный список фильтров и может посчитать объединение напрямую. Обработчик запроса выбирает этот путь при наличии нескольких фильтров. Для одного фильтра по-прежнему используется существующий метод CountEvents.
Это расширение интерфейса, а не безусловное исправление для любого backend. Если хранилище не реализует FiltersCounter, relayer продолжает считать фильтры отдельно и складывать результаты. Комментарий в коде точно описывает границу: резервный путь даёт верный ответ, пока фильтры не пересекаются. При пересечении избежать дублей может только backend с поддержкой новой операции объединения.
Релиз также меняет обработку ошибок на новом пути. Если CountEventsFilters завершается ошибкой, relay отвечает error: failed to count events, а не продолжает с частичным результатом. Старый резервный путь всё ещё записывает ошибку отдельного подсчёта в журнал и переходит к остальным фильтрам.
Различие закреплено тремя новыми тестами. Первый проверяет, что хранилище только со старым счётчиком получает два отдельных вызова. Второй отправляет пересекающиеся фильтры хранилищу с поддержкой объединения и ожидает результат 4 вместо суммы 6. Третий подтверждает, что запрос с одним фильтром остаётся на прежнем методе и не вызывает счётчик объединения.
Изменение небольшое, но оно влияет на видимый клиенту ответ. COUNT нужен, чтобы клиент не загружал большой набор событий только ради его размера. Счётчики реакций, ответов, reposts или подписчиков могут строиться из пересекающихся фильтров. Завышенный результат из-за повторного учёта одного события меняет число на экране, хотя сам набор событий не изменился.
NIP-45 также допускает вероятностные подсчёты и данные HyperLogLog, однако этот релиз их не меняет. Изменение касается обычного подсчёта по нескольким фильтрам. Точность объединения зависит от поддержки нового интерфейса выбранным хранилищем.
Версия 2.2.19 опубликована 8 сентября 2026 года. Релиз содержит два commits и изменяет три файла: обработчик запроса, интерфейс хранилища и тесты.
Источники
Каждое утверждение в этом материале ссылается на первоисточник.
- relayer v2.2.19 — fiatjaf/relayer (8 сентября 2026 г.)
- Сравнение v2.2.18...v2.2.19 — fiatjaf/relayer (8 сентября 2026 г.)
- NIP-45: Event Counts — nostr-protocol/nips (8 сентября 2026 г.)