spree / deface

Rails plugin that allows you to customize ERB views in a Rails application without editing the underlying view.
MIT License
519 stars 128 forks source link

Deface + cache = undefined method 'html_safe' for nil:NilClass #118

Open jagthedrummer opened 10 years ago

jagthedrummer commented 10 years ago

I'm trying to implement Russian doll style fragment caching in my Spree app. In general this works really well, but I'm running into problems when I have a Deface override that tries to alter something inside of a <% cache ... %> block.

For example, I'm trying to use the spree_wishlist gem, which contains this override:

Deface::Override.new(:virtual_path => "spree/products/show",
                 :name => "add_wish_to_cart_form",
                 :insert_bottom => "[data-hook='cart_form']",
                 :partial => "spree/products/wishlist_form",
                 :disabled => false)

I have a custom version of views/spree/products/show.html.erb that looks something like this:

<% cache @product %>
  ...
  <div id="cart-form" class="productcontrols" data-hook="cart_form">
  ...
  </div>
  ...
<% end %>

If I comment out the override in the spree_wishlist gem then the products/show pages will load. OR if I uncomment the override code, but remove the cache block the products/show pages will also load. With both the override in place and the cache block present I get the following stack trace. Is there a way to use Deface and fragment caching together?

undefined method `html_safe' for nil:NilClass

Extracted source (around line #35):

32:     
33:           <div id="content" class='span<%= !content_for?(:sidebar) ? "12" : "12" %>' data-hook>
34:             <%= flash_messages %>
35:               <%= yield %>
36:             </div>
37:         </div>
38:       <%= render :partial => 'spree/shared/footer' %>

actionpack (3.2.14) lib/action_view/context.rb:33:in `_layout_for'
actionpack (3.2.14) lib/action_view/helpers/rendering_helper.rb:85:in `_layout_for'
actionpack (3.2.14) lib/action_view/renderer/template_renderer.rb:60:in `block in render_with_layout'
app/views/spree/layouts/spree_application.html.erb:35:in `_eb080df772ab9364a400bc46c4887e0e'
actionpack (3.2.14) lib/action_view/template.rb:145:in `block in render'
activesupport (3.2.14) lib/active_support/notifications.rb:125:in `instrument'
actionpack (3.2.14) lib/action_view/template.rb:143:in `render'
deface (0.9.1) lib/deface/action_view_extensions.rb:37:in `render'
actionpack (3.2.14) lib/action_view/renderer/template_renderer.rb:60:in `render_with_layout'
actionpack (3.2.14) lib/action_view/renderer/template_renderer.rb:46:in `render_template'
actionpack (3.2.14) lib/action_view/renderer/template_renderer.rb:19:in `render'
newrelic_rpm (3.6.6.147) lib/new_relic/agent/instrumentation/rails3/action_controller.rb:160:in `block in render_with_newrelic'
newrelic_rpm (3.6.6.147) lib/new_relic/agent/method_tracer.rb:268:in `trace_execution_scoped'
newrelic_rpm (3.6.6.147) lib/new_relic/agent/instrumentation/rails3/action_controller.rb:159:in `render_with_newrelic'
actionpack (3.2.14) lib/action_view/renderer/renderer.rb:36:in `render_template'
actionpack (3.2.14) lib/action_view/renderer/renderer.rb:17:in `render'
actionpack (3.2.14) lib/abstract_controller/rendering.rb:110:in `_render_template'
actionpack (3.2.14) lib/action_controller/metal/streaming.rb:225:in `_render_template'
actionpack (3.2.14) lib/abstract_controller/rendering.rb:103:in `render_to_body'
actionpack (3.2.14) lib/action_controller/metal/renderers.rb:28:in `render_to_body'
actionpack (3.2.14) lib/action_controller/metal/compatibility.rb:50:in `render_to_body'
actionpack (3.2.14) lib/abstract_controller/rendering.rb:88:in `render'
actionpack (3.2.14) lib/action_controller/metal/rendering.rb:16:in `render'
actionpack (3.2.14) lib/action_controller/metal/instrumentation.rb:40:in `block (2 levels) in render'
activesupport (3.2.14) lib/active_support/core_ext/benchmark.rb:5:in `block in ms'
/Users/jgreen/.rvm/rubies/ruby-1.9.3-p392/lib/ruby/1.9.1/benchmark.rb:295:in `realtime'
activesupport (3.2.14) lib/active_support/core_ext/benchmark.rb:5:in `ms'
actionpack (3.2.14) lib/action_controller/metal/instrumentation.rb:40:in `block in render'
actionpack (3.2.14) lib/action_controller/metal/instrumentation.rb:83:in `cleanup_view_runtime'
activerecord (3.2.14) lib/active_record/railties/controller_runtime.rb:24:in `cleanup_view_runtime'
sunspot_rails (2.0.0) lib/sunspot/rails/railties/controller_runtime.rb:15:in `cleanup_view_runtime'
actionpack (3.2.14) lib/action_controller/metal/instrumentation.rb:39:in `render'
actionpack (3.2.14) lib/action_controller/metal/implicit_render.rb:10:in `default_render'
actionpack (3.2.14) lib/action_controller/metal/implicit_render.rb:5:in `send_action'
actionpack (3.2.14) lib/abstract_controller/base.rb:167:in `process_action'
actionpack (3.2.14) lib/action_controller/metal/rendering.rb:10:in `process_action'
actionpack (3.2.14) lib/abstract_controller/callbacks.rb:18:in `block in process_action'
activesupport (3.2.14) lib/active_support/callbacks.rb:502:in `_run__4325172496887106903__process_action__4015572256807538231__callbacks'
activesupport (3.2.14) lib/active_support/callbacks.rb:405:in `__run_callback'
activesupport (3.2.14) lib/active_support/callbacks.rb:385:in `_run_process_action_callbacks'
activesupport (3.2.14) lib/active_support/callbacks.rb:81:in `run_callbacks'
actionpack (3.2.14) lib/abstract_controller/callbacks.rb:17:in `process_action'
actionpack (3.2.14) lib/action_controller/metal/rescue.rb:29:in `process_action'
actionpack (3.2.14) lib/action_controller/metal/instrumentation.rb:30:in `block in process_action'
activesupport (3.2.14) lib/active_support/notifications.rb:123:in `block in instrument'
activesupport (3.2.14) lib/active_support/notifications/instrumenter.rb:20:in `instrument'
activesupport (3.2.14) lib/active_support/notifications.rb:123:in `instrument'
actionpack (3.2.14) lib/action_controller/metal/instrumentation.rb:29:in `process_action'
actionpack (3.2.14) lib/action_controller/metal/params_wrapper.rb:207:in `process_action'
activerecord (3.2.14) lib/active_record/railties/controller_runtime.rb:18:in `process_action'
newrelic_rpm (3.6.6.147) lib/new_relic/agent/instrumentation/rails3/action_controller.rb:38:in `block in process_action'
newrelic_rpm (3.6.6.147) lib/new_relic/agent/instrumentation/controller_instrumentation.rb:318:in `perform_action_with_newrelic_trace'
newrelic_rpm (3.6.6.147) lib/new_relic/agent/instrumentation/rails3/action_controller.rb:37:in `process_action'
actionpack (3.2.14) lib/abstract_controller/base.rb:121:in `process'
actionpack (3.2.14) lib/abstract_controller/rendering.rb:45:in `process'
actionpack (3.2.14) lib/action_controller/metal.rb:203:in `dispatch'
actionpack (3.2.14) lib/action_controller/metal/rack_delegation.rb:14:in `dispatch'
actionpack (3.2.14) lib/action_controller/metal.rb:246:in `block in action'
actionpack (3.2.14) lib/action_dispatch/routing/route_set.rb:73:in `call'
actionpack (3.2.14) lib/action_dispatch/routing/route_set.rb:73:in `dispatch'
actionpack (3.2.14) lib/action_dispatch/routing/route_set.rb:36:in `call'
journey (1.0.4) lib/journey/router.rb:68:in `block in call'
journey (1.0.4) lib/journey/router.rb:56:in `each'
journey (1.0.4) lib/journey/router.rb:56:in `call'
actionpack (3.2.14) lib/action_dispatch/routing/route_set.rb:608:in `call'
railties (3.2.14) lib/rails/engine.rb:484:in `call'
railties (3.2.14) lib/rails/railtie/configurable.rb:30:in `method_missing'
journey (1.0.4) lib/journey/router.rb:68:in `block in call'
journey (1.0.4) lib/journey/router.rb:56:in `each'
journey (1.0.4) lib/journey/router.rb:56:in `call'
actionpack (3.2.14) lib/action_dispatch/routing/route_set.rb:608:in `call'
omniauth (1.1.4) lib/omniauth/strategy.rb:184:in `call!'
omniauth (1.1.4) lib/omniauth/strategy.rb:164:in `call'
omniauth (1.1.4) lib/omniauth/strategy.rb:184:in `call!'
omniauth (1.1.4) lib/omniauth/strategy.rb:164:in `call'
omniauth (1.1.4) lib/omniauth/strategy.rb:184:in `call!'
omniauth (1.1.4) lib/omniauth/strategy.rb:164:in `call'
omniauth (1.1.4) lib/omniauth/strategy.rb:184:in `call!'
omniauth (1.1.4) lib/omniauth/strategy.rb:164:in `call'
app/middleware/spree_product_route.rb:17:in `call'
newrelic_rpm (3.6.6.147) lib/new_relic/rack/error_collector.rb:43:in `call'
newrelic_rpm (3.6.6.147) lib/new_relic/rack/agent_hooks.rb:22:in `call'
newrelic_rpm (3.6.6.147) lib/new_relic/rack/browser_monitoring.rb:16:in `call'
newrelic_rpm (3.6.6.147) lib/new_relic/rack/developer_mode.rb:28:in `call'
warden (1.2.3) lib/warden/manager.rb:35:in `block in call'
warden (1.2.3) lib/warden/manager.rb:34:in `catch'
warden (1.2.3) lib/warden/manager.rb:34:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/best_standards_support.rb:17:in `call'
rack (1.4.5) lib/rack/etag.rb:23:in `call'
rack (1.4.5) lib/rack/conditionalget.rb:25:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/head.rb:14:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/params_parser.rb:21:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/flash.rb:242:in `call'
rack (1.4.5) lib/rack/session/abstract/id.rb:210:in `context'
rack (1.4.5) lib/rack/session/abstract/id.rb:205:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/cookies.rb:341:in `call'
activerecord (3.2.14) lib/active_record/query_cache.rb:64:in `call'
activerecord (3.2.14) lib/active_record/connection_adapters/abstract/connection_pool.rb:479:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/callbacks.rb:28:in `block in call'
activesupport (3.2.14) lib/active_support/callbacks.rb:405:in `_run__399222298878305532__call__81867724251474373__callbacks'
activesupport (3.2.14) lib/active_support/callbacks.rb:405:in `__run_callback'
activesupport (3.2.14) lib/active_support/callbacks.rb:385:in `_run_call_callbacks'
activesupport (3.2.14) lib/active_support/callbacks.rb:81:in `run_callbacks'
actionpack (3.2.14) lib/action_dispatch/middleware/callbacks.rb:27:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/reloader.rb:65:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/remote_ip.rb:31:in `call'
/Users/jgreen/.rvm/gems/ruby-1.9.3-p392@kmree/bundler/gems/spree_redirects-2b638b8b4808/lib/spree_redirects/redirect_middleware.rb:13:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/debug_exceptions.rb:16:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/show_exceptions.rb:56:in `call'
railties (3.2.14) lib/rails/rack/logger.rb:32:in `call_app'
railties (3.2.14) lib/rails/rack/logger.rb:16:in `block in call'
activesupport (3.2.14) lib/active_support/tagged_logging.rb:22:in `tagged'
railties (3.2.14) lib/rails/rack/logger.rb:16:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/request_id.rb:22:in `call'
rack (1.4.5) lib/rack/methodoverride.rb:21:in `call'
rack (1.4.5) lib/rack/runtime.rb:17:in `call'
activesupport (3.2.14) lib/active_support/cache/strategy/local_cache.rb:72:in `call'
rack (1.4.5) lib/rack/lock.rb:15:in `call'
actionpack (3.2.14) lib/action_dispatch/middleware/static.rb:63:in `call'
railties (3.2.14) lib/rails/engine.rb:484:in `call'
railties (3.2.14) lib/rails/application.rb:231:in `call'
rack (1.4.5) lib/rack/content_length.rb:14:in `call'
railties (3.2.14) lib/rails/rack/log_tailer.rb:17:in `call'
rack (1.4.5) lib/rack/handler/webrick.rb:59:in `service'
/Users/jgreen/.rvm/rubies/ruby-1.9.3-p392/lib/ruby/1.9.1/webrick/httpserver.rb:138:in `service'
/Users/jgreen/.rvm/rubies/ruby-1.9.3-p392/lib/ruby/1.9.1/webrick/httpserver.rb:94:in `run'
/Users/jgreen/.rvm/rubies/ruby-1.9.3-p392/lib/ruby/1.9.1/webrick/server.rb:191:in `block in start_thread'
huoxito commented 10 years ago

hey @jagthedrummer thanks for the report interesting issue. Couldn't get that error yet though (I tried with spree_auth_device overrides) will try again with your spree wishlist example. Honestly I can't tell if deface works with rails cache out of the box but it sounds like something worth looking into.

radar commented 10 years ago

Hey @jagthedrummer, do you have an application which reproduces this problem? That'd be a great help.