操作缓存没有正确过期,即使我可以看到它正在被调用
我有一个清理器,它应该会使一些操作缓存过期。尽管调试器在调用 expire_action 之前立即停止,但它实际上并未使操作过期。知道会发生什么吗?
下面是相关的扫地机和控制器。
#company_sweeper.rb (在“models”目录中)
class CompanySweeper < ActionController::Caching::Sweeper
observe Company
def after_save(company)
expire_cache(company) if company.final_save && company.valid?
end
def expire_cache(company)
debugger <= #debugger stops here!
right before the call
I'm trying to make.
expire_action :controller => 'reports',
:action => 'full_report'
end
end
#reports_controller.rb
class ReportsController < ApplicationController
layout false
caches_action :full_report, :supplier_list, :service_categories
cache_sweeper :company_sweeper
def full_report
#do stuff...
end
end
我知道它没有过期的方式是完整报告返回旧数据,并且几乎立即响应。很奇怪,对吧?
I've got a sweeper that's supposed to expire a few action caches. Even though the debugger stops immediately before the call to expire_action, it's not actually expiring the action. Any idea what could be going on?
Here are the relevant sweeper and controller.
#company_sweeper.rb (in 'models' directory)
class CompanySweeper < ActionController::Caching::Sweeper
observe Company
def after_save(company)
expire_cache(company) if company.final_save && company.valid?
end
def expire_cache(company)
debugger <= #debugger stops here!
right before the call
I'm trying to make.
expire_action :controller => 'reports',
:action => 'full_report'
end
end
#reports_controller.rb
class ReportsController < ApplicationController
layout false
caches_action :full_report, :supplier_list, :service_categories
cache_sweeper :company_sweeper
def full_report
#do stuff...
end
end
The way I know it's not expiring is that the full report returns old data, and responds nearly instantaneously. Weird, right?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
您的 CompaniesController 中是否也有
cache_sweeper
声明?清理器必须包含在对相关模型执行生命周期操作的控制器中。除非您在 ReportsController 中使用 Company 实例进行操作,否则cache_sweeper
行不属于那里。操作缓存包含隐式主机名。如果两次命中来自不同的主机名,则在一个主机名下进行缓存,并在另一个主机名下进行过期。
Do you have a
cache_sweeper
declaration in your CompaniesController, too? The sweeper must be included in the controller that performs lifecycle actions on the model in question. Unless you do things with Company instances in ReportsController, thecache_sweeper
line doesn't belong there.Action caching includes an implicit host name. If the two hits are coming in on different host names, caching is done under one and expiration under a different one.
我认为这里没有足够的细节来真正回答您的问题,但这里有一些问题:
清理器应该独立于 full_report 操作触发,因此如果您对公司进行更改,您应该看到调试器触发(看起来正在正确发生)。然后,您不需要运行 full_report 操作,因此此时您可以验证缓存的文件是否已被删除。在调试器中单步执行expire_action以查看rails是否由于其他原因跳过到期可能很有用。
编辑:
哦,你知道吗,我只是在深入研究这个问题,看起来expire_action应该在控制器的上下文中运行(我正在阅读actionpack中的gem源代码)。它假设“self”是一个控制器,因此您传入的选项 :controller 将被忽略。
其他示例给出了特定的字符串而不是选项(例如
expire_action'/reports/full_report'
)我个人不喜欢这样——它没有使用路由器——但看起来它会工作。也许您应该切换到该方法,确保它有效,然后在调试器中查看您是否有权访问 url_for。它可以像expire_action url_for(:controller => 'reports', :action => 'full_report')一样简单
I don't think there are enough details here to really answer your question, but here are some questions:
The sweeper should fire independently from the full_report action, so if you make a change to a Company, you should see the debugger fire (which it looks like is happening correctly). You don't then need to run the full_report action, so at this point you could verify the cached file has been removed. It could be useful to step through expire_action in the debugger to see if rails is skipping the expiry for some other reason.
EDIT:
oh you know what, I was just diggging into this, and it looks like expire_action is expected to run in a controller's context (I was reading the gem source in actionpack). It assumes 'self' is a controller, so your passing in the option :controller is being ignored.
Other examples give a specific string instead of options (e.g.
expire_action '/reports/full_report'
) I don't like that personally---it's not using the router---but it seems like it would work.Perhaps you should switch to that method, ensure it works, and then in the debugger see if you have access to url_for. it could be as simple as
expire_action url_for(:controller => 'reports', :action => 'full_report')