Перечислите только методы подкласса ActiveRecord - PullRequest
1 голос
/ 27 февраля 2012

Учитывая следующую модель ActiveRecord:

class User < ActiveRecord::Base
  has_many :games
  def name
    "Joe"
  end

  def city
     "Chicago"
  end
end

Я хотел бы получить список методов, которые я добавил непосредственно в класс User (а не те, которые были добавлены путем расширения ActiveRecord и / или добавления ассоциаций),Пример вывода:

["name","city"]

Вызов User.instance_methods (false) возвращает метод, добавленный ActiveRecord:

["validate_associated_records_for_games", "games", "game_ids", "games=", "game_ids=", "after_create_or_update_associated_records_for_games", "before_save_associated_records_for_games"]

Наряду с любыми атрибутами модели из столбцов базы данных.Я хотел бы исключить их и просто получить пользовательские методы для подкласса.

Моя цель - отслеживание методов: я хотел бы отслеживать свои пользовательские методы, исключая те, которые добавлены ActiveRecord.

Есть идеи?

Ответы [ 2 ]

1 голос
/ 27 февраля 2012
User.instance_methods - ActiveRecord::Base.instance_methods #=> [:name,:city]

UPDATE:

порядок этих методов значим

class User < ActiveRecord::Base
  def self.my_own_methods
    self.instance_methods - @@im
  end
  has_many :games
  @@im = self.instance_methods
  def name
    "Joe"
  end
  def city
    "Chicago"
  end
end

User.my_own_methods #=> [:name, :city]

Этот проверен и работает

0 голосов
/ 27 февраля 2012

Используйте хук method_added, который добавляет имена методов в список, и обезьяна-патч Active Record, чтобы методы, добавленные AR, не добавлялись в этот список.

Если вы не хотите открывать AR и начинать ковыряться, вы также можете определить «макрос класса», который определяет метод , и добавляет его в список. Для ваших собственных пользовательских методов используйте макрос класса, а не def.

Если вы не знакомы с тем, что я называю «макросом класса», это просто метод, подобный этому:

class Class
  def mydef(name,&block)
    (@methods || []) << name
    define_method(name,&block)
  end
end

Использовать что-то вроде mydef для определения методов, а не def, безусловно, некрасиво, но это решило бы проблему, не требуя каких-либо махинационных исправлений.

...