Неопределенный метод даже после обработки method_missing
Я изучаю Ruby и пытаюсь реализовать method_missing
, но это не работает. Например, я хочу напечатать имя метода после find_
но ruby вызывает "неопределенный метод 'find_hello'", когда я вызываю его в экземпляре Book.
TEST_05.RB
module Searchable
def self.method_missing(m, *args)
method = m.to_s
if method.start_with?("find_")
attr = method[5..-1]
puts attr
else
super
end
end
end
class Book
include Searchable
BOOKS = []
attr_accessor :author, :title, :year
def initialize(name = "Undefined", author = "Undefined", year = 1970)
@name = name
@author = author
@year = year
end
end
book = Book.new
book.find_hello
2 ответа
Вы вызываете метод на object
который ищет instance_level
метод. Так что вам нужно определить instance_level method_missing
метод:
module Searchable
def method_missing(m, *args)
method = m.to_s
if method.start_with?("find_")
attr = method[5..-1]
puts attr
else
super
end
end
end
class Book
include Searchable
BOOKS = []
attr_accessor :author, :title, :year
def initialize(name = "Undefined", author = "Undefined", year = 1970)
@name = name
@author = author
@year = year
end
end
book = Book.new
book.find_hello #=> hello
Когда вы используете self
с определением метода. Определяется как class level
метод. В твоем случае Book.find_hello
будет выводить hello
,
Вы определили method_missing
как метод класса на Searchable
, но вы пытаетесь вызвать его как метод экземпляра. Чтобы вызвать метод как есть, запустите его для класса:
Book.find_hello
Если вы хотите найти что-то из всей коллекции книг, это канонический способ. ActiveRecord использует этот подход.
Вы могли бы так же иметь find_*
Метод экземпляра, который будет искать текущий экземпляр книги для чего-то. Если это ваше намерение, то измените def self.method_missing
в def method_missing
,