So, I have a turbo frame in the show view of my Rental:
views/rentals/show.html.erb
<%= turbo_frame_tag "new_rate", src: new_rental_rate_path(@rental) %>
<div id="rates<%= year %>">
<%= render @rates.where("DATE_PART('year', firstnight) = ?", year) %>
</div>
views/rates/new.html.erb
<%= turbo_frame_tag "new_rate", do %>
<%= render "form", rate: @rate, vrental: @vrental %>
<% end %>
views/rates/form.html.erb
<%= simple_form_for [vrental, rate], id: dom_id(rate, "form") do |f| %>
controllers/rates_controller.rb
def create
@rate = Rate.new(rate_params)
@rate.rental = @rental
if @rate.save
flash.now[:notice] = "You've created a new rate."
render turbo_stream: [
turbo_stream.prepend("rates#{@rate.firstnight.year}", @rate),
turbo_stream.replace("new_rate", partial: "form", locals: { rate: Rate.new }),
turbo_stream.replace("notice", partial: "shared/flashes"),
]
else
render :new, status: :unprocessable_entity
end
end
So, here's the problem.
On page load, the new rate form is correctly rendered inside a turbo frame:
<turbo-frame id="new_rate" src="http://localhost:3000/rentals/1/rates/new" complete="">
<form id="new_rate" [...]>
</form>
</turbo-frame>
However, after submitting and correctly saving the first rate, the form is then displayed outside the turbo frame:
<form id="new_rate" [...]>
</form>
I can see that it's happening because I'm replacing the div with "new form" id by partial: "form", which is not wrapped in a turbo frame, but I can't figure out how to fix it..
CodePudding user response:
The most simplistic solve for this is to add a partial that loads the form. but to keep it DRY, make sure to render that partial from within your new.html.erb
file.
Practically, it will look like this.
views/rates/new.html.erb
<%= render "new" %>
views/rates/_new.html.erb
<%= turbo_frame_tag "new_rate", do %>
<%= render "form", rate: @rate, vrental: @vrental %>
<% end %>
app/controllers/rates_controller.rb
def create
@rate = Rate.new(rate_params)
@rate.rental = @rental
if @rate.save
flash.now[:notice] = "You've created a new rate."
render turbo_stream: [
turbo_stream.prepend("rates#{@rate.firstnight.year}", @rate),
turbo_stream.replace("new_rate", partial: "new", locals: { rate: Rate.new }),
turbo_stream.replace("notice", partial: "shared/flashes"),
]
else
render :new, status: :unprocessable_entity
end
end