Вещание на несколько турбо-потоков с помощью hotwire

Я правильно подключил hotwire / turbo, чтобы выполнять грубые операции на одной модели в одном месте моей страницы, но я хотел бы обновить ту же модель одновременно в другом месте на моей странице. Я думал, что могу просто настроить два потока, но это не работает.

Указание цели действительно работает для действия create в зависимости от того, как я называю цель, но не для обновления и уничтожения. Это то, что я думаю, должно работать, но не работает:

---- место 1 (поток "существ") ----

      <div id="creatures">
  <%= turbo_stream_from "creatures" %>
  <%= turbo_frame_tag "creatures" do %>
    <div>
      <% @creatures.each do |creature| %>
        <div>
          <%= render "creatures/creature", creature: creature %>
        </div>
      <% end %>
    </div>
  <% end %>
</div>

---- место 2 (поток "creatures_main") ----

      <%= turbo_stream_from "creatures_main" %>
<%= turbo_frame_tag "creatures_main" do %>
  <% @creatures.each do |creature| %>
    <div>
      <%= render "creatures/creature", creature: creature %>
    </div>
  <% end %>
<% end %>

---- common _creature.html.erb частичный ----

      <%= turbo_frame_tag dom_id(creature) do %>
  <%= link_to creature.name, "#" %>
<% end %>

---- creature.rb ----

      class Creature < ApplicationRecord
  validates :name, presence: true

  after_create_commit {
    broadcast_append_to "creatures"
    broadcast_append_to "creatures_main"
    }
  after_update_commit {
    broadcast_replace_to "creatures"
    broadcast_replace_to "creatures_main"
    }
  after_destroy_commit {
    broadcast_remove_to "creatures"
    broadcast_remove_to "creatures_main"
    }

end

Что происходит, когда у меня есть два вызова в моей модели, так это то, что действие create помещает вновь созданное существо в местоположение 1 дважды, только одно из двух обновляется, но оба уничтожаются правильно независимо от того, где они находятся на странице.

1 ответ

creatures а также creatures_mainбудет именем потока. Вы ищете target а также partial чтобы контролировать, где поток будет искать для обновления ваших данных и какую часть он будет использовать для обновления.

Можешь попробовать:

      after_create_commit -> {
  # target here is the ID of the outer div, where data would be appended to
  broadcast_append_to "creatures", target: "creatures"`
  broadcast_append_to "creatures_main", target: "creatures_main"
}
after_update_commit {
  # target here is the ID of each of the creature div
  broadcast_replace_to "creatures", target: "creature_#{id}"
  broadcast_replace_to "creatures_main", target: "creature_main_#{id}"
}
after_destroy_commit {
  broadcast_remove_to "creatures"
  broadcast_remove_to "creatures_main"
}
      <%= turbo_frame_tag "creature_#{creature.id}" do %>
  <%= link_to creature.name, "#" %>
<% end %>

<%= turbo_frame_tag "creature_main_#{creature.id}" do %>
  <%= link_to creature.name, "#" %>
<% end %>

Конечно, это означает, что вам, возможно, придется использовать 2 разных партиала, если у вас есть turbo_frame_tagвнутри частичного. Сделать это можно так:

      after_update_commit {
  # target here is the ID of each of the creature div
  broadcast_replace_to "creatures", target: "creature_#{id}", partial: "creatures/creature", locals: {creature: self}
  broadcast_replace_to "creatures_main", target: "creature_main_#{id}", partial: "creatures/creature_main", locals: {creature: self}
}

Кстати, вы должны использовать _ более позднюю версию этих методов. Также используйте коллекцию рендеров для облегчения чтения.

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