Rambling Labs Blog Ramblings on software development

  • Stripping down Rails 3.1: Using only the database migrations

    The current project I'm working on is not using Ruby on Rails, but I still want to use ActiveRecord Migrations for the database changes.

    There are some options out there for this, and most people that I read about and had this issue just use the activerecord gem and set up their rake tasks.

    I don't want to write my own rake tasks, since I feel that I would be reinventing the wheel. So what did I do? I created a new rails application, and stripped it down, removing everything that is not needed to run the migrations.

    First, I created a rails application called 'deploy' on the root folder of the application with:

    rails new deploy

    Then, I removed all the directories in the deploy folder, except for these:

    • config
    • db
    • lib
    • log
    • script

    So far so good. The only uncomfortable thing now is that I have to enter to the deploy directory to run bundle install or rake db:migrate. To solve this issue, I did the following:

    I added this Gemfile to the root directory of the application:

    source 'http://rubygems.org'
    gem 'git-deploy'

    gemfile = File.open(File.join(File.dirname(__FILE__), 'deploy', 'Gemfile'))
    eval gemfile.read

    And this Rakefile as well:

    rakefile = File.open(File.join(File.dirname(__FILE__), 'deploy', 'Rakefile'))
    eval rakefile.read.gsub(/config/, 'deploy/config')
    task :generate do
      arguments = ARGV.find { |a| a.start_with?('GENERATE=') }
      arguments = arguments.split('=')[1] unless arguments.nil?
      sh "cd deploy; rails generate #{arguments}" unless arguments.nil? or arguments.empty?
    db_tasks_file = File.open(File.join(File.dirname(__FILE__), 'deploy', 'lib', 'tasks', 'db.rb'))
    db_tasks = db_tasks_file.read
    namespace :db do
      namespaces = [:test, :production]
      namespaces.each do |name|
        namespace name do
          eval db_tasks.gsub(/{environment}/, name.to_s)

    This is the lib/tasks/db.rb being included in the Rakefile:

    tasks = [:create, :drop, :migrate, :rollback, :version, :seed, :setup]
    tasks.each do |name|
      task name do
        sh "rake db:#{name.to_s} RAILS_ENV={environment}"

    As you can see I added some rake dynamic tasks to manage the migrations in the development, test and production environments from the root directory of the application.

    Now, I can run bundle install and rake whatever from my usual working directory.

    That's all folks!

  • blog comments powered by Disqus