2009-02-04 4 views
1

У меня унаследованную базу с кучей идиотски именованных столбцов, как:Rails ActiveRecord: автоматически псевдоним/добавить суффикс?

some_field_c 
some_other_field_c 
a_third_field_c

Я бы очень хотел, чтобы сделать Rails ActiveRecord суб-класс, который автоматически псевдонимы эти атрибуты своего имени минус подчеркиванием и «с». Однако, когда я попытался:

attributes.each_key do | key | 
    name = key 
    alias_attribute key.to_sym, key[0, (key.length -2)].to_sym if key =~ /_c$/ 
end 

в моем определении класса я получил «неопределенные локальная переменная или метод` атрибуты»ошибка. Я также попытался переписать эти методы:

method_missing 
respond_to?

, но я продолжал получать ошибки с этим маршрутом.

Так что мой вопрос (на самом деле вопросы) является/являются:

  1. Это то, что я пытаюсь сделать даже можно?
  2. Если да, то что это лучший способ сделать это (итеративное сглаживание или метод перезаписи отсутствует)?
  3. Если это не так много проблем, очень короткий пример кода, как сделать # 2, был бы потрясающим.

Заранее благодарим за любые ответы на этот пост.

+0

Можете ли вы опубликовать полный пример, это должно быть довольно легко получить работу –

ответ

2

Возможно, ваша проблема связана с тем, что attributes - это метод экземпляра, и вы делаете это в контексте класса. Метод класса, который наиболее близок к тому, что вам нужно, - column_names.

+0

Это сработало, спасибо! Мне пришлось поместить код в метод, который был вызван подклассом, чтобы заставить его работать, и было бы неплохо, если бы вместо этого можно было сказать «Запустите этот код повторного сглаживания сразу после того, возникает свойство атрибута класса ", но * shrug * oh well. Еще раз спасибо! – machineghost

+0

Я попытался вставить свой рабочий код здесь, но форматирование комментария испортило его :-(Однако это был по сути тот же код, что и в моем вопросе, за исключением «column_names» вместо «attributes», и no «name = key "(эта линия была мусора), все определенные в методе, который вызывается в подклассе. – machineghost

1

вы могли бы сделать что-то вроде:

methods.each do |method| 
    if method.ends_with("_c") then 
    self.send(:defind_method,method.slice(0,-2)){self.send(method)} 
    end 
end 
1

Хм ... Я приготовил это маленькое решение, которое я думал, кончались довольно элегантно ...

Не уверен, если это будет работать, но я алиас method_missing по-прежнему позволяет active_record сделать это Тханг:

module ShittyDatabaseMethods 
    alias :old_method_missing :method_missing 

    def method_missing(method) 
    if methods.include?("#{method}_c") 
     send("#{method}_c".to_sym) 
    else 
     old_method_missing(method) 
    end 
    end 

end 

class Test 
    attr_accessor :test_c 
    include ShittyDatabaseMethods 
end 

вы не можете получить имя вашего модуля «ShittyDatabaseMethods», но вы получите идею;) После того, как вы определили, что модуль и прочее я т в Lib, вам просто нужно включить этот модуль и ступай: D

Хотелось бы услышать, если это работает для вас :)

+0

Спасибо, но, к сожалению, это не будет работать :-(Если я что-то вроде my_shitty_object.some_attribute = 5 что становится вызовом метода «some_attribute =», если вы добавляете «_c» к тому, что вы получаете «some_attribute = _c» в качестве имени вашего метода, а не «some_attribute_c =». – machineghost

+0

Ах, правда правда. Хороший улов :) –

 Смежные вопросы

  • Нет связанных вопросов^_^