This project is archived and is in readonly mode.
has_one through associations not saved correctly
Reported by gerad | November 11th, 2009 @ 12:15 AM
Summary
Attributes created using has_one :through associations are lost upon serialization to the database.
Details
class Club < ActiveRecord::Base
has_one :membership
end
class Membership < ActiveRecord::Base
belongs_to :person
belongs_to :club
end
class Person < ActiveRecord::Base
has_one :membership
has_one :club, :through => :membership
end
require 'test_helper'
class PersonTest < ActiveSupport::TestCase
test "person's club is saved" do
p = Person.new
c = Club.new
p.club = c
assert_equal c, p.club
c.save!; c.reload
p.save!; p.reload
assert_equal c, p.club
end
end
$ ruby -Itest test/unit/person_test.rb
Loaded suite test/unit/person_test
Started
F
Finished in 0.057744 seconds.
1) Failure:
test_person's_club_is_saved(PersonTest) [test/unit/person_test.rb:11]:
<#<Club id: 1, created_at: "2009-11-11 01:01:47", updated_at: "2009-11-11 01:01:47">> expected but was
<nil>.
1 tests, 2 assertions, 1 failures, 0 errors
Comments and changes to this ticket
-
gerad November 11th, 2009 @ 01:03 AM
Also happens on 2.3.4 version 7ba80252a5a6bd94c8445347caee663b12c1a526
-
Jigar Patel July 24th, 2010 @ 12:58 PM
Three cases -
1. p = Person.new
c = Club.new p.club = c This line will insert a new row in memberships table with both person_id and club_id as nil.
c.save p.save Both objects will be saved without any related membership. Hence your test case fails.- p = Person.new
c = Club.new c.save p.club = c
This will create an entry in Membership table with club_id = "c.id" and person_id as nil
p.save will save the object but without any related membership and hence without any related organization.- p = Person.new
p.save p will be a Person with some id.
c = Club.new c.save c will be a Club with some id.
p.club = c This will create an entry in memberships table with person_id and club_id pointing to corresponding rows in persons and clubs tables.
p.save will save and you will be able to fetch club.
- p = Person.new
-
lakshmanan July 24th, 2010 @ 01:08 PM
I ran your testcase statements in console and I test Membership after every statement. You are not saving anything
In short -> you are playing in memory without saving anything. so literally you are playing with nils
>> p = Person.new => #<Person id: nil, created_at: nil, updated_at: nil> >> Membership.last => nil >> c = Club.new => #<Club id: nil, created_at: nil, updated_at: nil> >> Membership.last => nil >> p.club = c => #<Club id: nil, created_at: nil, updated_at: nil> >> Membership.last => nil >> c.save! => true >> Membership.last => nil >> c.reload => #<Club id: 2, created_at: "2010-07-24 11:57:24", updated_at: "2010-07-24 11:57:24"> >> p.save! # after this statement - your test will pass => true >> Membership.last => #<Membership id: 2, club_id: nil, person_id: 2, created_at: "2010-07-24 11:57:43", updated_at: "2010-07-24 11:57:43">
Hope it helps
-
Rohit Arondekar September 27th, 2010 @ 02:52 PM
- State changed from new to invalid
- Importance changed from to Low
p.club
andc
are not the same.c
is created whenc
is saved. Whilep.club
is created whenp
is saved. -
csnk May 18th, 2011 @ 08:28 AM
We are the professional underwear manufacturer, underwear supplier, underwear factory, custom underwear.
Create your profile
Help contribute to this project by taking a few moments to create your personal profile. Create your profile »
<h2 style="font-size: 14px">Tickets have moved to Github</h2>
The new ticket tracker is available at <a href="https://github.com/rails/rails/issues">https://github.com/rails/rails/issues</a>