leshill / handlebars_assets

Use handlebars.js templates with the Rails asset pipeline.
MIT License
648 stars 159 forks source link

How to use asset pipeline assets from within slimbars templates? #77

Closed pboling closed 11 years ago

pboling commented 11 years ago

I have a slimbars template like so:

li
  a.profile-button
    img src="/assets/profile.png"
    span.menu-link My Profile

This loads the asset from my rails server. I am deployed on Heroku, and push all my assets to S3, so the assets are available, and fingerprinted, on S3 by the asset pipeline, but I can't figure out how to use asset pipeline'd assets from within my templates.

This is my main template:

        ul.dropdown
          | {{> _menu_list_items }}

In the partial template I render image tags which I would like to server from S3. I tried adding a .erb on the end of the template and inserting it that way, but resulted in the template being inserted into my view as a giant slimbars string. It was processed by erb, but that prevented the processing by slim.

Here is the partial:

li
  a.profile-button
    img src="<%= asset_path('/assets/profile.png') %>"
    span.menu-link My Profile

became the following in the final DOM (local, so not hitting S3, but it did evaluate the asset_path:

<ul class="dropdown">li
  a.profile-button
    img src="/assets/profile.png"
    span.menu-link My Profile
</ul>

Hoping I missed something obvious, because it seems like this would be a common need, yet I haven't been able to find anything by googling.

leshill commented 11 years ago

Hi @pboling,

The usual way this is done in haml would be something like:

img{src: asset_path('blah')}

Does slim support a similar syntax?

pboling commented 11 years ago

Yeah, it is actually just like Ruby string interpolation:

img.love src="#{image_path('landing/heart@2x.png')}" height="25" width="25" alt=""

Not sure if I've tried that...

pboling commented 11 years ago

It doesn't work. asset_path is not a defined method in whatever scope handlebars or slim is evaluating this:

Uncaught Error: NoMethodError: undefined method `asset_path' for #<Object:0x007f93a4ba1d20>
  (in /Users/pboling/Documents/RubyMineProjects/simple/app/assets/javascripts/templates/_menu_list_items.slimbars) 

Same result with image_url. Does this actually work with the Haml engine? I may have to try switching to that for some views. Can I use both haml and slim in the same project?

pboling commented 11 years ago

Actually it looks like slim supports a very wide array of options for processing Ruby in the template. (Lots more here: http://rdoc.info/gems/slim/frames)

li
  a.profile-button
    img src=image_url('fake/bat_profile.jpeg')
    span.menu-link My Profile

... Yes, the same error.

pboling commented 11 years ago

Does it matter that my file is named .slimbars? Is there a different extension that exposes the template to more of the rails view helper methods? What would the extension be for haml - .hamlbars?

pboling commented 11 years ago

converting to hamlbars works as long as I don't use the asset pipeline helpers, like asset_path:

%li.feedback-nav{"data-type" => "feedback"}
  %a.feedback-button
    %img{:src => asset_path("/admin/charmander.jpg")}
    %span Feedback

still results in:

Uncaught Error: NoMethodError: undefined method `asset_path' for #<Object:0x007fef0e1ba198>
  (in /Users/pboling/Documents/RubyMineProjects/simple/app/assets/javascripts/templates/_menu_list_items_admin.hamlbars) 
pboling commented 11 years ago

I am working on my fork of this project, which there is a pull request for (which was for AMD compatibility, and is not yet ready to be merged) and I think perhaps I have broken something if this is supposed to work, and does work in master. I'll try your latest release.

pboling commented 11 years ago

I merged leshill/master into my branch, which I still have to use due to the AMD support, amazingly had no conflicts(!) and now get this error loading my site:

Uncaught Template was precompiled with an older version of Handlebars than the current runtime. Please update your precompiler to a newer version (>= 1.0.0) or downgrade your runtime to an older version (== 1.0.0-rc.3).

I am not sure what to make of that.

AlexRiedler commented 11 years ago

@pboling - It is probably due to a versioning issue of the Javascript Context. I had this happen when I loaded the runtime and the precompiler into the same context.

as for the asset-path issue, this is either caused by sprockets not having the helpers built into it's context (so you manually have to monkey patch them in); or the context which is passed in for slim evaluation is incorrect. I would have tried to point to your source; but is your fork private?

My steps to debugging:

pboling commented 11 years ago

@AlexRiedler: I forked it to my company's github: https://github.com/acquaintable/handlebars_assets

Thanks for the pointers, still feeling a bit lost. I am only using the handlebars vendored by handlebars_assets.

I had this happen when I loaded the runtime and the precompiler into the same context.

As far as I know I am not loading the "runtime" anywhere. If it is loading somehow, it is not intentional, nor do I think it is needed.

check if asset_path works in regular ".slim" files that are views (to verify the name asset_path)

Yes, they do work in regular slim views.

try to register ".slim" in the regular asset pipeline (verify compilation)

My slim templates are being compiled. The entire app uses slim, and all the parts of the app that are outside backbone are rendered in the normal rails fashion. No problems with slim anywhere but inside the require.js / handlebars.js / backbone.js setup.

register as slimbars (if this still fails it is probably context passing issue)

Do you mean use slimbars as an extension in my regular views and see if that works, outside the entire context of my javascript env?

pboling commented 11 years ago

@AlexRiedler also here is the AMD support pull request I mentioned.

pboling commented 11 years ago

I have merged the latest leshill/master into my AMD fork (acquaintable/amd) and am still getting the same error:

Uncaught Template was precompiled with an older version of Handlebars than the current runtime. Please update your precompiler to a newer version (>= 1.0.0) or downgrade your runtime to an older version (== 1.0.0-rc.3).

pboling commented 11 years ago

Hell yeah. Reading through other issues and found the rake tmp:clear solution. Worked for me! :)

leshill commented 11 years ago

Great!