Hey guys, I''ve been working on engines lately and I can''t understand why a class in an engine can''t be monkey patched. Here''s an example: In the engine: class MyEngine::MyController < ApplicationController def index @stuff = 1 end def show ... something happens ... end end In the app including the engine: class MyEngine::MyController < ApplicationController def index @stuff = 2 end end In this example I would expect for only the index method to be overriden, but it seems the entire class is overriden. Is there any reason for this behaviour? Is this a feature or a bug? Regards, Luís Ferreira -- 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.
Probably because of the way how Rails is looking for constants ? I would guess that it does not read the file from engine at all, and just reads the file from your app. Robert Pankowecki http://robert.pankowecki.pl On Fri, Sep 28, 2012 at 12:59 PM, Luís Ferreira <zamith.28@gmail.com> wrote:> Hey guys, > > I''ve been working on engines lately and I can''t understand why a class in > an engine can''t be monkey patched. Here''s an example: > > In the engine: > > class MyEngine::MyController < ApplicationController > def index > @stuff = 1 > end > > def show > ... something happens ... > end > end > > In the app including the engine: > > class MyEngine::MyController < ApplicationController > def index > @stuff = 2 > end > end > > In this example I would expect for only the index method to be overriden, > but it seems the entire class is overriden. Is there any reason for this > behaviour? Is this a feature or a bug? > > > Regards, > Luís Ferreira > > > > -- > 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.
Hum... Haven''t thought of that. Thanks. Still, this is not the expected behaviour for a ruby class right? Or am I completly wrong here? On Sep 28, 2012, at 12:02 PM, Robert Pankowecki wrote:> Probably because of the way how Rails is looking for constants ? I would guess that it does not read the file from engine at all, and just reads the file from your app. > > Robert Pankowecki > http://robert.pankowecki.pl > > On Fri, Sep 28, 2012 at 12:59 PM, Luís Ferreira <zamith.28@gmail.com> wrote: > Hey guys, > > I''ve been working on engines lately and I can''t understand why a class in an engine can''t be monkey patched. Here''s an example: > > In the engine: > > class MyEngine::MyController < ApplicationController > def index > @stuff = 1 > end > > def show > ... something happens ... > end > end > > In the app including the engine: > > class MyEngine::MyController < ApplicationController > def index > @stuff = 2 > end > end > > In this example I would expect for only the index method to be overriden, but it seems the entire class is overriden. Is there any reason for this behaviour? Is this a feature or a bug? > > > Regards, > Luís Ferreira > > > > -- > 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.Cumprimentos, Luís Ferreira -- 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.
Also, even if I change the load order of the app and engine and load the engine first the same thing happens. This way the engine''s file has already been loaded and then it is completly overriden. Maybe I''m missing something here, but this is the behavior I have experienced. On Sep 28, 2012, at 12:02 PM, Robert Pankowecki wrote:> Probably because of the way how Rails is looking for constants ? I would guess that it does not read the file from engine at all, and just reads the file from your app. > > Robert Pankowecki > http://robert.pankowecki.pl > > On Fri, Sep 28, 2012 at 12:59 PM, Luís Ferreira <zamith.28@gmail.com> wrote: > Hey guys, > > I''ve been working on engines lately and I can''t understand why a class in an engine can''t be monkey patched. Here''s an example: > > In the engine: > > class MyEngine::MyController < ApplicationController > def index > @stuff = 1 > end > > def show > ... something happens ... > end > end > > In the app including the engine: > > class MyEngine::MyController < ApplicationController > def index > @stuff = 2 > end > end > > In this example I would expect for only the index method to be overriden, but it seems the entire class is overriden. Is there any reason for this behaviour? Is this a feature or a bug? > > > Regards, > Luís Ferreira > > > > -- > 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.Cumprimentos, Luís Ferreira -- 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.
If you are using Rails 3.2, you can tell Rails to load your engine before it loads your app like so: config.railties_order = [ Your::Engine, :main_app, :all ] Then your monkey patching should work. If you are on older versions of Rails you can monkey patch AS::Dependencies like http://www.slideshare.net/AndyMaleh/rails-engine-patterns (Slide 17). You probably want to watch the whole talk by Andy Maleh here. Godfrey On 2012-09-28, at 4:14 AM, Luís Ferreira wrote:> Hum... Haven''t thought of that. Thanks. > > Still, this is not the expected behaviour for a ruby class right? Or am I completly wrong here? > On Sep 28, 2012, at 12:02 PM, Robert Pankowecki wrote: > >> Probably because of the way how Rails is looking for constants ? I would guess that it does not read the file from engine at all, and just reads the file from your app. >> >> Robert Pankowecki >> http://robert.pankowecki.pl >> >> On Fri, Sep 28, 2012 at 12:59 PM, Luís Ferreira <zamith.28@gmail.com> wrote: >> Hey guys, >> >> I''ve been working on engines lately and I can''t understand why a class in an engine can''t be monkey patched. Here''s an example: >> >> In the engine: >> >> class MyEngine::MyController < ApplicationController >> def index >> @stuff = 1 >> end >> >> def show >> ... something happens ... >> end >> end >> >> In the app including the engine: >> >> class MyEngine::MyController < ApplicationController >> def index >> @stuff = 2 >> end >> end >> >> In this example I would expect for only the index method to be overriden, but it seems the entire class is overriden. Is there any reason for this behaviour? Is this a feature or a bug? >> >> >> Regards, >> Luís Ferreira >> >> >> >> -- >> 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. > > Cumprimentos, > Luís Ferreira > > > > > -- > 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.
I just clicked thru those slides the other day too. Having developed engines locally bundled to other applications, the part he talks about continuous development, is a dream. I found that in Bundler 1.2 you can config a repo for local usage without changing the Gemfile too. http://gembundler.com/v1.2/whats_new.html Gem/engine authoring has never been so good :) - Ken On Sep 28, 2012, at 7:20 AM, Godfrey Chan <godfreykfc@gmail.com> wrote:> If you are using Rails 3.2, you can tell Rails to load your engine before it loads your app like so: > > config.railties_order = [ Your::Engine, :main_app, :all ] > > Then your monkey patching should work. > > If you are on older versions of Rails you can monkey patch AS::Dependencies like http://www.slideshare.net/AndyMaleh/rails-engine-patterns (Slide 17). You probably want to watch the whole talk by Andy Maleh here. > > Godfrey > > On 2012-09-28, at 4:14 AM, Luís Ferreira wrote: > >> Hum... Haven''t thought of that. Thanks. >> >> Still, this is not the expected behaviour for a ruby class right? Or am I completly wrong here? >> On Sep 28, 2012, at 12:02 PM, Robert Pankowecki wrote: >> >>> Probably because of the way how Rails is looking for constants ? I would guess that it does not read the file from engine at all, and just reads the file from your app. >>> >>> Robert Pankowecki >>> http://robert.pankowecki.pl >>> >>> On Fri, Sep 28, 2012 at 12:59 PM, Luís Ferreira <zamith.28@gmail.com> wrote: >>> Hey guys, >>> >>> I''ve been working on engines lately and I can''t understand why a class in an engine can''t be monkey patched. Here''s an example: >>> >>> In the engine: >>> >>> class MyEngine::MyController < ApplicationController >>> def index >>> @stuff = 1 >>> end >>> >>> def show >>> ... something happens ... >>> end >>> end >>> >>> In the app including the engine: >>> >>> class MyEngine::MyController < ApplicationController >>> def index >>> @stuff = 2 >>> end >>> end >>> >>> In this example I would expect for only the index method to be overriden, but it seems the entire class is overriden. Is there any reason for this behaviour? Is this a feature or a bug? >>> >>> >>> Regards, >>> Luís Ferreira >>> >>> >>> >>> -- >>> 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. >> >> Cumprimentos, >> Luís Ferreira >> >> >> >> >> -- >> 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.
Also, you might want to use class_eval for monkey patching. This way it errors out if the original implementation has not been loaded yet, so you''ll know something has gone wrong. See here - http://practicalruby.blogspot.com/2007/02/reopen-with-moduleeval.html Godfrey On 2012-09-28, at 4:20 AM, Godfrey Chan wrote:> If you are using Rails 3.2, you can tell Rails to load your engine before it loads your app like so: > > config.railties_order = [ Your::Engine, :main_app, :all ] > > Then your monkey patching should work. > > If you are on older versions of Rails you can monkey patch AS::Dependencies like http://www.slideshare.net/AndyMaleh/rails-engine-patterns (Slide 17). You probably want to watch the whole talk by Andy Maleh here. > > Godfrey > > On 2012-09-28, at 4:14 AM, Luís Ferreira wrote: > >> Hum... Haven''t thought of that. Thanks. >> >> Still, this is not the expected behaviour for a ruby class right? Or am I completly wrong here? >> On Sep 28, 2012, at 12:02 PM, Robert Pankowecki wrote: >> >>> Probably because of the way how Rails is looking for constants ? I would guess that it does not read the file from engine at all, and just reads the file from your app. >>> >>> Robert Pankowecki >>> http://robert.pankowecki.pl >>> >>> On Fri, Sep 28, 2012 at 12:59 PM, Luís Ferreira <zamith.28@gmail.com> wrote: >>> Hey guys, >>> >>> I''ve been working on engines lately and I can''t understand why a class in an engine can''t be monkey patched. Here''s an example: >>> >>> In the engine: >>> >>> class MyEngine::MyController < ApplicationController >>> def index >>> @stuff = 1 >>> end >>> >>> def show >>> ... something happens ... >>> end >>> end >>> >>> In the app including the engine: >>> >>> class MyEngine::MyController < ApplicationController >>> def index >>> @stuff = 2 >>> end >>> end >>> >>> In this example I would expect for only the index method to be overriden, but it seems the entire class is overriden. Is there any reason for this behaviour? Is this a feature or a bug? >>> >>> >>> Regards, >>> Luís Ferreira >>> >>> >>> >>> -- >>> 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. >> >> Cumprimentos, >> Luís Ferreira >> >> >> >> >> -- >> 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.
Thanks for the quick response. As I''ve said, even if I change the loading order it still won''t work. I''ll try class_eval but still I don''t understand why the monkey patching does not work. Is it a feature of the engine that it has an all or nothing overriding of classes? On Sep 28, 2012, at 12:27 PM, Godfrey Chan wrote:> Also, you might want to use class_eval for monkey patching. This way it errors out if the original implementation has not been loaded yet, so you''ll know something has gone wrong. See here - http://practicalruby.blogspot.com/2007/02/reopen-with-moduleeval.html > > Godfrey > > On 2012-09-28, at 4:20 AM, Godfrey Chan wrote: > >> If you are using Rails 3.2, you can tell Rails to load your engine before it loads your app like so: >> >> config.railties_order = [ Your::Engine, :main_app, :all ] >> >> Then your monkey patching should work. >> >> If you are on older versions of Rails you can monkey patch AS::Dependencies like http://www.slideshare.net/AndyMaleh/rails-engine-patterns (Slide 17). You probably want to watch the whole talk by Andy Maleh here. >> >> Godfrey >> >> On 2012-09-28, at 4:14 AM, Luís Ferreira wrote: >> >>> Hum... Haven''t thought of that. Thanks. >>> >>> Still, this is not the expected behaviour for a ruby class right? Or am I completly wrong here? >>> On Sep 28, 2012, at 12:02 PM, Robert Pankowecki wrote: >>> >>>> Probably because of the way how Rails is looking for constants ? I would guess that it does not read the file from engine at all, and just reads the file from your app. >>>> >>>> Robert Pankowecki >>>> http://robert.pankowecki.pl >>>> >>>> On Fri, Sep 28, 2012 at 12:59 PM, Luís Ferreira <zamith.28@gmail.com> wrote: >>>> Hey guys, >>>> >>>> I''ve been working on engines lately and I can''t understand why a class in an engine can''t be monkey patched. Here''s an example: >>>> >>>> In the engine: >>>> >>>> class MyEngine::MyController < ApplicationController >>>> def index >>>> @stuff = 1 >>>> end >>>> >>>> def show >>>> ... something happens ... >>>> end >>>> end >>>> >>>> In the app including the engine: >>>> >>>> class MyEngine::MyController < ApplicationController >>>> def index >>>> @stuff = 2 >>>> end >>>> end >>>> >>>> In this example I would expect for only the index method to be overriden, but it seems the entire class is overriden. Is there any reason for this behaviour? Is this a feature or a bug? >>>> >>>> >>>> Regards, >>>> Luís Ferreira >>>> >>>> >>>> >>>> -- >>>> 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. >>> >>> Cumprimentos, >>> Luís Ferreira >>> >>> >>> >>> >>> -- >>> 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.Cumprimentos, Luís Ferreira -- 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.