The title sucks but its the best I could think of. I have three scripts (that should probably be one, but I worked on and debugged them individualy so this is how they are. ;) They could certainly be coded better but here is a start in case anyone else out there is going through the agony of a migration from Oracle to MySQL.All DB connections will need to setup for your connection settings.
The first script updates empty date/datetime fields to NULL.
use strict;
use warnings;
use DBI;
use Data::Dumper;
my $dbh = DBI->connect() or die DBI->errstr;
my $tables = [@ARGV];
$tables =$dbh->selectcol_arrayref("show tables;") unless defined @$tables;
for my $table (@$tables) {
print "Checking $table ... ";
my $cols = $dbh->selectall_arrayref("describe $table",{Slice=>{}});
my @dates = grep { $_->{Type} =~ /date/ } @$cols;
# print Dumper(@dates);
for my $col (@dates) {
my $field = $col->{Field};
my $count = $dbh->do("UPDATE `$table` SET `$field` = NULL WHERE `$field` = '0000-00-00';");
print "fixed '$field' ($count) ... ";
}
print " done.\n";
# die;
}
The second updates timestamp fields to the current time. This is because clients don't seem to like 0 in the timestamps and updateing to NOW() seemed safe.
use strict;
use warnings;
use DBI;
use Data::Dumper;
my $dbh = DBI->connect() or die DBI->errstr;
my $tables = [@ARGV];
$tables =$dbh->selectcol_arrayref("show tables;") unless defined @$tables;
for my $table (@$tables) {
print "Checking $table ... ";
my $cols = $dbh->selectall_arrayref("describe $table",{Slice=>{}});
my @dates = grep { $_->{Type} =~ /timestamp/ } @$cols;
# print Dumper(@dates);
for my $col (@dates) {
my $field = $col->{Field};
my $count = $dbh->do("UPDATE `$table` SET `$field` = NOW() WHERE `$field` = '0000-00-00 00:00:00';");
print "fixed '$field' ($count) ... " if $count > 0;
}
print " done.\n";
# die;
}
And the third the script checks all date/datetime fields and finds records with a day >28. It then makes sure that it is a valid date, and sets it to NULL if it is not.
use strict;
use warnings;
use DBI;
use Data::Dumper;
my $dbh = DBI->connect() or die DBI->errstr;
my $tables = [@ARGV];
$tables =$dbh->selectcol_arrayref("show tables;") unless defined @$tables;
for my $table (@$tables) {
print "Checking $table ... ";
my $cols = $dbh->selectall_arrayref("describe $table",{Slice=>{}});
my @dates = grep { $_->{Type} =~ /timestamp/ } @$cols;
# print Dumper(@dates);
for my $col (@dates) {
my $field = $col->{Field};
my $count = $dbh->do("UPDATE `$table` SET `$field` = NOW() WHERE `$field` = '0000-00-00 00:00:00';");
print "fixed '$field' ($count) ... " if $count > 0;
}
print " done.\n";
# die;
}
These are all noisy scripts that output a bit of info that is nice if you are fighting your way through thousands of migration errors like I was. The scripts automaticaly scan every colum in every table, it is not fast but it does work. I know they could fairly easily be combined into one script but they each server a specific use so I left them alone. BTW you can call any one of them with a list of tables you want it to run on if you are focused on a specific set of tables.
Hopefully this will save someone else all the trouble i went through discovering these issues. Enjoy!
perlmonks.org content © perlmonks.org and eric256
prlmnks.org © 2006 edmund von der burg (eccles & toad)
v 0.03