DRY out your database.yml
27 Jun 2006
While paging through my RSS aggregator this afternoon, I came across James Duncan Davidson’s article Conditional Rails Database Configuration. “Damn”, thought I, “ERb in the database.yml is a neat trick, but it’s so ugly!”
That reminded me of a little trick I’ve been using for as long as I can remember. I can’t take credit for this technique as I learned it from someone else… I just don’t remember who. Anyway, it goes a little something like this:
login: &login
adapter: mysql
username: username
password: password
host: mysql.example.com
development:
<<: *login
database: app_dev
test:
<<: *login
database: app_test
production:
<<: *login
database: app_prod
That’s a pretty standard Rails database.yml, all DRYed out. Like I said, I’ve been doing this forever but I rarely see it in other apps.
To extend on James’ post, here’s what his example would look like if you follow this technique:
common: &common
adapter: mysql
dev: &dev
<<: *common
username: root
<% if File.exist? "/opt/local/var/run/mysql5/mysqld.sock" %>
socket: /opt/local/var/run/mysql5/mysqld.sock
<% elsif File.exist? "/tmp/mysql.sock" %>
socket: /tmp/mysql.sock
<% end %>
development:
<<: *dev
database: birdy
test:
<<: *dev
database: birdy_test
production:
<<: *common
host: 10.0.1.24
<% if `uname -n`.strip == "staging" %>
database: birdy_stage
username: birdy_stage
password: somethingsecret
<% else %>
database: birdy
username: birdy
password: somethingelsethatissecret
<% end %>
Okay okay, it’s ugly for sure. But it’s functional and repetition has been removed where possible, making it less ugly than before. Of course you could get even trickier and tweak with the conditionals in the Production environment, but then you start getting into spaghetti ERb in your database.yml, which has got to be some sort of sin.
So there you go. I’d dearly love to see this method gain more popularity as it’s so much cleaner. I can’t be the only one whose development environment is close enough to his production environment to let this work!
Update: Matt says that Typo uses this scheme for their database.yml, which is likely where I first saw it. Jonathan mentions that this is also included in Rails Recipes, which I have to admit I’ve owned since the day it came out as a betabook but never actually looked at. Thanks, guys!
« go back