How to call expire_fragment from Rails Observer/Mo

2019-01-30 14:50发布

I've pretty much tried everything, but it seems impossible to use expire_fragment from models? I know you're not supposed to and it's non-MVC, but surely there much be some way to do it.

I created a module in lib/cache_helper.rb with all my expire helpers, within each are just a bunch of expire_fragment calls. I have all my cache sweepers setup under /app/sweepers and have an "include CacheHelper" in my application controller so expiring cache within the app when called via controllers works fine.

Then things is I have some external daemons and especially some recurring cron tasks which call a rake task that calls a certain method. This method does some processing and inputs entries into the model, after which I need to expire cache.

What's the best way to do this as I can't specify cache sweeper within the model. Straight up observers seem to be the best solution but then it complains about expire_fragment being undefined etc etc, I've even tried including the ActionController caching classes into the observer but that didn't work. I'd love some ideas of how to create a solution for this. Thanks.

8条回答
等我变得足够好
2楼-- · 2019-01-30 15:50

I'm a bit of a rails noob, so this may not be correct, or even helpful, but it seems wrong to be trying to call controller actions from within the model.

Is it not possible to write an action within the controller that does what you want and then invoke the controller action from within your rake task?

查看更多
We Are One
3楼-- · 2019-01-30 15:54

The solution provided by Orion works perfectly. As an enhancement and for convenience, I've put the following code into config/initializers/active_record_expire_fragment.rb

class ActiveRecord::Base
  def expire_fragment(*args)
    ActionController::Base.new.expire_fragment(*args)
  end
end

Now, you can use expire_fragment on all instances of ActiveRecord::Base, e.g. User.first.expire_fragment('user-stats')

查看更多
登录 后发表回答