Ruby 3.x下如何重写Pundit命名空间策略的authorize方法?
解决方案
1. 修复Ruby 3.x下关键字参数传递问题
原代码未适配Ruby 3.x中关键字参数与位置参数分离的特性,导致policy_class等选项被忽略。需重写authorize方法以捕获并传递关键字参数:
def authorize(record, query = nil, **kwargs) super([:admin, record], query, **kwargs) end
修改后,调用authorize时传入的policy_class等关键字参数会被正确传递给Pundit原生方法,不再被忽略。
2. 解决STI子类策略查找问题
方法一:显式指定policy_class(已修复)
现在关键字参数可正常传递,直接在调用authorize时指定父类策略即可:
@licensee = authorize Licensee.find(params[:id]), policy_class: Admin::LicenseePolicy
方法二:全局覆盖策略查找逻辑(可选)
若希望所有Licensee子类自动使用父类策略,可在AdminController中重写policy方法:
def policy(record) if record.is_a?(Licensee) Admin::LicenseePolicy.new(current_user, record) else super([:admin, record]) end end
此方式无需每次调用authorize都指定policy_class,Pundit会自动使用父类策略处理所有Licensee子类实例。
内容的提问来源于stack exchange,提问作者KenB
相关产品推荐
相关产品推荐

