Я фронтендер, в Rails захожу со стороны Stimulus. Rails 8.0, Turbo 8, включили морфинг, чтобы список задач обновлялся у всех, когда кто-то добавляет новую: в модели broadcasts_refreshes, в layout turbo_refreshes_with method: :morph. Обновляется красиво, но если у человека в этот момент открыт выпадающий фильтр, он закрывается, а набранный текст в поиске пропадает. Как сохранить состояние?
Элементы, которые морфинг не должен трогать, помечают data-turbo-permanent, и у них обязательно должен быть стабильный id:
<%= turbo_refreshes_with method: :morph, scroll: :preserve %>
<div id="task-filters" data-turbo-permanent>
<%= render "filters" %>
</div>
Без scroll: :preserve прокрутка ещё и прыгает наверх при каждом обновлении. Только учти, что permanent-блок не обновится вообще, даже если на сервере в фильтрах что-то поменялось. И проверь, что id правда стабильный: если он собирается из случайного числа или object_id, при каждом обновлении он новый и permanent молча не работает.
Если фильтр сделан на элементе details и нужно сохранить только его открытость, можно точечнее: отменять морфинг одного атрибута.
document.addEventListener("turbo:before-morph-attribute", (event) => {
if (event.target.matches("details.filters") && event.detail.attributeName === "open") {
event.preventDefault()
}
})
Остальное содержимое фильтра при этом обновляется как обычно.
а текст поиска можно держать в параметрах адреса, через GET-форму. Тогда после refresh сервер сам подставит его обратно в поле