0
votes

I'm following the #322 RailsCasts and in the last part he comments a way to embebed json into html

<div id="articles" data-articles="<%= render(template: "articles/index.json.rabl") %>" >

In my project I have a rabl template: app/views/places/show.json.rabl

object  @place
attributes :id, :name, :desc, :address
node(:type) { |place| place.type_place.name }
child :photos do 
  attributes :id, :desc
  node(:url) { |photo| photo.image.url(:square) }
end

If I render /places/21.json it shows:

{"id":21,"name":"foo","desc":"bar","address":"some address","type":"baz",
 "photos":[{"id":26,"desc":"foofoo","url":"/uploads/photo/image/26/square_conmemorativo-1920x1080.jpg"}]}

well it's working but if I try to embebed json data into html I'm doing this:

<article id="show_place" data-place="<%= render(template: "places/#{@place.id}.json.rabl") %>" >

error log

Missing template places/21.json with {:locale=>[:en], :formats=>[:html], :handlers=>[:erb, :builder, :coffee, :rabl]}. Searched in: * "/home/ed/projects/rails_projects/final_u/app/views"

What Am I doing wrong?

UPDATE

I just found the solution

<article id="show_place" data-place="<%= render(template: "places/show.json.rabl") %>" >

And it works but I don't know why.. and here I have another question

There is a way to pass a single object to the render(template: "") ??

Thanks in advance.... and sorry for my English

1

1 Answers

0
votes

The reason behind this is convention for render. The function expects the template itself to render, not the route (which is what you're typing into your URL bar).

If you enter /places/21.json into your URL bar in your browser, it will call the places controller with the parameters of id = 21 and format = json. It will then render the appropriately named view (Which in this case will be your RABL template) at the end of the function defined in your controller. That template then renders it's data from the value of the @place variable defined on the first line.

I'm assuming your controller sets the @place variable with params[:id] or something similar.

When you call render you are essentially manually doing the last part that the controller function automatically does for you: Displaying a template. You then should specify what template you wish to render, making sure any variables are set before hand.

So the reason why places/show.json.rabl works is simply because you are rendering the appropriately named template. This will render the show template under your places folder inside views. It will then use the @place variable I assume you've defined in earlier in your controller or view.

TL;DR
You did the right thing at the end by rendering the template. You can render a different object by changing the variable the template uses on it's first line.