Neeraj Singh
2010-May-12 03:47 UTC
In development mode not all types are included in the query related to type
class User end class Agent < User end script/console production User.find_by_name ''john'' SELECT "people".* FROM "people" WHERE ((("people"."type" = ''User'' OR "people"."type" = ''Manager'') OR "people"."type" = ''Agent'')) AND ("people"."name" = ''agent'') LIMIT 1 In development mode. script/console User.find_by_name ''john'' SELECT "people".* FROM "people" WHERE ("people"."type" = ''User'') AND ("people"."name" = ''agent'') LIMIT 1 I should have mentioned the ticket rather than typing all this much. https://rails.lighthouseapp.com/projects/8994-ruby-on-rails/tickets/4516-correct-type-conditions-arent-added-when-using-multiple-inheritances-wsti#ticket-4516-3 I am sure this issue must be there for a while. And probably the consensus is to leave it the way it is and no need to try to fix it in development mode. Just asking for confirmation. -- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Colin Law
2010-May-12 08:32 UTC
Re: In development mode not all types are included in the query related to type
On 12 May 2010 04:47, Neeraj Singh <neerajdotname@gmail.com> wrote:> class User > end > > class Agent < User > end > > script/console production > User.find_by_name ''john'' > > SELECT "people".* FROM "people" WHERE ((("people"."type" = ''User'' OR > "people"."type" = ''Manager'') OR "people"."type" = ''Agent'')) AND > ("people"."name" = ''agent'') LIMIT 1That does not make sense, there is no ''john'' in the query.> > > In development mode. > script/console > User.find_by_name ''john'' > SELECT "people".* FROM "people" WHERE ("people"."type" = ''User'') AND > ("people"."name" = ''agent'') LIMIT 1I am guessing that it is due to the way files are loaded in development vs production. I think (but may be wrong) that in production all files are loaded so it knows about the other user types, whereas in development it only loads files as it needs them so does not know about the other types. Though why it is testing the type at all in the query I am not sure. Is User derived from ActiveRecord base? I wonder whether there is more to the class declarations than you have shown us. Colin> > > I should have mentioned the ticket rather than typing all this much. > https://rails.lighthouseapp.com/projects/8994-ruby-on-rails/tickets/4516-correct-type-conditions-arent-added-when-using-multiple-inheritances-wsti#ticket-4516-3 > > I am sure this issue must be there for a while. And probably the > consensus is to leave it the way it is and no need to try to fix it in > development mode. Just asking for confirmation. > > -- > You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. > To post to this group, send email to rubyonrails-core@googlegroups.com. > To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. > For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en. > >-- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Neeraj Singh
2010-May-12 10:42 UTC
Re: In development mode not all types are included in the query related to type
The sql that I posted came out after testing the exact case provided by the author of the ticket. While composing this email I did not layout the full hierarchy. @Colin. It is definitely due to class loading. If in development I load Agent then query will include Agent too. script/console> Agent > User.find_by_name ''john'' # now the query will include agentMy question is this: This is something I am encountering now but it must have been there since STI was introduced which was years ago. So should this bug be fixed. For some it might not be a bug given that it happens only in development mode. Nonetheless it could be confusing if you are not aware of how it works (as I was initially). -- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Colin Law
2010-May-12 10:53 UTC
Re: Re: In development mode not all types are included in the query related to type
On 12 May 2010 11:42, Neeraj Singh <neerajdotname@gmail.com> wrote:> The sql that I posted came out after testing the exact case provided > by the author of the ticket. While composing this email I did not > layout the full hierarchy. > > @Colin. It is definitely due to class loading. If in development I > load Agent then query will include Agent too. > > script/console >> Agent >> User.find_by_name ''john'' # now the query will include agent > > My question is this: This is something I am encountering now but it > must have been there since STI was introduced which was years ago. So > should this bug be fixed. For some it might not be a bug given that it > happens only in development mode. Nonetheless it could be confusing if > you are not aware of how it works (as I was initially).Since you have deleted all of the original post and my comments the above now makes no sense. No-one reading this will know what your problem is without going back to the previous mail, which is something one should not normally be forced to do. Colin> > -- > You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. > To post to this group, send email to rubyonrails-core@googlegroups.com. > To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. > For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en. > >-- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Neeraj Singh
2010-May-12 11:56 UTC
Re: In development mode not all types are included in the query related to type
> Since you have deleted all of the original post and my comments the > above now makes no sense. No-one reading this will know what your > problem is without going back to the previous mail, which is something > one should not normally be forced to do.Extremely sorry about that. I have created a gist which explains the problem much more succintly. http://gist.github.com/398486 -- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Colin Law
2010-May-12 12:33 UTC
Re: Re: In development mode not all types are included in the query related to type
On 12 May 2010 12:56, Neeraj Singh <neerajdotname@gmail.com> wrote:>> Since you have deleted all of the original post and my comments the >> above now makes no sense. No-one reading this will know what your >> problem is without going back to the previous mail, which is something >> one should not normally be forced to do. > > Extremely sorry about that. I have created a gist which explains the > problem much more succintly. > http://gist.github.com/398486What are the names of the rb files containing the class definitions? Colin -- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Colin Law
2010-May-12 12:34 UTC
Re: Re: In development mode not all types are included in the query related to type
On 12 May 2010 13:33, Colin Law <clanlaw@googlemail.com> wrote:> On 12 May 2010 12:56, Neeraj Singh <neerajdotname@gmail.com> wrote: >>> Since you have deleted all of the original post and my comments the >>> above now makes no sense. No-one reading this will know what your >>> problem is without going back to the previous mail, which is something >>> one should not normally be forced to do. >> >> Extremely sorry about that. I have created a gist which explains the >> problem much more succintly. >> http://gist.github.com/398486 > > What are the names of the rb files containing the class definitions?Also what version of rails? Colin -- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Mislav Marohnić
2010-May-12 12:50 UTC
Re: Re: In development mode not all types are included in the query related to type
Isn''t the problem obvious? ActiveRecord cannot list all subclasses under STI until it loads all modes in the app. In development mode it relies on autoloading and never preloads all models. The local solution: require statements in the end of "user.rb": require ''manager'' require ''agent'' So when User is preloaded, all subclasses will get loaded and be known to ActiveRecord too. The global solution: ActiveRecord shouldn''t rely on obtaining a list of all subclasses. Instead, when you query on a parent model, it shouldn''t specify any classes at all. Thus: User.all # SELECT * FROM users However, this is not adequate with complex STI schemes where there are grandchildren. If we''re querying on a child that has subclasses, we still have to know what they are: Manager.all # SELECT * from users WHERE users.type = ''Manager'' # OR users.type = ''EvilManager'' OR users.type = ''GoodManager'' On Wed, May 12, 2010 at 14:34, Colin Law <clanlaw@googlemail.com> wrote:> > What are the names of the rb files containing the class definitions? > > Also what version of rails? > > Colin > > -- > You received this message because you are subscribed to the Google Groups > "Ruby on Rails: Core" group. > To post to this group, send email to rubyonrails-core@googlegroups.com. > To unsubscribe from this group, send email to > rubyonrails-core+unsubscribe@googlegroups.com<rubyonrails-core%2Bunsubscribe@googlegroups.com> > . > For more options, visit this group at > http://groups.google.com/group/rubyonrails-core?hl=en. > >-- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Colin Law
2010-May-12 12:57 UTC
Re: Re: In development mode not all types are included in the query related to type
On 12 May 2010 13:50, Mislav Marohnić <mislav.marohnic@gmail.com> wrote:> Isn''t the problem obvious? ActiveRecord cannot list all subclasses under STI > until it loads all modes in the app. In development mode it relies on > autoloading and never preloads all models. > The local solution: require statements in the end of "user.rb": > require ''manager'' > require ''agent'' > So when User is preloaded, all subclasses will get loaded and be known to > ActiveRecord too. > The global solution: ActiveRecord shouldn''t rely on obtaining a list of all > subclasses. Instead, when you query on a parent model, it shouldn''t specify > any classes at all. Thus: > User.all > # SELECT * FROM users > However, this is not adequate with complex STI schemes where there are > grandchildren. If we''re querying on a child that has subclasses, we still > have to know what they are: > Manager.all > # SELECT * from users WHERE users.type = ''Manager'' > # OR users.type = ''EvilManager'' OR users.type = ''GoodManager''Can you explain why when the OP does Agent.find_by_name ''agent'' it generates SELECT "users".* FROM "users" WHERE (("users"."type" = ''Agent'' OR "users"."type" = ''SuperAgent'')) AND ("users"."name" = ''agent'') LIMIT 1 I would have expected only type Agent to be allowed, it appears to be returning SuperAgents also. If the user of name ''agent'' is actually a SuperAgent I would not expect Agent.find_by_name to find it. Note that both Agent and SuperAgent are directly derived from User. Unless the OP is leading us astray. Colin> On Wed, May 12, 2010 at 14:34, Colin Law <clanlaw@googlemail.com> wrote: >> >> > What are the names of the rb files containing the class definitions? >> >> Also what version of rails? >> >> Colin >> >> -- >> You received this message because you are subscribed to the Google Groups >> "Ruby on Rails: Core" group. >> To post to this group, send email to rubyonrails-core@googlegroups.com. >> To unsubscribe from this group, send email to >> rubyonrails-core+unsubscribe@googlegroups.com. >> For more options, visit this group at >> http://groups.google.com/group/rubyonrails-core?hl=en. >> > > -- > You received this message because you are subscribed to the Google Groups > "Ruby on Rails: Core" group. > To post to this group, send email to rubyonrails-core@googlegroups.com. > To unsubscribe from this group, send email to > rubyonrails-core+unsubscribe@googlegroups.com. > For more options, visit this group at > http://groups.google.com/group/rubyonrails-core?hl=en. >-- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Neeraj Singh
2010-May-12 13:50 UTC
Re: In development mode not all types are included in the query related to type
User.find_by_name ''agent'' generates a sql that does not use Agent or SuperAgent even if they are loaded. However the behavior of Agent.find_by_name ''agent'' is different if SuperAgent is loaded. @Colin: SuperAgent should be a subclass of Agent. I have updated the gist with this info. @Mislav: Yes the problem is obvious. That''s why I am asking if it is something that needs to be fixed or it is okay the way it is. If it is something that needs no fixing then ticket #4516 can be marked as wontfix. On May 12, 8:57 am, Colin Law <clan...@googlemail.com> wrote:> On 12 May 2010 13:50, Mislav Marohnić <mislav.maroh...@gmail.com> wrote: > > > > > > > Isn''t the problem obvious? ActiveRecord cannot list all subclasses under STI > > until it loads all modes in the app. In development mode it relies on > > autoloading and never preloads all models. > > The local solution: require statements in the end of "user.rb": > > require ''manager'' > > require ''agent'' > > So when User is preloaded, all subclasses will get loaded and be known to > > ActiveRecord too. > > The global solution: ActiveRecord shouldn''t rely on obtaining a list of all > > subclasses. Instead, when you query on a parent model, it shouldn''t specify > > any classes at all. Thus: > > User.all > > # SELECT * FROM users > > However, this is not adequate with complex STI schemes where there are > > grandchildren. If we''re querying on a child that has subclasses, we still > > have to know what they are: > > Manager.all > > # SELECT * from users WHERE users.type = ''Manager'' > > # OR users.type = ''EvilManager'' OR users.type = ''GoodManager'' > > Can you explain why when the OP does > Agent.find_by_name ''agent'' > it generates > SELECT "users".* FROM "users" WHERE (("users"."type" = ''Agent'' OR > "users"."type" = ''SuperAgent'')) AND ("users"."name" = ''agent'') LIMIT 1 > > I would have expected only type Agent to be allowed, it appears to be > returning SuperAgents also. If the user of name ''agent'' is actually a > SuperAgent I would not expect Agent.find_by_name to find it. Note > that both Agent and SuperAgent are directly derived from User. Unless > the OP is leading us astray. > > Colin > > > > > > > On Wed, May 12, 2010 at 14:34, Colin Law <clan...@googlemail.com> wrote: > > >> > What are the names of the rb files containing the class definitions? > > >> Also what version of rails? > > >> Colin > > >> -- > >> You received this message because you are subscribed to the Google Groups > >> "Ruby on Rails: Core" group. > >> To post to this group, send email to rubyonrails-core@googlegroups.com. > >> To unsubscribe from this group, send email to > >> rubyonrails-core+unsubscribe@googlegroups.com. > >> For more options, visit this group at > >>http://groups.google.com/group/rubyonrails-core?hl=en. > > > -- > > You received this message because you are subscribed to the Google Groups > > "Ruby on Rails: Core" group. > > To post to this group, send email to rubyonrails-core@googlegroups.com. > > To unsubscribe from this group, send email to > > rubyonrails-core+unsubscribe@googlegroups.com. > > For more options, visit this group at > >http://groups.google.com/group/rubyonrails-core?hl=en. > > -- > You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. > To post to this group, send email to rubyonrails-core@googlegroups.com. > To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. > For more options, visit this group athttp://groups.google.com/group/rubyonrails-core?hl=en.-- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Xavier Noria
2010-May-12 13:54 UTC
Re: Re: In development mode not all types are included in the query related to type
In general, if you have grandchildren you need to load them to ensure they are known. I compute them this way: http://gist.github.com/274219 The bottom line is that Active Record needs to know the STI hierarchy that is relevant to any given query. That just does not play nice with autoloading, it is a trade-off. -- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Colin Law
2010-May-12 14:12 UTC
Re: Re: In development mode not all types are included in the query related to type
On 12 May 2010 14:50, Neeraj Singh <neerajdotname@gmail.com> wrote:> User.find_by_name ''agent'' generates a sql that does not use Agent or > SuperAgent even if they are loaded. > > However the behavior of Agent.find_by_name ''agent'' is different if > SuperAgent is loaded. > > @Colin: SuperAgent should be a subclass of Agent. I have updated the > gist with this info.So you _were_ leading us astray. It is not surprising that I was confused by the results you were seeing. I think Mislav''s reply covers it in that case. Colin -- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Matt Jones
2010-May-12 14:29 UTC
Re: Re: In development mode not all types are included in the query related to type
On Wed, May 12, 2010 at 8:50 AM, Mislav Marohnić <mislav.marohnic@gmail.com> wrote:> Isn''t the problem obvious? ActiveRecord cannot list all subclasses under STI > until it loads all modes in the app. In development mode it relies on > autoloading and never preloads all models. > The local solution: require statements in the end of "user.rb": > require ''manager'' > require ''agent'' > So when User is preloaded, all subclasses will get loaded and be known to > ActiveRecord too.I''ve run across this before too, but I used something like this: %w(Admin Manager Candidate).each { |c| c.constantize } As I can never remember which one of require / require_dependency sometimes jams up (or used to back in the day) the autoloader. --Matt Jones -- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Mislav Marohnić
2010-May-12 14:36 UTC
Re: Re: In development mode not all types are included in the query related to type
When you''re querying a parent that doesn''t have any non-abstract parent (meaning he''s the top of the STI hierarchy), then theoretically you really don''t have to know the list of descendants. AR could just make a query without conditions. I think it would be a good addition to AR. Or am I missing some edge case? Are explicit conditions with list of classnames always required for some reason? On Wed, May 12, 2010 at 15:54, Xavier Noria <fxn@hashref.com> wrote:> In general, if you have grandchildren you need to load them to ensure > they are known. I compute them this way: > > http://gist.github.com/274219 > > The bottom line is that Active Record needs to know the STI hierarchy > that is relevant to any given query. That just does not play nice with > autoloading, it is a trade-off.-- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Xavier Noria
2010-May-12 14:51 UTC
Re: Re: In development mode not all types are included in the query related to type
On Wed, May 12, 2010 at 4:36 PM, Mislav Marohnić <mislav.marohnic@gmail.com> wrote:> When you''re querying a parent that doesn''t have any non-abstract parent > (meaning he''s the top of the STI hierarchy), then theoretically you really > don''t have to know the list of descendants. AR could just make a query > without conditions.Exactly, that is why in the last example in Neeraj''s gist there''s no conditions on the type column even if you load the subclasses: http://gist.github.com/398486 I added a couple of comments at the bottom. Neeraj these are just two techniques that do not match transparently. Do you see what is going on now? I think the ticket could be closed, but a warn about this gotcha could be helpful both in the API and guides. Santiago Pastorino is about to add it. -- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
Neeraj Singh
2010-May-12 15:21 UTC
Re: In development mode not all types are included in the query related to type
Thanks everyone for the input. I understand what''s going on now. I will mark ticket #4516 as invalid. On May 12, 10:51 am, Xavier Noria <f...@hashref.com> wrote:> On Wed, May 12, 2010 at 4:36 PM, Mislav Marohnić > > <mislav.maroh...@gmail.com> wrote: > > When you''re querying a parent that doesn''t have any non-abstract parent > > (meaning he''s the top of the STI hierarchy), then theoretically you really > > don''t have to know the list of descendants. AR could just make a query > > without conditions. > > Exactly, that is why in the last example in Neeraj''s gist there''s no > conditions on the type column even if you load the subclasses: > > http://gist.github.com/398486 > > I added a couple of comments at the bottom. > > Neeraj these are just two techniques that do not match > transparently. Do you see what is going on now? > > I think the ticket could be closed, but a warn about > this gotcha could be helpful both in the API and guides. Santiago > Pastorino is about to add it. > > -- > You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. > To post to this group, send email to rubyonrails-core@googlegroups.com. > To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. > For more options, visit this group athttp://groups.google.com/group/rubyonrails-core?hl=en.-- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.
matthewrudyjacobs@gmail.com
2010-May-13 05:33 UTC
Re: In development mode not all types are included in the query related to type
On May 12, 10:29 pm, Matt Jones <al2o...@gmail.com> wrote:> I''ve run across this before too, but I used something like this: > > %w(Admin Manager Candidate).each { |c| c.constantize } > > As I can never remember which one of require / require_dependency > sometimes jams up (or used to back in the day) the autoloader.I always use "require_dependency" I guess it''s more explicit that it will be reloaded in the future. https://gist.github.com/4db76a1dbce03f3e4435 But its really annoying when you forget to require one of these. I guess a simple approach would be doing the following on load CtiModel.all(:select => "type", :distinct => true).each{|model| model.type.constantize} thereby ensuring that all the types in the db were loaded (there may be some other subclass missing... but that wouldnt matter) -- You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group. To post to this group, send email to rubyonrails-core@googlegroups.com. To unsubscribe from this group, send email to rubyonrails-core+unsubscribe@googlegroups.com. For more options, visit this group at http://groups.google.com/group/rubyonrails-core?hl=en.