Hammed Malik
2006-Sep-24 09:51 UTC
How to specify condition for eagerly joined model using :include?
I''d like to specify conditions for a model that I''m left outer
joining
using :include. A simplification of the problem:
User.find :all, :include => :addresses, :conditions =>
["addresses.is_active = 1"]
Results in the following SQL.
SELECT
users.*,
addresses.*
FROM users
LEFT OUTER JOIN addresses ON addresses.user_id = users.id
WHERE (addresses.is_active = 1)
The SQL I''d like is:
SELECT
users.*,
addresses.*
FROM users
LEFT OUTER JOIN addresses ON addresses.user_id = users.id AND
addresses.is_active = 1
Note the condition has been moved from the main query''s WHERE clause
to the left join''s condition. Any way to do this? I really
don''t want
to use find_by_sql.
Thanks
Hammed
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups
"Ruby on Rails: Talk" group.
To post to this group, send email to
rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org
To unsubscribe from this group, send email to
rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org
For more options, visit this group at
http://groups.google.com/group/rubyonrails-talk
-~----------~----~----~----~------~----~------~--~---
Mark Reginald James
2006-Sep-24 13:35 UTC
Re: How to specify condition for eagerly joined model using :include?
Hammed Malik wrote:> I''d like to specify conditions for a model that I''m left outer joining > using :include. A simplification of the problem: > > User.find :all, :include => :addresses, :conditions => > ["addresses.is_active = 1"] > > Results in the following SQL. > > SELECT > users.*, > addresses.* > FROM users > LEFT OUTER JOIN addresses ON addresses.user_id = users.id > WHERE (addresses.is_active = 1) > > > The SQL I''d like is: > > > SELECT > users.*, > addresses.* > FROM users > LEFT OUTER JOIN addresses ON addresses.user_id = users.id AND > addresses.is_active = 1 > > > Note the condition has been moved from the main query''s WHERE clause > to the left join''s condition. Any way to do this? I really don''t want > to use find_by_sql.Try: class User has_many :active_addresses, :className => Address, :conditions => ''addresses.is_active = 1'' end User.find :all, :include => :active_addresses -- We develop, watch us RoR, in numbers too big to ignore. --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group. To post to this group, send email to rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org To unsubscribe from this group, send email to rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org For more options, visit this group at http://groups.google.com/group/rubyonrails-talk -~----------~----~----~----~------~----~------~--~---
Hammed Malik
2006-Sep-24 13:49 UTC
Re: How to specify condition for eagerly joined model using :include?
Thanks Mark. That works for the example I quoted but I do need to specify the conditions (which vary) when creating the query in the controller. Hammed On 9/24/06, Mark Reginald James <mrj-bzGI/hKkdgQnC9Muvcwxkw@public.gmane.org> wrote:> > Hammed Malik wrote: > > I''d like to specify conditions for a model that I''m left outer joining > > using :include. A simplification of the problem: > > > > User.find :all, :include => :addresses, :conditions => > > ["addresses.is_active = 1"] > > > > Results in the following SQL. > > > > SELECT > > users.*, > > addresses.* > > FROM users > > LEFT OUTER JOIN addresses ON addresses.user_id = users.id > > WHERE (addresses.is_active = 1) > > > > > > The SQL I''d like is: > > > > > > SELECT > > users.*, > > addresses.* > > FROM users > > LEFT OUTER JOIN addresses ON addresses.user_id = users.id AND > > addresses.is_active = 1 > > > > > > Note the condition has been moved from the main query''s WHERE clause > > to the left join''s condition. Any way to do this? I really don''t want > > to use find_by_sql. > > Try: > > class User > has_many :active_addresses, :className => Address, > :conditions => ''addresses.is_active = 1'' > end > > User.find :all, :include => :active_addresses > > -- > We develop, watch us RoR, in numbers too big to ignore. > > > > >--~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group. To post to this group, send email to rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org To unsubscribe from this group, send email to rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org For more options, visit this group at http://groups.google.com/group/rubyonrails-talk -~----------~----~----~----~------~----~------~--~---
Mark Reginald James
2006-Sep-24 14:26 UTC
Re: How to specify condition for eagerly joined model using :include?
Hammed Malik wrote:> That works for the example I quoted but I do need to specify the > conditions (which vary) when creating the query in the controller.Hmm, the only way I can think of is: class User has_many :conditional_addresses, :className => Address end User.reflect_on_association(:conditional_addresses).options[:conditions] = ''...'' User.find :all, :include => :conditional_addresses -- We develop, watch us RoR, in numbers too big to ignore. --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group. To post to this group, send email to rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org To unsubscribe from this group, send email to rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org For more options, visit this group at http://groups.google.com/group/rubyonrails-talk -~----------~----~----~----~------~----~------~--~---
Mark Reginald James
2006-Sep-24 14:40 UTC
Re: How to specify condition for eagerly joined model using :include?
Mark Reginald James wrote:> Hmm, the only way I can think of is: > > class User > has_many :conditional_addresses, :className => Address > end > > User.reflect_on_association(:conditional_addresses).options[:conditions] = ''...'' > User.find :all, :include => :conditional_addressesSomewhat neater: class User has_many :conditional_addresses, :className => Address do def conditions=(condition) reflection.options[:conditions] = condition end end end User.conditional_addresses.conditions = ''...'' User.find :all, :include => :conditional_addresses -- We develop, watch us RoR, in numbers too big to ignore. --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group. To post to this group, send email to rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org To unsubscribe from this group, send email to rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org For more options, visit this group at http://groups.google.com/group/rubyonrails-talk -~----------~----~----~----~------~----~------~--~---
Hammed Malik
2006-Sep-26 01:46 UTC
Re: How to specify condition for eagerly joined model using :include?
Thanks Mark. Not exactly what I was hoping for but this actually answers another question I had. Cheers Hammed On 9/25/06, Mark Reginald James <mrj-bzGI/hKkdgQnC9Muvcwxkw@public.gmane.org> wrote:> > Mark Reginald James wrote: > > > Hmm, the only way I can think of is: > > > > class User > > has_many :conditional_addresses, :className => Address > > end > > > > User.reflect_on_association(:conditional_addresses).options[:conditions] = ''...'' > > User.find :all, :include => :conditional_addresses > > Somewhat neater: > > class User > has_many :conditional_addresses, :className => Address do > def conditions=(condition) > reflection.options[:conditions] = condition > end > end > end > > User.conditional_addresses.conditions = ''...'' > User.find :all, :include => :conditional_addresses > > -- > We develop, watch us RoR, in numbers too big to ignore. > > > > >--~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group. To post to this group, send email to rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org To unsubscribe from this group, send email to rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org For more options, visit this group at http://groups.google.com/group/rubyonrails-talk -~----------~----~----~----~------~----~------~--~---
Mark Reginald James
2006-Sep-30 10:49 UTC
Re: How to specify condition for eagerly joined model using :include?
Mark Reginald James wrote:> class User > has_many :conditional_addresses, :className => Address do > def conditions=(condition) > reflection.options[:conditions] = condition > end > end > end > > User.conditional_addresses.conditions = ''...'' > User.find :all, :include => :conditional_addressesJust for the record, this won''t work because conditional_addresses is a User instance method, not a class method, so with this code you''d have to write: User.new.conditional_addresses.conditions = ''...'' Better would be: class User < ActiveRecord::Base has_many :addresses def self.with_conditions(assoc, conditions) options = reflect_on_association(assoc).options orig_conditions = options[:conditions] options[:conditions] = conditions yield options[:conditions] = orig_conditions end end User.with_conditions(:addresses, ''addresses.is_active = 1'') do User.find :all, :include => :addresses end You could even augment method_missing and add a class context so you can instead write: User.with_address_conditions(''addresses.is_active = 1'') do find :all, :include => :addresses end -- We develop, watch us RoR, in numbers too big to ignore. --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "Ruby on Rails: Talk" group. To post to this group, send email to rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org To unsubscribe from this group, send email to rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org For more options, visit this group at http://groups.google.com/group/rubyonrails-talk -~----------~----~----~----~------~----~------~--~---
Hi Mark,
Thank you _so_ much for your code and your return trip to update/fix it
above as well. We have a large schema with tons of lookup tables
defining entity type/kind and the problem as original descibed has come
up a bunch.
Your code above DOES work as described. I just set this up and was able
to do:
Person.with_conditions(:addresses,
''addresses_mailing.id_t_addresses_mailing = 2'') do
@people = Person.find :all, :include => [{:addresses =>
:t_address}, :email_addresses], :conditions => "name_last like
''W%''",
:limit => 15
end
which, includes multiple other associations, a limit clause and some
WHERE clause action as well.
All best!
>> class User
>> has_many :conditional_addresses, :className => Address do
>> def conditions=(condition)
>> reflection.options[:conditions] = condition
>> end
>> end
>> end
>>
>> User.conditional_addresses.conditions = ''...''
>> User.find :all, :include => :conditional_addresses
>
> Just for the record, this won''t work because conditional_addresses
> is a User instance method, not a class method, so with this code
> you''d have to write: User.new.conditional_addresses.conditions =
''...''
>
> Better would be:
>
> class User < ActiveRecord::Base
> has_many :addresses
>
> def self.with_conditions(assoc, conditions)
> options = reflect_on_association(assoc).options
> orig_conditions = options[:conditions]
> options[:conditions] = conditions
> yield
> options[:conditions] = orig_conditions
> end
> end
>
> User.with_conditions(:addresses, ''addresses.is_active =
1'') do
> User.find :all, :include => :addresses
> end
>
> You could even augment method_missing and add a class context
> so you can instead write:
>
> User.with_address_conditions(''addresses.is_active =
1'') do
> find :all, :include => :addresses
> end
>
> --
> We develop, watch us RoR, in numbers too big to ignore.
--
Posted via http://www.ruby-forum.com/.
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups
"Ruby on Rails: Talk" group.
To post to this group, send email to
rubyonrails-talk-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org
To unsubscribe from this group, send email to
rubyonrails-talk-unsubscribe-/JYPxA39Uh5TLH3MbocFFw@public.gmane.org
For more options, visit this group at
http://groups.google.com/group/rubyonrails-talk?hl=en
-~----------~----~----~----~------~----~------~--~---