Я не ожидаю, что модель с NULL как внешним ключом будет принадлежать чему угодно!Активная запись has_many генерирует sql с внешним ключом IS NULL
У меня есть следующее приложение для рельсов, моделирование муравьев и муравейников (вдохновлено Jozef).
$ rails -v
Rails 3.2.8
$ rails new ant_hill
$ cd ant_hill
Создайте муравейник и муравьиные модели. Муравей может принадлежать муравейнику, а муравейник может иметь много муравьев.
$ rails generate model AntHill name:string
$ rails generate model Ant name:string ant_hill_id:integer
$ vim app/models/ant.rb
$ cat app/models/ant.rb
class Ant < ActiveRecord::Base
belongs_to :ant_hill
end
$ vim app/models/ant_hill.rb
$ cat app/models/ant_hill.rb
class AntHill < ActiveRecord::Base
has_many :ants
end
$ rake db:migrate
== CreateAntHills: migrating =================================================
-- create_table(:ant_hills)
-> 0.0013s
== CreateAntHills: migrated (0.0016s) ========================================
== CreateAnts: migrating =====================================================
-- create_table(:ants)
-> 0.0035s
== CreateAnts: migrated (0.0037s) ============================================
Запустите следующий код в консоли.
$ rails c
Loading development environment (Rails 3.2.8)
Создайте пару муравьев, сохранившихся, которые не принадлежат ни одному муравейнику.
1.9.2-p290 :001 > Ant.create! name: "August"
=> #<Ant id: 1, name: "August", ant_hill_id: nil, created_at: "2012-09-27 12:01:06", updated_at: "2012-09-27 12:01:06">
1.9.2-p290 :002 > Ant.create! name: "Bertil"
=> #<Ant id: 2, name: "Bertil", ant_hill_id: nil, created_at: "2012-09-27 12:01:13", updated_at: "2012-09-27 12:01:13">
Теперь создайте экземпляр муравейника, но пока не сохраняйте его.
1.9.2-p290 :003 > ant_hill = AntHill.new name: "Storkullen"
=> #<AntHill id: nil, name: "Storkullen", created_at: nil, updated_at: nil>
Я ожидаю, что этот муравейник не будет иметь муравьев, а это не так.
1.9.2-p290 :004 > ant_hill.ants
=> []
Я все еще ожидаю, что муравейник не будет иметь муравьев, но теперь он имеет два.
1.9.2-p290 :005 > ant_hill.ants.count
(0.1ms) SELECT COUNT(*) FROM "ants" WHERE "ants"."ant_hill_id" IS NULL
=> 2
То же самое здесь он никогда не должен генерировать запрос, содержащий «IS NULL» при работе с внешними ключами. Я имею в виду, что «belongs_to NULL» не может принадлежать ни к чему, не так ли?
1.9.2-p290 :006 > ant_hill.ants.all
Ant Load (0.4ms) SELECT "ants".* FROM "ants" WHERE "ants"."ant_hill_id" IS NULL
=> [#<Ant id: 1, name: "August", ant_hill_id: nil, created_at: "2012-09-27 12:01:06", updated_at: "2012-09-27 12:01:06">, #<Ant id: 2, name: "Bertil", ant_hill_id: nil, created_at: "2012-09-27 12:01:13", updated_at: "2012-09-27 12:01:13">]
После того, как он сохраняется, он ведет себя так, как ожидалось.
1.9.2-p290 :007 > ant_hill.save!
=> true
1.9.2-p290 :008 > ant_hill.ants.count
(0.4ms) SELECT COUNT(*) FROM "ants" WHERE "ants"."ant_hill_id" = 1
=> 0
1.9.2-p290 :009 > ant_hill.ants.all
Ant Load (0.4ms) SELECT "ants".* FROM "ants" WHERE "ants"."ant_hill_id" = 1
=> []
Любое понимание? Это ожидаемое поведение?
В этом случае я не могу сделать ant_hill_id, потому что мое приложение позволяет муравьям, которые не принадлежат к муравейнику. – ludde
с использованием '.size' должен работать в вашем случае – PinnyM
Чтобы быть ясным, я уже работаю над этой проблемой в своем приложении, и я признаю, что есть много способов обойти это. Я просто не думаю, что это ожидаемое поведение.Когда что-то имеет внешний ключ NULL, это означает, что он не принадлежит ни к чему. Думаю, вы могли бы утверждать, что несохраненный холм муравья ничем не отличается от перспективы базы данных, но на самом деле. – ludde