Skip to content

Instantly share code, notes, and snippets.

@mcfiredrill
Created July 12, 2013 17:53
Show Gist options
  • Save mcfiredrill/5986381 to your computer and use it in GitHub Desktop.
Save mcfiredrill/5986381 to your computer and use it in GitHub Desktop.

Overview

Replicate is a Gem that lets you dump and load relational objects between Ruby/Ruby on Rails environments, e.g. dump data from your production database and load it in your development database.

The examples given in the README are of shell scripts being used to do this. I wanted to use a Capistrano task because it keeps everything related to the production site in one place (particularly the config).

Note: This is tested on a relatively small data set yet it still took about 20 seconds to run - YMMV!

Usage

  • Add the code below to your config/deploy.rb
  • Alter the code = ENV["DATA"] || "User.all; Project.all" line to list all the data you want dumped by default
  • Run cap db:replicate to download all data from the production site
  • Run cap -e db:replicate to see the full usage instructions

Possible future improvements

  • Steam the data directly from the dumper to the loader instead of holding it in a temporary variable
  • Automatically dump all tables instead of requiring them to be listed manually
  • Improve the DATA variable parsing - currently this is not possible: Character.find_by_name(";") because the ; is treated as a command separator
namespace :db do
desc <<DESC
Replicates data from production site database to the local database.
By default all database objects are downloaded:
cap db:replicate
Set the DATA variable to specify the objects to download:
cap db:replicate DATA='User.find(1); Page.find(1)'
Dependant records are automatically downloaded by Replicate, e.g. this downloads
both the Project records and the User record:
cap db:replicate DATA='User.find_by_name("dave").projects'
To empty the local database first, set CLEAR=1:
cap db:replicate CLEAR=1
cap db:replicate CLEAR=1 DATA='User.all'
See https://github.com/rtomayko/replicate for more details about Replicate.
DESC
task :replicate, roles: :db, only: { primary: true } do
# Download data from the production database
# NOTE: YOU NEED TO ALTER THE LINE BELOW TO LIST ALL THE OBJECTS YOU WANT TO DUMP BY DEFAULT
code = ENV["DATA"] || "User.all; Project.all"
code = code.split(";").map{|c| c.strip.shellescape }.join(" ")
data = capture("cd #{latest_release} && RAILS_ENV=#{rails_env} bundle exec replicate -q -r '#{latest_release}/config/environment' -d #{code}")
# Clear the local database
system "rake db:schema:load" if ENV["CLEAR"] == "1"
# Load the data into the local database
require File.dirname(__FILE__) + '/../config/environment'
require 'replicate'
Replicate::Loader.new do |loader|
loader.log_to $stdout
loader.read StringIO.new(data)
end
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment