activeuuid – binary uuid primary keys in Rails 3.1 on MySQL

I’ve been debating a lot recently if I want to use NoSQL (Cassandra) for my next project or if I should just use MySQL. I plan to write a longer post on this soon, but for now I want to share with you a little gem I wrote.

I plan to use NoSQL in the not-too-distance future, but not today. When I port the data over I don’t want to have to map “old ids” to “new ids”. By using a uuid from day one I can easily maintain referential integrity when I migrate to a new datastore.

I looked up how this is typically done in Rails using MySQL and all I could find was examples that store the UUID as strings (e.g. here). The UUID is natively just 16 bytes so storing this in a VARCHAR(36) seemed like a poor solution. Ideally we would store the UUID as binary and let the ORM deal with translating it to and from a UUID object.

activeuuid solves this problem. activeuuid is a Rails plugin that will let you use UUIDTools::UUID objects as primary keys for your ActiveRecords and it stores them in MySQL as binary(16).

Here’s how to use it:

Create a Migration

activeuuid adds the uuid type to your migrations. Example:

class CreateEmails < ActiveRecord::Migration
  def self.up
    create_table :emails, :id => false  do |t|
      t.uuid :id, :unique => true
      t.uuid :sender_id  # belongs_to :sender
      t.string :subject
      t.text :body
      t.timestamp :sent_at
    add_index :emails, :id
  def self.down
    drop_table :emails

include ActiveUUID::UUID in your model

class Email < ActiveRecord::Base
  include ActiveUUID::UUID
  belongs_to :sender

use it

Here are some example specs:

require 'spec_helper'
describe Email do
  context "when using uuid's as keys" do
    before(:each) do
      @guid = "1dd74dd0-d116-11e0-99c7-5ac5d975667e"
      @e = => "hello", :body => "world") {|e| = UUIDTools::UUID.parse(@guid) }
    it "the id guid should be equal to the uuid" do eql(@guid)
    it "should be able to find an email by the uuid" do
      f = Email.find(UUIDTools::UUID.parse(@guid)) eql(@guid)


There are a number of benefits to using UUIDs as primary keys.:

  • no id conflict during multi-master write
  • no locking due to auto-increment
  • with time-based UUIDs you can store a timestamp within your UUID
  • you can create natural keys (based on the SHA of model attributes)

Future work

  • more transparent support for natural and composite keys
  • support for MySQLs `INSERT … ON DUPLICATE KEY UPDATE` syntax
  • support a primary column name other than `id`
  • work on other databases (Postgres, etc)
  • tests


Add this to your Gemfile

    gem "activeuuid"

Or get the code here:



Note that this depends on Rails 3.1 because it uses the custom column serialization added by Aaron Patterson. (See:

  • Reddit
  • Technorati
  • Twitter
  • Facebook
  • Google Bookmarks
  • HackerNews
  • PDF
  • RSS
This entry was posted in code, rails. Bookmark the permalink. Post a comment or leave a trackback: Trackback URL.