[Nitro] Posible belongs_to problem/bug
Humber Aquino
humberaquino at gmail.com
Wed Dec 28 09:50:01 EST 2005
I think this can be a bug, please follow mi explanation and don't get bored! +)
I'll wil show a common use of a has_many - belongs_to relationship
class User
property :name, String
property :telephone, String
property :username, String, :uniq => true
property :password, String
#roles: plural of Role
has_many :roles, Role
end
class Role
property :permissions, String
#When og maps this class it will create a column named user_oid
belongs_to :user, User
end
#User fixture user.yml
user1:
name: John Doe
telephone: '132312'
username: jduser
password: jdpassword
user2:
name: Some person
telephone: '13d2312'
username: spuser
password: sppassword
#Role fixture role.yml
role1:
user_oid: 1
permmisions: something
role2:
user_oid: 1
permmisions: something else
#So when whe test this we have no problems ;-)
class TestUsuario < Test::Unit::TestCase
def setup
@og = Og.setup(
:destroy => true,
:store => :mysql, #4.0.20
:name => 'test_db',
:user => 'webuser',
:password => '******'
)
og_fixture User
og_fixture Role
end
def test_roles
assert_equal 2, @user1.roles.size
end
end
I run the test an i get this:
1 tests, 1 assertions, 0 failures, 0 errors
:-) Sorry for the verbosity
Then i change the name of the role property in my User class
has_many :roles, Role -> has_many :roles_i_love, Role
And in the test case
def test_roles
assert_equal 2, @user1.roles_i_love.size
end
I run the test.... again :D
1 tests, 1 assertions, 0 failures, 0 errors
Great!
Now i change the name of the property user in the role class
belongs_to :user, User -> belongs_to :user_owner, User
I run the test.... again :D and:
E, [2005-12-28T18:54:58.992435 #10695] ERROR -- : DB error Unknown
column 'user_oid' in 'where clause', [SELECT COUNT(*) FROM ogrole
WHERE user_oid = 1]
E, [2005-12-28T18:54:58.994148 #10695] ERROR -- :
/usr/lib/ruby/gems/1.8/gems/og-0.26.0/lib/og/store/mysql.rb:181:in
`query'
/usr/lib/ruby/gems/1.8/gems/og-0.26.0/lib/og/store/mysql.rb:181:in `query'
/usr/lib/ruby/gems/1.8/gems/og-0.26.0/lib/og/store/sql.rb:476:in `count'
/usr/lib/ruby/gems/1.8/gems/og-0.26.0/lib/og/entity.rb:166:in `count'
(eval):47:in `count_roles_i_love'
/usr/lib/ruby/gems/1.8/gems/og-0.26.0/lib/og/collection.rb:212:in `size'
test/tc_users.rb:26:in `test_roles'
/usr/lib/ruby/1.8/test/unit/testcase.rb:70:in `run'
/usr/lib/ruby/1.8/test/unit/testsuite.rb:32:in `run'
/usr/lib/ruby/1.8/test/unit/testsuite.rb:31:in `run'
/usr/lib/ruby/1.8/test/unit/testsuite.rb:32:in `run'
/usr/lib/ruby/1.8/test/unit/testsuite.rb:31:in `run'
/usr/lib/ruby/1.8/test/unit/ui/testrunnermediator.rb:44:in `run_suite'
/usr/lib/ruby/1.8/test/unit/ui/console/testrunner.rb:65:in `start_mediator'
/usr/lib/ruby/1.8/test/unit/ui/console/testrunner.rb:39:in `start'
/usr/lib/ruby/1.8/test/unit/ui/testrunnerutilities.rb:27:in `run'
/usr/lib/ruby/1.8/test/unit/autorunner.rb:200:in `run'
/usr/lib/ruby/1.8/test/unit/autorunner.rb:13:in `run'
/usr/lib/ruby/1.8/test/unit.rb:285
test/tc_users.rb:25
/usr/lib/ruby/gems/1.8/gems/og-0.26.0/lib/og/store/sql.rb:822:in
`handle_sql_exception': Og::StoreException (Og::StoreException)
from /usr/lib/ruby/gems/1.8/gems/og-0.26.0/lib/og/store/mysql.rb:183:in
`query'
from /usr/lib/ruby/gems/1.8/gems/og-0.26.0/lib/og/store/sql.rb:476:in
`count'
from /usr/lib/ruby/gems/1.8/gems/og-0.26.0/lib/og/entity.rb:166:in
`count'
from (eval):47:in `count_roles_i_love'
from /usr/lib/ruby/gems/1.8/gems/og-0.26.0/lib/og/collection.rb:212:in
`size'
from test/tc_users.rb:26:in `test_roles'
from /usr/lib/ruby/1.8/test/unit/testcase.rb:70:in `run'
from /usr/lib/ruby/1.8/test/unit/testsuite.rb:32:in `run'
... 7 levels...
from /usr/lib/ruby/1.8/test/unit/autorunner.rb:200:in `run'
from /usr/lib/ruby/1.8/test/unit/autorunner.rb:13:in `run'
from /usr/lib/ruby/1.8/test/unit.rb:285
from test/tc_users.rb:25
It executes this sql:
SELECT COUNT(*) FROM ogrole WHERE user_oid = 1
Look at the where clause, it is user_oid and not user_owner_oid
This is the description of the table generated by og
mysql> desc ogrole;
+----------------+---------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+----------------+---------+------+-----+---------+----------------+
| permissions | text | YES | | NULL | |
| user_owner_oid | int(11) | YES | | NULL | |
| oid | int(11) | | PRI | NULL |
auto_increment |
+----------------+---------+------+-----+---------+----------------+
3 rows in set (0.00 sec)
The mapping is correct but the query is not..
Is this a bug or i'm missing something?
I know that this problem can be solved jos changing the property
user_owner back to user, but what can i do when i have 2 has_many
relationships from User to Role for example..
class User
....
has_many :roles_he_like, Role
has_many :roles_he_doesnt_like, Role
....
end
class Role
belongs_to :user, User
has_one :user_doesnt_like, User
end
And make this test
def test_roles
assert_equal 2, @user1.roles_he_like.size #has_many - belongs_to
relationship
assert_equal 0, @user1.roles_he_doesnt_like.size #has_many -
has_one relationship
end
#In mysql
desc ogrole;
+----------------------+---------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default
| Extra |
+----------------------+---------+------+-----+---------+----------------+
| permissions | text | YES | | NULL |
|
| user_oid | int(11) | YES | | NULL |
|
| user_doesnt_like_oid | int(11) | YES | | NULL | |
| oid | int(11) | | PRI | NULL
| auto_increment |
+----------------------+---------+------+-----+---------+----------------+
4 rows in set (0.00 sec)
And the result of the test:
1) Failure:
test_roles(TestUsuario) [test/tc_users.rb:27]:
<0> expected but was
<2>.
1 tests, 2 assertions, 1 failures, 0 errors
This is because it makes this sql query for @user1.roles_he_doesnt_like.size
SELECT COUNT(*) FROM ogrole WHERE user_oid = 1
and not
SELECT COUNT(*) FROM ogrole WHERE user_doesnt_like_oid = 1
Sorry for this long long long mail ;->
Humber
More information about the Nitro-general
mailing list