My “fix” for preserving timestamps on import with Laravel

Edit: This will not work on “updated_at” btw, for reasons that become obvious very quickly, but for my application, this is not an issue.

I’m currently re-developing a Coldfusion app in Laravel 4. Most of the current db tables have “createdat” and “updatedat” fields. I went thru the trouble of creating migrations for all of the db tables and then writing an Artisan command called “Import” that connects to a copy of the old db and imports all of the data into the new db created with the migrations that includes a few schema changes that are crosswalked over.

One of the problems with this is that the timestamp fields (“created_at” and “updated_at”) created by Laravel during migrations will be current(as in “now”) even if I try to map the old timestamps on import:

//no workie
$videogroup->created_at = $vg->createdat;

As a result, I lose important timestamp info. from my old database.

My new fix involves running the import as before:

$videogroups = DB::connection('mysql_vm_old')->select('select * from videogroups');
foreach ($videogroups as $vg) {
$videogroup = new VideoGroup;
...
$videogroup->save();

Except that I add this to the loop:

$videogroup->createdat  = $vg->createdat;

Then after the initial table import is complete, run:

$videogroups = VideoGroup::all();

//replace default timestamp value with the one from the old db
foreach ($videogroups as $vg) {
$vg->created_at = $vg->createdat;
$vg->save();
}

//get rid of the temporary 'createdat' column
Schema::table('videogroups', function($table)
{
$table->dropColumn('createdat');
});

This certainly adds more overhead to my import script for larger tables, and I’ve already had to increase mysql’s memory limit to handle the script as it’s grown, but once the site goes into production, I’ll no longer need the Import script.

As it stands now, I’m running the following on a daily basis as I make changes:

php artisan migrate:refresh --seed
php artisan import