1

我在一个类中有几个函数。对于每个函数,我希望能够指定在执行之前应该调用什么,以及在执行之后调用什么。

例如,假设我的函数是 a、b、c、d 和 e。我想做如下的事情:

before: [:a, :b, :c], execute: :before_func
after: [d, e], execute: :after_func

有没有我可以用来完成上述任务的宝石或技术?

背景:

我的课基本上是一个从 ftp 读取文件的课。我声明了一个@ftp 变量,该变量在创建类实例时初始化,然后在需要时尝试从ftp 读取,或在ftp 上执行其他操作。现在,如果这些操作一起发生,它可以工作,否则它会超时。所以在每个函数之前我想关闭当前的@ftp,然后重新打开一个新的连接并使用它。当函数结束时,我想关闭 ftp 连接。我已经编写了大多数函数,所以只想声明两个函数,一个打开连接,一个关闭连接。

4

2 回答 2

2

您可以通过define_methodand使用一些 ruby​​ 元编程alias_method_chain,可能是这样的:

module MethodHooks

  def before(*symbols)
    hook=symbols.pop
    symbols.each { |meth|
      define_method :"#{meth}_with_before_#{hook}" do |*args, &block|
        self.send hook, *args, &block
        self.send :"#{meth}_without_before_#{hook}", *args, &block
      end
      alias_method_chain meth, :"before_#{hook}"
    }
  end

  def after(*symbols)
    hook=symbols.pop
    symbols.each { |meth|
      define_method :"#{meth}_with_after_#{hook}" do |*args, &block|
        self.send :"#{meth}_without_after_#{hook}", *args, &block
        self.send hook, *args, &block
      end
      alias_method_chain meth, :"after_#{hook}"
    }
  end
end

Object.extend(MethodHooks)

然后在任意类中使用它:

before :a, :b, :c, :before_func
after :a, :b, :c, :after_func

上面的(未经测试的)代码演示了挂钩实例方法的想法,但如果需要,您也可以适应类方法。

于 2013-09-16T15:32:22.337 回答
0

本质上,您希望在 Rails 中进行面向方面的编程。

也许这个宝石可能会帮助https://github.com/davesims/simple-aop

于 2013-09-16T15:33:59.643 回答