I am modifying an existing open source rails 4.2 app and wanted to keep my changes (some of which are to models, some to controllers, some to views) as separate as I can, so that when a new release of the app comes out, I won’t be in (too much) merge hell.
This app was not designed to be extended, which makes things more interesting.
For the views, I’m just doing partials with a prefix (
For the models and controllers, I started out hacking the code directly, but after some digging around I discovered how to monkey patch (I believe that is what it is called) the classes.
config/application.rb file, I added the following code:
Dir.glob(Rails.root + "app/decorators/**/*_decorator*.rb").each do |c|
And then, if I want to make a change to
app/models/person.rb, I add the file
app/decorators/models/person_decorator.rb. In that file is something like this:
# ... changes
This lets me add additional relations, helper methods, and other classes to extend existing functionality. I try to prefix things with a unique identifier (
xxx_set_timezone rather than
set_timezone) to lessen the chances of a collision, because if a method is added to the
Person class with the same name as a method in the decorator, the decorator will win.
Write tests around this new functionality so that if anything changes, I’m aware and can more easily troubleshoot.
The downsides of this approach is that it is harder to track logic, because instead of everything in one file, it is now in two. (I don’t know if there are memory or performance implications.) However, that is a tradeoff I’m willing to make to make it easier to keep up with the upstream development and to pull said development in as often as possible.
I’m still fairly new to rails and didn’t know if this is the only or best way, but thought I’d share.