I'm generating a small form through render_to_string
and for some reason the CSRF token is not being generated correctly (i.e. it's different from the header and the user is logged out on submit, along with a "Can't verify CSRF token" on the logs). Here's the relevant code:
Controller:
def publish
@question = @event.questions.find(params[:id])
@question.update_attribute(:published, true) unless @question.published?
Pusher[@event.to_param].trigger('new_question', question: render_question)
redirect_to event_path(@event)
end
private
def render_question
render_to_string('questions/_unanswered_question', locals: {question: @question}, layout: false)
end
def fetch_event
@event ||= current_user.events.find(params[:event_id])
end
I'm using Pusher, but you can assume this is just being rendered on the page with this Javascript:
$("#questions").append(data.question); // data is what I send from Pusher.
And finally, the partial being rendered:
.answer
= form_for [@event, question, question.answers.new] do |f|
%h2
= question.title
%ul
- (1..5).each do |n|
- if question.send("answer_#{n}").present?
%li
= f.radio_button :option, n, id: "q_#{question.id}_answer_option_#{n}"
= f.label question.send("answer_#{n}"), for: "q_#{question.id}_answer_option_#{n}"
%p
= f.submit "Answer"
This works just fine without being appended to the page, but rendered within the layout. Note that this is not a remote form.
It looks like you are generating the form using ajax and then adding it to the Dom. The csrf token is generated new for every request. As far as I know, you have to use the csrf token which is available in the header and replace the one in the form with it using js.
Should look something like this:
Currently I have no computer to test that first, so hopefully I am right :/