Виртуальные атрибуты из методов define_method, созданных в rails 2.3 - PullRequest
0 голосов
/ 18 января 2012

У меня есть методы для получения и установки виртуальных атрибутов. На самом деле они устанавливают один символ для реального атрибута, как должен объяснить этот фрагмент кода:

attr_accessible :picnic_on_sunday, :picnic_on_monday, :picnic_on_tuesday,
                :picnic_on_wednesday, :picnic_on_thursday, :picnic_on_friday,
                :picnic_on_saturday,

['sunday', 'monday', 'tuesday', 'wednesday', 'thursday',
  'friday', 'saturday'].each_with_index do |dayname, dayindex|
  define_method "picnic_on_#{dayname.downcase}".to_sym do
    picnic_weekdays[dayindex]=='1'
  end
  define_method "picnic_on_#{dayname.downcase}=" do |value|
    wdays = picnic_weekdays
    wdays[dayindex] = (value==true or value=='1') ? '1':'0'
    self.picnic_weekdays = wdays 
  end
end

picnic_weekdays - это реальный атрибут, присутствующий в схеме. Моя проблема в том, что хотя сгенерированные геттеры / сеттеры работают, когда я делаю изменения, x.picnic_on_monday = true меняет индекс 1 на x.picnic_weekdays, при вызове save в модели ничего не сохраняется Такое поведение имеет место только тогда, когда методы генерируются define_method. Почему это так? Как я могу заставить сгенерированные виртуальные атрибуты работать? Спасибо за ваше объяснение.

1 Ответ

1 голос
/ 08 марта 2012

Изменение, которое вы вносите в picnic_weekdays, не является постоянным, потому что вы, кажется, победили внутреннюю логику в ActiveRecord, которая отслеживает измененные атрибуты!Я предполагаю, что это связано с тем, что модуль Dirty пропатчен в ActiveRecord.

Пример вашего вопроса можно исправить, сказав ActiveRecord, что атрибут изменился с помощью метода <attribute>_will_change! следующим образом:

define_method "picnic_on_#{dayname.downcase}=" do |value|
  wdays = picnic_weekdays
  wdays[dayindex] = (value==true or value=='1') ? '1':'0'
  self.picnic_weekdays = wdays 
  self.picnic_weekdays_will_change!
end
...