2012-01-04 4 views
5

Почему-то мой alias_method_chain не хочет работать, и я понятия не имею, почему. Может ли кто-нибудь объяснить мне, почему следующее не будет работать?Метод псевдонима метод неопределенного метода

[2] pry(main)> Client.respond_to? :mapping 
=> true 
[3] pry(main)> Client.alias_method_chain :mapping, :safety 
NameError: undefined method `mapping' for class `Client' 

ответ

7

Чтобы получить цепочку методов псевдонима для объекта какого-либо класса, вы должны позвонить по номеру alias_method_chain по самому классу, а не по его экземпляру. Если вы хотите, чтобы сделать цепочку из методов класса применяется то же правило: вы должны вызвать alias_method_chain на класс одноплодной класса, который может быть получен так:

klass = class << Client; self; end # => returns singleton class for Client class 

В этом случае Client является экземпляром klass класса (то есть Class класс как его суперкласс).

Результирующего пример методов класса цепи может быть следующим:

class Client 
    def self.mapping 
    puts 'mapping' 
    end 

    def self.mapping_with_safety 
    puts 'safety' 
    mapping_without_safety 
    end 

    class << self 
    # call alias_method_chain in context of Client's singleton class 
    alias_method_chain :mapping, :safety 
    end 
end 

# alternatively you can do it outside of Client class like that 
# (class << Client; self; end).alias_method_chain :mapping, :safety 

Client.mapping 
# => safety 
# => mapping 
+0

Я узнал об этом после того, как факт, но для всех, кто находит это, это правильный ответ. Другой способ сделать это будет с Client.class_eval {} –

2

Для того, чтобы alias_method_chain работать, отображающая функция должна быть методом экземпляра, а не метод класса, как в вашем примере, так Client.new.respond_to? :mapping потребности, чтобы быть правдой (обратите внимание на новый вызов).

+0

(Вы также можете проверить, если методы экземпляра существует путь вызова Client.method_defined «отображение», просто говоря?) – Robin