DEV Community

Adam Rogers
Adam Rogers

Posted on

Updating Rails applications with vimdiff

This is probably one of those things everyone knows about, but I only just figured it out, so here it is for the next person (likely me, six months from now).

Ever run bin/rails app:update, been greeted with this:

   identical  config/boot.rb
       exist  config
    conflict  config/application.rb
Overwrite /home/rodreegez/Projects/my-app/config/application.rb? (enter "h" for help) [Ynaqdhm]
Enter fullscreen mode Exit fullscreen mode

...and wondered what to do?

Y will overwrite your existing file with the new one. d will show you the diff between your existing file and the new one. But what if you want the new stuff but also keep your changes?

vimdiff to the rescue.

The option we're looking for is m for merge. To use it, we have to set the THOR_MERGE environment variable and tell it which tool to use to show the diff.

Let's cancel out of the update process we just started and try again, this time with vimdiff:

THOR_MERGE=vimdiff bin/rails app:update
Enter fullscreen mode Exit fullscreen mode

This time, when we press the m key, vimdiff will spring into life. It might look something like this:

vimdiff in action

In the diff we can see that I have made some changes to application.rb (on the right - my additions are highlighted in green) and I'd like to keep those.

The goal of this exercise is to make both of these files the same. We do that by :diffgeting and :difputing changes - diffget "gets" the corresponding change from the other file, while diffput "puts" the change from this file to the other one.

Many changes will be of little consequence - strings being changed from single to double quotes, for example - but some will require a bit of thought.

Both commands work from the perspective of the window we're currently in. I tend to think it's easier to think about if I ctrl-w over to "my" version of the file and get and put changes from there.

Every time we diffget or diffput a change, that change will disappear and we're free to cursor down to the next highlighted change. Once there are no more changes left we can :wqa which will save and quit everything, and our update script will move on to the next file.

Rinse and repeat with all the files that bin/rails app:update touches and, by the end of it, you'll have a nice and up-to-date Rails application with all your customisations, personalisations and preferences still intact.

Don't forget to configure any new framework defaults and check for any further changes you might need to make. And, of course, make sure your tests still pass.

Top comments (0)