Я замечаю, что на публичном сайте, который я администрирую, эмодзи отображаются некорректно. ACL установлен как приватный и помечен как безопасный с причиной «политика контроля доступа определяет безопасность | источник: создатель публикации».
Запуск задачи uploads:secure_upload_analyse_and_update исправляет проблему, но через несколько дней она возникает снова. Это также однажды произошло с логотипом сайта, но больше не повторялось.
Привет, @Wolftallemo, это довольно сложная проблема, когда кастомные эмодзи (или любые публично доступные загрузки, которые могут использоваться в постах) комбинируются с защищёнными загрузками. Некоторое время назад мы начали использовать таблицу UploadReference, чтобы отслеживать связи между сущностями и загрузками. Однако при миграции на эту таблицу мы установили одинаковые значения для всех полей created_at. Это привело к тому, что при проверке того, является ли первое использование загрузки публичным (в целях безопасности), порядок иногда оказывается неверным, и мы используем не ту запись. Дело в том, что если у обеих записей одинаковое значение created_at, PostgreSQL действует по своему усмотрению:
Ваше упоминание этого заставило меня ещё раз пересмотреть ситуацию, и я думаю, что мы можем решить это лучше, сортируя сначала по created_at ASC, а затем по id ASC. Таким образом, даже при наличии таких конфликтов будет использоваться действительно первая запись.
Если после объединения этого изменения (я постараюсь сделать это сегодня) проблемы сохранятся и вы уже загрузили свой сайт, мы сможем обсудить дополнительные варианты. Однако я подозреваю, что именно в этом ваша проблема. Вы можете подтвердить это, выполнив следующие запросы и сравнив результаты на своём сайте:
CustomEmoji.find_by(name: "success").upload.upload_references.order("created_at ASC")
CustomEmoji.find_by(name: "success").upload.upload_references.order("created_at ASC, id ASC")
В первом случае target_type должен быть Post, во втором — CustomEmoji.
Интересно, значит, возвращается правильный результат. Для загруженного файла, который вы прислали по ссылке, пожалуйста, опубликуйте значения security_last_changed_reason и security_last_changed_at, а также проверьте, заполнено ли поле access_control_post_id. Оно не должно помечать эту загрузку как защищённую, если первое упоминание — это пользовательский эмодзи. Попробуйте также следующее:
Upload.find(ID)
.upload_references
.joins(<<~SQL)
LEFT JOIN posts ON upload_references.target_type = 'Post' AND upload_references.target_id = posts.id
SQL
.where("posts.deleted_at IS NULL")
.order("upload_references.created_at ASC, upload_references.id ASC")
.first
Я получил access control post dictates security | source: post creator с датой Wed, 22 Mar 2023 09:13:10.341411000 UTC +00:00
Мне был предоставлен идентификатор контрольного поста для публикации в закрытой категории, которая была создана более трёх лет назад и никогда не редактировалась.
Интересно, а в том посте использовался пользовательский эмодзи? Что возвращается, если запустить приведённый выше код для загрузки с этим ID загрузки? Также было бы полезно запустить это с записью о загрузке и вывести результат:
upload
.upload_references
.joins(<<~SQL)
LEFT JOIN posts ON upload_references.target_type = 'Post' AND upload_references.target_id = posts.id
SQL
.where("posts.deleted_at IS NULL")
.order("upload_references.created_at ASC, upload_references.id ASC")
.first
Если нам действительно это нужно, вы можете просто установить дату и время created_at для записи UploadReferenceCustomEmoji на время раньше, чем у любых других записей UploadReference для этой загрузки, но вам не должно приходится этого делать.
Я должен был уточнить. Идентификатор загрузки был верным, а идентификатор поста — нет (именно поэтому пост не содержал эмодзи: тот, который я вставил сюда, был правильным, но я ошибся при вводе, пытаясь его найти).
Все остальные команды по-прежнему возвращают то же самое.
И проблема должна быть решена… Я действительно думаю, что это будет в основном проблемой для более старых загрузок после этой миграции. Ещё один вариант, который вы можете попробовать, — удалить пользовательский эмодзи, загрузить его заново, а затем выполнить: