В этот прекрасный четверг я обращаюсь к вам с интересной загадкой. На моём сайте, похоже, отображается ложный счётчик непрочитанных сообщений.
Что происходит
В верхней навигационной панели отображается Непрочитанные (14). Однако при нажатии на неё и переходе на страницу /unread там нет ни одной непрочитанной темы. На странице сообщается, что непрочитанных сообщений больше нет.
Аналогичную проблему наблюдают и другие пользователи, не являющиеся сотрудниками, хотя у них счётчики непрочитанных сообщений отличаются.
В приложении Discourse для iOS я также вижу счётчик непрочитанных сообщений, когда непрочитанных тем нет; иногда число в нём тоже отличается.
Платформа: десктопный веб и приложение Discourse для iOS
Проблема сохраняется и там, поэтому, похоже, она не вызвана темами или кастомизациями клиентских плагинов. В любой теме нет «шёпотов», так что, скорее всего, дело не в них.
Также я не могу использовать функцию Отклонить, потому что на странице /unread, когда список непрочитанных пуст, кнопки «Отклонить» нет.
Ожидаемое поведение
Если в навигации указано Непрочитанные (14), на странице /unread должно быть показано 14 непрочитанных тем, или хотя бы какие-то видимые непрочитанные темы.
Фактическое поведение
в навигации указано Непрочитанные (14)
страница /unread пуста
кнопка «Отклонить» отсутствует
проблема сохраняется в безопасном режиме
Вопросы
Есть ли известный способ восстановить/сбросить состояние непрочитанных сообщений для одного пользователя?
Существует ли серверная несогласованность, из-за которой счётчики непрочитанных сообщений могут сохраняться, даже когда страница /unread пуста?
Ранее я обращался к ИИ на ask.discourse.org по этому вопросу, и в итоге он порекомендовал мне опубликовать отчёт об ошибке здесь.
А, «фантомные непрочитанные» снова ударили по вашему сайту!
Вы недавно меняли права доступа к категориям или перемещали какие-то темы в защищённую категорию? Что-то изменило состояние отслеживания.
Раз уж у других та же проблема, разве не нужно сбросить это для всех?
Думаю, это можно исправить для всех через консоль Rails, но это немного непросто: мне нужно сначала разобраться и протестировать решение. Сейчас я с телефона, но постараюсь опубликовать решение через некоторое время, если никто другой не сделает этого раньше.
Да. В частном порядке наш персонал работал над категорией, аналогичной Documentation, которая недавно стала публичной после завершения.
Да, конечно. Моя идея заключалась в том, чтобы сначала протестировать это на себе, а затем исправить для всех. Поскольку это настолько сложный баг для тестирования (по крайней мере, для меня), я не хотел поднимать всем ожидания, пока не будет готово рабочее решение.
Спасибо за уверенность. Сегодня утром я заметил ежемесячный релиз за май 2026 годаv2026.05 и подумал, что он может исправить проблему, но она всё ещё сохраняется. Я уверен, что команда работает над этим. Discourse — это здорово.
О, боже. Честно говоря, я просмотрел все соответствующие отчёты о багах bug. На мгновение я даже подумал просто скрыть вкладку «Непрочитанные» из навигации и просто игнорировать проблему. Но это ничего не решит, верно? Похоже, она даже следует за мной здесь, на Meta.
Хорошо, этот скрипт Rails будет действовать как глобальная функция «Отметить все как прочитанное» и принудительно сбросит счётчик unread до 0 для всех пользователей, поэтому, к сожалению, он очистит любые корректные непрочитанные сообщения, а также любые фиктивные непрочитанные. Мы можем сделать это с помощью SQL-команды в Rails. Но имейте в виду, что это не исправляет корневую ошибку. Также это хорошая идея, если у вас есть свежая резервная копия, но я протестировал это на своём тестовом форуме, и всё сработало.
cd /var/discourse ./launcher enter app rails c
Вставьте весь следующий блок и нажмите Enter
sql = <<~SQL
UPDATE topic_users
SET last_read_post_number = topics.highest_post_number
FROM topics
WHERE topics.id = topic_users.topic_id
AND COALESCE(topic_users.last_read_post_number, 0) < topics.highest_post_number
AND topic_users.notification_level IN (2, 3, 4) -- Отслеживание, Наблюдение, Наблюдение за первым сообщением
SQL
# выполнить обновление
result = ActiveRecord::Base.connection.execute(sql)
puts "Успешно очищено #{result.cmd_tuples} непрочитанных тем на всём сайте."
# принудительно заставить браузеры клиентов сбросить кэшированное состояние и синхронизироваться с базой данных
MessageBus.publish("/topic-tracking-state", { clear: true })
Пользователям, возможно, придётся выполнить жёсткую перезагрузку, чтобы увидеть очищённое состояние unread.