【问题标题】:How can I DRY up Rails Controller cache_page if=>proc如果=>proc,我怎样才能干掉Rails Controller cache_page
【发布时间】:2014-02-03 19:09:46
【问题描述】:

不禁想到有一种方法可以稍微干掉这个 proc,但跨文件,但我有点像 ruby​​ n00b,我想从概念上讲,客观化/公开/引用 proc 仍然超出我的掌握.可行吗?

# controller_1.rb
caches_page :flu, :if => Proc.new{ |c| c.request.format && !c.request.format.json? && !is_google_bot? && flash[:notice].nil? && flash[:error].nil? }
caches_page :baz, :if => Proc.new{ |c| c.request.format && !c.request.format.json? && !is_google_bot? && flash[:notice].nil? && flash[:error].nil? }
# controller_2.rb
caches_page :foo, :if => Proc.new{ |c| c.request.format && !c.request.format.json? && !is_google_bot? && flash[:notice].nil? && flash[:error].nil? }
caches_page :bar, :if => Proc.new{ |c| c.request.format && !c.request.format.json? && !is_google_bot? && flash[:notice].nil? && flash[:error].nil? }

【问题讨论】:

    标签: ruby-on-rails ruby ruby-on-rails-3.2 proc actioncontroller


    【解决方案1】:

    首先,您可以向caches_page 添加多个操作。这将代码简化为:

    # controller_1.rb
    caches_page :flu, :baz, :if => Proc.new{ |c| c.request.format && !c.request.format.json? && !is_google_bot? && flash[:notice].nil? && flash[:error].nil? }
    
    # controller_2.rb
    caches_page :foo, :bar, :if => Proc.new{ |c| c.request.format && !c.request.format.json? && !is_google_bot? && flash[:notice].nil? && flash[:error].nil? }
    

    其次,你所有的控制器都应该继承自你的ApplicationController,因此你可以把这个方法放在那里:

    class ApplicationController < ActionController::Base
      #...
    
      private
    
      def should_cache_pages?
        request.format && request.format.json? && !is_google_bot? && flash[:notice].nil? && flash[:error].nil?
      end
    end
    

    这会将这些行简化为:

    # controller_1.rb
    caches_page :flu, :baz, if: :should_cache_pages?
    
    # controller_2.rb
    caches_page :foo, :bar, if: :should_cache_pages?
    

    但是你可以更进一步 - 如果你总是用这个 if 键调用 caches_page 方法,我会考虑覆盖这个方法(未经测试):

    class ApplicationController < ActionController::Base
      #...
    
      def self.caches_page(*args)
        options = args.extract_options!
        options[:if] = Array.wrap(option[:if]) << :should_cache_pages?
        super *args, options
      end
    
      private
    
      def should_cache_pages?
        request.format && request.format.json? && !is_google_bot? && flash[:notice].nil? && flash[:error].nil?
      end
    end
    

    然后它简化为:

    # controller_1.rb
    caches_page :flu, :baz
    
    # controller_2.rb
    caches_page :foo, :bar
    

    【讨论】:

      【解决方案2】:

      我很确定 caches_page:if 选项可以采用方法名称,这样您就可以拥有一个简单的 mixin:

      module CacheHelpers
        def should_be_cached?(c)
          c.request.format && !c.request.format.json? && !is_google_bot? && flash[:notice].nil? && flash[:error].nil?
        end
      end
      

      然后在你的控制器类中 include CacheHelpers 说:

      # controller_1.rb
      caches_page :flu, :if => :should_be_cached?
      caches_page :baz, :if => :should_be_cached?
      
      # controller_2.rb
      caches_page :foo, :if => :should_be_cached?
      caches_page :bar, :if => :should_be_cached?
      

      如果您在大多数控制器中都在做这种事情,那么请跳过单独的 CacheHelpers 并将其直接放入 ApplicationController

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2016-11-11
        • 2015-11-09
        • 2014-09-18
        • 2011-04-23
        • 1970-01-01
        • 2021-09-30
        • 2010-11-21
        • 2018-08-29
        相关资源
        最近更新 更多