Bug #18662
closedEnsure Taxonomix empty default scope isn't overridden by association scopes
Description
Since #16982, the following test fails on Rails 5:
HostsControllerTest#test_0009_should create new host with hostgroup inherited fields [/home/travis/build/domcleal/foreman/test/controllers/hosts_controller_test.rb:114]:
--- expected
++ actual
@ -1 +1
@
-nil
#<Environment id: 334344675, name: "production", created_at: "2017-02-23 13:29:27", updated_at: "2017-02-23 13:29:27">
(Note that actual/expected are the wrong way around.)
When a Taxonomix resource (e.g. Environment) has a default scope that is empty, i.e. the user has access to no resources, returning the scope where(:id => [])
under Rails 5 causes an issue with associations.
An association accessor merges rather than appending a scope to the default scope, so host#environment essentially merges a where(:id => environment_id)
scope to the default. On Rails 4.2, this doesn't merge correctly and so effectively ANDs the two where(:id..) clauses, so no record is found.
irb(main):001:0> Hostgroup.unscoped.first.environment
2017-02-24T10:13:41 [sql] [D] Hostgroup Load (0.6ms) SELECT "hostgroups".* FROM "hostgroups" ORDER BY "hostgroups"."id" ASC LIMIT 1
2017-02-24T10:13:41 [sql] [D] (0.1ms) SELECT "environments"."id" FROM "environments"
2017-02-24T10:13:41 [sql] [D] (0.4ms) SELECT "environments"."id" FROM "environments"
2017-02-24T10:13:41 [sql] [D] Environment Load (0.5ms) SELECT "environments".* FROM "environments" WHERE 1=0 AND "environments"."id" = ? ORDER BY environments.name LIMIT 1 [["id", 1]]
=> nil
irb(main):002:0> Hostgroup.unscoped.first.environment_id
2017-02-24T10:13:45 [sql] [D] Hostgroup Load (0.5ms) SELECT "hostgroups".* FROM "hostgroups" ORDER BY "hostgroups"."id" ASC LIMIT 1
=> 1
On Rails 5.0, this merges fully and so returns a simple where(:id => environment_id)
scope. This overrides the default scope, so host#environment now returns the environment even if the default scope doesn't permit access to it.
irb(main):001:0> Hostgroup.unscoped.first.environment
2017-02-24T10:13:05 [sql] [D] Hostgroup Load (0.2ms) SELECT "hostgroups".* FROM "hostgroups" ORDER BY "hostgroups"."id" ASC LIMIT ? [["LIMIT", 1]]
2017-02-24T10:13:05 [sql] [D] (0.1ms) SELECT "environments"."id" FROM "environments"
2017-02-24T10:13:05 [sql] [D] (0.1ms) SELECT "environments"."id" FROM "environments"
2017-02-24T10:13:05 [sql] [D] Environment Load (0.3ms) SELECT "environments".* FROM "environments" WHERE "environments"."id" = ? ORDER BY environments.name LIMIT ? [["id", 1], ["LIMIT", 1]]
[..]
1 row in set
Changing the default scope to generate a SQL string ('1=0'
) ensures the two clauses are combined rather than the default being overridden.
Also worth noting is that on develop, the test is checking that host.environment
is nil, because hostgroup.environment
now returns nil due to the default scope. It used to test, and should test, that the environment is present.
Updated by Dominic Cleal over 7 years ago
- Related to Bug #16982: CVE-2016-7078 - User with no organizations or locations can see all resources added
Updated by The Foreman Bot over 7 years ago
- Status changed from Assigned to Ready For Testing
- Pull request https://github.com/theforeman/foreman/pull/4330 added
Updated by Dominic Cleal over 7 years ago
- Status changed from Ready For Testing to Closed
- % Done changed from 0 to 100
Applied in changeset f54cb6a2079e9acce75e8a621211541c948ad01b.
Updated by Dominic Cleal over 7 years ago
- Translation missing: en.field_release set to 209