Рефакторинг Turbolinks и Pagy's Infinite Scroll для работы с Turbo

В настоящее время я перевожу приложение с Turbolinks на Turbo.

Я изо всех сил пытаюсь найти лучший способ перенести общий шаблон, который у меня есть в моей текущей настройке Turbolinks:

  • У меня установлена ​​бесконечная прокрутка с помощью драгоценного камня Pagy, и он захватывает следующую страницу через запрос
  • У меня есть много меню фильтров, которые фильтруют результаты через форму, используя method: :get, отвечая format.js
  • После нажатия кнопки фильтра отфильтрованные результаты с разбивкой на страницы заменяют текущий набор, а прокрутка вниз запускает ответ, который добавляет новые записи, обновляет div и запускает несколько других изменений DOM.

При миграции:

  • Чтобы формы работали с Turbo, мне пришлось изменить их так, чтобы они отправлялись через запрос и отвечали format.turbo_stream
  • В turbo-stream response обновляет целевой div с первой страницей результатов и обновленным div
  • Теперь бесконечная прокрутка не работает с ошибками 404, потому что маршрута больше не существует.

Вот что мне нужно:

  • Когда я нажимаю, чтобы отфильтровать список, возвращается первая страница результатов, а div обновляется для загрузки второй страницы.
  • Прокрутка вниз в конечном итоге приводит к тому, что вторая страница добавляется к первой странице, текущая infinite-scroll Затем div удаляется и обновляется или заменяется одним для третьей страницы.

Каким будет идиоматический способ сделать это с помощью Pagy и Hotwire?

Есть ли способ запустить контроллер Stimulus после того, как мой контроллер Rails завершил обработку? Если есть, я мог бы просто перенести уже имеющийся у меня JS, который хорошо работает.

Вот общая настройка моего кода прямо сейчас:

Во-первых, у меня есть бесконечная прокрутка, настроенная для всего сайта через JS, например:

      $(document).on('turbo:load', function() {
  var isLoading = false
  if ($('#infinite-scroll', this).size() > 0) {
    $(window).on('scroll', function() {
      var more_posts_url = $('.page.next a').attr('href');
      var threshold_passed = $(window).scrollTop() > $(document).height() - $(window).height() - 200;
      if (!isLoading && more_posts_url && threshold_passed) {
        isLoading = true;
        $('.page.next').html('<%= image_tag("loading-more-books.gif", alt: "Loading...", title: "Loading...") %>')
        $.getScript(more_posts_url).done(function (data,textStatus,jqxhr) {
          isLoading = false;
        }).fail(function() {
          isLoading = false;
        });
      }
    });
  }
});

В целом страницы просмотра индекса выглядят следующим образом:

          <div class="posts">
      <div class="posts-panes">
        <% @posts.each do |post| %>
          <%= render post %>
        <% end %>
      </div>
      <div id="infinite-scroll">
        <%== pagy_next_link(@pagy, 'More...', 'id="next_link"') %>
      </div>
    </div>

И блок для index действие в контроллере выглядит так:

          respond_to do |format|
      format.html
      format.js
    end

В index.js вид бывают так:

      $('.posts-panes').append("<%= j render @posts %>");
<% if pagy_next_url(@pagy) %>
    $('.page.next').replaceWith('<%== j pagy_next_link(@pagy, 'More...', 'id="next_link"') %>');
<% else %>
    $(window).off('scroll');
    $('.page.next').remove();
<% end %>

Для каждого представления индекса есть форма фильтра, которая через GET, фильтрует записи.

Блоки для методов фильтрации выглядят так:

          respond_to do |format|
      format.js
    end

И js просмотры выглядят примерно так:

        ...

  $('.posts-panes').append("<%= j render @posts %>");
  $('#infinite-scroll').replaceWith('<div id=\"infinite-scroll\"><%== j pagy_next_link(@pagy, 'id="next_link"') %></div>');

<% if pagy_next_url(@pagy) %>
  $('.page.next').replaceWith('<%== j pagy_next_link(@pagy, 'more...', 'id="next_link"') %>');
<% else %>
  $(window).off('scroll');
  $('.page.next').remove();
<% end %>

До сих пор я обновил действие фильтра, чтобы оно стало POST запрос (чтобы он работал с Турбо), а теперь respond_to блоки для методов фильтрации читаются следующим образом:

          respond_to do |format|
      format.turbo_stream
    end

Представления turbo_stream выглядят так:

      <turbo-stream action="append" target="posts-panes">
  <template>
    <%= render partial:'posts/post', collection: @posts, as: :post, formats: [:html] %>
  </template>
</turbo-stream>

Я могу успешно вернуть первую страницу записей - все подключено правильно - но я изо всех сил пытаюсь подключить Pagy.

Каким будет лучший способ рефакторинга / перенастройки моего существующего кода, чтобы у меня был шаблон, который я мог бы использовать во всех моих представлениях и контроллерах?

Большое спасибо!

0 ответов

Другие вопросы по тегам