2010-01-27 3 views
1

У меня есть некоторые проблемы в Rails Active Record Inheritance, мне нужно создать модель, которая наследует свойства (поля) класса родителя и также должна содержать свои собственные свойства.Наследование активной записи

Ex: Родитель Класс

class Content < ActiveRecord::Base 
end 

Классы наследующих родительский класс (Content)

class Wiki < Content // Inherting Class Content 
end 

class Video < Content // Inherting Class Content 
end 

Пусть таблица "Содержание" содержит тип полей, имя (для хранения общих полей)

  • "Wiki" таблица содержит поля body, описание
  • стола «Видео» содержит поле имени файла, описание

Вставки в содержании и вик-таблицу, как

def create 
    WikiPage.new("name" =>"new_wikipage") 
    @wiki_page = WikiPage.new(params[:wiki_page]) 
end 

, но проблема в том, вновь созданные виках страницы не вставляя (так как родительский класс «Содержание "является абстрагирование значения класса ребенок Param вики страницы)

Генерация ошибки, как метод„тела“не определен (поле„тело“является частью вики-таблицы, которые получили по таблице спрятал содержание)

ответ

2

Rails использует однонаправленное наследование (STI) для подклассов модели. Это означает, что вы не создаете отдельную таблицу для Wiki или Video в своей базе данных. Все они будут сохранены в таблице «Содержание», и эта таблица должна включать все поля, необходимые для всех подклассов.

Все в порядке, если не все подклассы используют все доступные поля. Затем Rails отслеживает, какой подкласс является записью, используя столбец «type» родительской таблицы.

Я подробно рассмотрю эту статью под названием Single-Table Inheritance with Tests in Rails. Я думаю, что образцы кода дадут вам лучшее представление о том, как действовать.

+0

Что делать, если вы не хотите использовать STI? Из документов: «Если у вас нет столбца типа, определенного в вашей таблице, однонаправленное наследование не будет запущено. В этом случае он будет работать так же, как и обычные подклассы без специальной магии для дифференциации между их или перезагрузить правильный тип с помощью find. " Этот вопрос касается получения этой работы БЕЗ ИППП, что должно быть возможным. У меня такая же проблема с наличием дочерних классов с разными атрибутами. – scragz

+0

scragz: вопрос был о том, чтобы заставить его работать. Ассистент никогда не говорил «без ИППП», потому что они, вероятно, даже не знали, что это вариант. Нижняя строка, наследование классов в ActiveRecord выполняется с помощью STI. Есть много хороших аргументов против ИППП, и я избегаю этого, когда могу, но они не имеют значения.Вы не можете иметь таблицы, наследующие друг от друга в реляционных базах данных, поэтому попытка подражать этому поведению в AR-классах бесполезна. Вместо этого попробуйте абстрагировать общие методы в модуль, который затем включается в каждый класс. Выполнение «rails g model content: wiki» приведет к качению мяча. –

1

Техника, которую вы хотите использовать, называется Наследование отдельных таблиц. В принципе, только те модели, которые наследуют напрямую от ActiveRecord::Base, имеют свои собственные таблицы. В этой таблице должен быть столбец type (требуется не-NULL), который сохраняет имя класса для каждой строки/объекта.

Подробнее об этом можно узнать в Rails API docs. Я также написал article on when to use STI, который может быть полезен.

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