Действительны ли ассоциации ActiveRecord перед фиксацией в базе данных? - PullRequest
0 голосов
/ 28 августа 2009

У меня есть модель, которая использует действует как дерево. Например:

class CartoonCharacter < ActiveRecord::Base
  acts_as_tree
end

Действует как дерево, имеет следующие ассоциации:

class ActsAsTree
  belongs_to :parent
  has_many :children
end

Из скрипта / консоли я строю свое дерево, ничего не сохраняя, пока не будет построено все дерево. Проблема, с которой я столкнулся, заключается в том, что до фиксации базы данных я не могу успешно перемещаться по дереву. Вызовы #parent и #sibling дают сомнительные результаты. Я могу только предположить, что что-то упустил.

fred=CartoonCharacter.new(:name=>'Fred')
fred.children.build(:name => 'BamBam')
pebbles = fred.children.build(:name => 'Pebbles')

fred.children #=> [BamBam, Pebbles]
fred.children.last.parent #=> nil --- why not Fred?
pebbles.siblings #=> [completely unrelated records from db??]

Я предполагаю, что это как-то связано с обработкой ассоциаций. Я бы предположил, что структуры ActiveRecord в памяти будут полностью ориентированы, но они, похоже, не будут. От принудительного входа в консоль я иногда замечал, что навигация по ассоциациям вызывает доступ к базе данных. Это мешает узнать, как обходить ассоциации. (Я кратко изучил кэширование запросов.) Как другие справляются с этим? Или вы всегда делаете записи и их отношения на ходу? Это озадачивает.


EDIT:

То, что, кажется, решает эту проблему, состоит в том, чтобы установить оба отношения одновременно. То есть недостающий кусок был:

pebbles.parent = fred
bambam.parent = fred

Это задумано? То есть всегда ли мы должны устанавливать обе части взаимных отношений?


EDIT:

Похожие question

1 Ответ

0 голосов
/ 28 августа 2009

Используете ли вы плагин act_as_tree? - http://github.com/rails/acts_as_tree/tree/master

Это будет работать так, как вы хотите / ожидаете.

Если вы катите эту структуру данных самостоятельно, ваши ассоциации, как описано в ОП, не являются полными - они ссылаются на разные внешние ключи.

belongs_to :parent  # parent_id field in this model
has_many :children  # child_id field in the child models

Таким образом, в настоящее время существуют две разные ассоциации между парами экземпляров. Вот почему вам нужно сделать два оператора присваивания.

Вместо вышесказанного, что-то вроде

belongs_to :parent, :class_name => "CartoonCharacter", 
  :foreign_key => :tree_key

has_many :children, :class_name => "CartoonCharacter",
  :foreign_key => :tree_key

Larry

...