Rendering simple_calendar content using Turbo Frames
Hi there,
It's a great pleasure to use this gem which is really handy ! I started using Turbo recently on my application and still had troubles wrapping my head around... Idea here is not only to get things working, but having a better understanding of how Turbo works.
As per the documentation, it says "if you are using Hotwire, just wrap in a Turbo Frame", which is what I did:
# app/views/calendars/index.html.erb
<%= turbo_frame_tag 'calendar' do %>
<%= month_calendar(events: @events, attribute: :start_date, end_attribute: :end_date) do |date, events| %>
<div class='d-flex justify-content-end'><%= date.day %></div>
<div class='mb-5'>
<%= render partial: 'events/calendar_event', collection: events, as: :event %>
</div>
<% end %>
<% end %>
But I still got Processing by CalendarsController#index as HTML
...
Is that because I'm using
simple_calendar
on@events
within aCalendar
view ?Shouldn't 'Previous' and 'Next' links be aware of which
turbo-frame
to replace ?Will my instance variables be redefined in my CalendarController#index ? (I guess it'll, that's kind of a stupid question)
EDIT 1: Tried to set a format.turbo_stream
inside CalendarController#index
rendering a partial containing a turbo_frame_tag, without result
EDIT 2: Tried to add a data-turbo-action: replace
to navigation links, without result
EDIT 3: When using <%= turbo_frame_tag 'calendar' do %>
backend sends me the HTML portion of app/views/calendars/index.html.erb
. When omitting that tag, backend sends me the whole page (include navbar and so on). Server logs does not indicate request is processed as TURBO_STREAM, but it looks to me that it is...
EDIT 4: Let's be more precise:
My Calendar#index
action renders a view containing 3 parts: a sidebar, the actual calendar, and a modal template.
# app/views/calendars/index.html.erb
<div class='row'>
<div class='col-2'>
<%= render partial: 'calendars_sidebar', collection: @calendars, as: :calendar %>
<hr class='text-white'>
<%= render partial: 'form', locals: { calendar: @calendar} %>
</div>
<div class='col-10'>
<%= render partial: 'calendars/calendar' %>
</div>
<div id='add-event-modal-placeholder'>
<%= render partial: 'events/add_event_modal' %>
</div>
</div>
The goal to me is that when a user clicks 'Previous' or 'Next', only the calendar is actualized. I used a turbo_frame_tag
block to do this:
# app/views/calendars/_calendar.html.erb
<%= turbo_frame_tag 'calendar' do %>
<%= month_calendar(events: @events, attribute: :start_date, end_attribute: :end_date) do |date, events| %>
<div class='d-flex justify-content-end'><%= date.day %></div>
<div class='mb-5'>
<%= render partial: 'events/calendar_event', collection: events, as: :event %>
</div>
<% end %>
<% end %>
And set the corresponding controller's format (which I believe isn't required)
# app/controller/calendars_controller.rb
respond_to do |format|
format.turbo_stream
format.html
end
However, according to the logs, the page is processed as HTML:
Processing by CalendarsController#index as HTML
Parameters: {"start_date"=>"2022-03-07"}
...
And here's the HTML returned (shorten):
<div class='row'>
<div class='col-2'>
<!-- CALENDAR SIDEBAR -->
</div>
<div class='col-10'>
<turbo-frame id="calendar">
<!-- CONTENT OF THE CALENDAR (each days + events) -->
</turbo-frame>
</div>
<div id='add-event-modal-placeholder'>
<!-- MODAL TEMPLATE OMITTED -->
</div>
</div>
</div>
Which does only contain the HTML corresponding to the index action (does not includes the navbar). Though, it contains the sidebar and the modal template...
Question is, how to replace only the calendar's turbo-frame instead of the whole #index action ?
btw, here's a development demo of the application: https://open-calendar-dev.herokuapp.com/
Credentials are "foo@bar.com" / "foobar" (and will change at some point)
And here's the forge repository: https://gitlab.com/kawsay/open_calendar
(Anyone is welcome to join :) )
Did you ever get this working? I am working on something similar and would love for hotwire to update the events in the calendar.