I think trying to do something like this through Rails will just complicate things. I will completely ignore some of the Rails stuff and just do it in SQL.
Your first step is to capture a full backup of your database. Then restore this backup to another database to:
- Make sure your backup is working.
- Give you a realistic playpen where you can make mistakes without consequences.
First, you want to clear your data by adding real foreign keys to match all your Rails associations. There is a good chance that some of your FKs will fail if you have to clear your broken links.
Now that you have clean data, rename all your tables to make room for new versions of UUIDs. For table t we will refer to the renamed table as t_tmp . For each t_tmp create another table to preserve the mapping from the old integer id to the new UUID id s, something like this:
create table t_id_map ( old_id integer not null, new_id uuid not null default uuid_generate_v1() )
and then fill it in:
insert into t_id_map (old_id) select id from t_tmp
And you probably want to index t_id_map.old_id while you are here.
This gives us old tables with integer ids and a lookup table for each t_tmp , which maps the old id to the new one.
Now create new tables with a UUID, replacing all the old integer and serial columns that contained id s; I would add real foreign keys at this point; you must be paranoid about your data: broken code is temporary, broken data is usually forever.
Filling in new tables is quite simple: just use the insert into ... select ... from and JOIN constructors in the corresponding t_id_map tables to match the old id with the new ones. After the data has been matched and copied, you will want to perform some health checks to make sure that everything makes sense. Then you can leave your tables t_tmp and t_id_map and continue your life.
Practice this process on a copy of your database script and you quit.
Of course, you want to close all applications that access your database while you do this work.
mu is too short
source share