Trailing WS crusade - got to save them bits
[dbsrgits/DBIx-Class.git] / t / 71mysql.t
index 01c32d8..3ed8493 100644 (file)
@@ -3,11 +3,18 @@ use warnings;
 
 use Test::More;
 use Test::Exception;
+
+use DBI::Const::GetInfoType;
+use Scalar::Util qw/weaken/;
+use DBIx::Class::Optional::Dependencies ();
+
 use lib qw(t/lib);
 use DBICTest;
-use DBI::Const::GetInfoType;
 use DBIC::SqlMakerTest;
 
+plan skip_all => 'Test needs ' . DBIx::Class::Optional::Dependencies->req_missing_for ('test_rdbms_mysql')
+  unless DBIx::Class::Optional::Dependencies->req_ok_for ('test_rdbms_mysql');
+
 my ($dsn, $user, $pass) = @ENV{map { "DBICTEST_MYSQL_${_}" } qw/DSN USER PASS/};
 
 #warn "$dsn $user $pass";
@@ -45,7 +52,7 @@ $dbh->do("CREATE TABLE books (id INTEGER NOT NULL AUTO_INCREMENT PRIMARY KEY, so
 
 #'dbi:mysql:host=localhost;database=dbic_test', 'dbic_test', '');
 
-# make sure sqlt_type overrides work (::Storage::DBI::mysql does this) 
+# make sure sqlt_type overrides work (::Storage::DBI::mysql does this)
 {
   my $schema = DBICTest::Schema->connect($dsn, $user, $pass);
 
@@ -85,6 +92,16 @@ lives_ok {
   });
 } 'Limited FOR UPDATE select works';
 
+# shared-lock
+lives_ok {
+  $schema->txn_do (sub {
+    isa_ok (
+      $schema->resultset('Artist')->find({artistid => 1}, {for => 'shared'}),
+      'DBICTest::Schema::Artist',
+    );
+  });
+} 'LOCK IN SHARE MODE select works';
+
 my $test_type_info = {
     'artistid' => {
         'data_type' => 'INT',
@@ -127,7 +144,7 @@ $schema->populate ('BooksInLibrary', [
 ]);
 
 #
-# try a distinct + prefetch on tables with identically named columns 
+# try a distinct + prefetch on tables with identically named columns
 # (mysql doesn't seem to like subqueries with equally named columns)
 #
 
@@ -263,7 +280,6 @@ NULLINSEARCH: {
   my $ansi_schema = DBICTest::Schema->connect ($dsn, $user, $pass, {
     on_connect_call => 'set_strict_mode',
     quote_char => '`',
-    name_sep => '.'
   });
   my $rs = $ansi_schema->resultset('CD');
 
@@ -322,7 +338,7 @@ ZEROINSEARCH: {
     'Zero-year groups successfully',
   );
 
-  # convoluted search taken verbatim from list 
+  # convoluted search taken verbatim from list
   my $restrict_rs = $rs->search({ -and => [
     year => { '!=', 0 },
     year => { '!=', undef }
@@ -335,13 +351,78 @@ ZEROINSEARCH: {
   );
 }
 
-## If find() is the first query after connect()
-## DBI::Storage::sql_maker() will be called before
-## _determine_driver() and so the ::SQLHacks class for MySQL
-## will not be used
+# make sure find hooks determine driver
+{
+  my $schema = DBICTest::Schema->connect($dsn, $user, $pass);
+  $schema->resultset("Artist")->find(4);
+  isa_ok($schema->storage->sql_maker, 'DBIx::Class::SQLMaker::MySQL');
+}
+
+# make sure the mysql_auto_reconnect buggery is avoided
+{
+  local $ENV{MOD_PERL} = 'boogiewoogie';
+  my $schema = DBICTest::Schema->connect($dsn, $user, $pass);
+  ok (! $schema->storage->_get_dbh->{mysql_auto_reconnect}, 'mysql_auto_reconnect unset regardless of ENV' );
+
+  # Make sure hardcore forking action still works even if mysql_auto_reconnect
+  # is true (test inspired by ether)
+
+  my $schema_autorecon = DBICTest::Schema->connect($dsn, $user, $pass, { mysql_auto_reconnect => 1 });
+  my $orig_dbh = $schema_autorecon->storage->_get_dbh;
+  weaken $orig_dbh;
 
-my $schema2 = DBICTest::Schema->connect($dsn, $user, $pass);
-$schema2->resultset("Artist")->find(4);
-isa_ok($schema2->storage->sql_maker, 'DBIx::Class::SQLMaker::MySQL');
+  ok ($orig_dbh, 'Got weak $dbh ref');
+  ok ($orig_dbh->{mysql_auto_reconnect}, 'mysql_auto_reconnect is properly set if explicitly requested' );
+
+  my $rs = $schema_autorecon->resultset('Artist');
+
+  my $pid = fork();
+  if (! defined $pid ) {
+    die "fork() failed: $!"
+  }
+  elsif ($pid) {
+    # sanity check
+    $schema_autorecon->storage->dbh_do(sub {
+      is ($_[1], $orig_dbh, 'Storage holds correct $dbh in parent');
+    });
+
+    # kill our $dbh
+    $schema_autorecon->storage->_dbh(undef);
+
+    TODO: {
+      local $TODO = "Perl $] is known to leak like a sieve"
+        if DBIx::Class::_ENV_::PEEPEENESS();
+
+      ok (! defined $orig_dbh, 'Parent $dbh handle is gone');
+    }
+  }
+  else {
+    # wait for parent to kill its $dbh
+    sleep 1;
+
+    #simulate a  subtest to not confuse the parent TAP emission
+    Test::More->builder->reset;
+    Test::More->builder->plan('no_plan');
+    Test::More->builder->_indent(' ' x 4);
+
+    # try to do something dbic-esque
+    $rs->create({ name => "Hardcore Forker $$" });
+
+
+    TODO: {
+      local $TODO = "Perl $] is known to leak like a sieve"
+        if DBIx::Class::_ENV_::PEEPEENESS();
+
+      ok (! defined $orig_dbh, 'DBIC operation triggered reconnect - old $dbh is gone');
+    }
+
+    exit 0;
+  }
+
+  wait;
+  ok(!$?, 'Child subtests passed');
+
+  ok ($rs->find({ name => "Hardcore Forker $pid" }), 'Expected row created');
+}
 
 done_testing;