#!/usr/bin/perl -w use strict; use Test::More tests => 1 + (2 * 13); BEGIN { require 't/test-lib.pl'; use_ok('Rose::DB::Object::Loader'); } our %Have; # # Tests # #$Rose::DB::Object::Manager::Debug = 1; foreach my $db_type (qw(pg mysql)) { SKIP: { skip("$db_type tests", 13) unless($Have{$db_type}); } next unless($Have{$db_type}); Rose::DB->default_type($db_type); my $class_prefix = ucfirst($db_type); my $loader = Rose::DB::Object::Loader->new( db => Rose::DB->new, class_prefix => $class_prefix); my @classes = $loader->make_classes(include_tables => '^rose_db_object_test$'); my $object_class = $class_prefix . '::RoseDbObjectTest'; my $manager_class = $object_class . '::Manager'; my $data = "\000\001\002\003\004\005" x 10; # Standard save my $o = $object_class->new(num => 123, data => $data); $o->save; $o = $object_class->new(id => $o->id)->load; is($o->data, $data, "save 1 - $db_type"); $o->save; $o = $object_class->new(id => $o->id)->load; is($o->data, $data, "save 2 - $db_type"); # Changes only my $short_data = "\000\001\002\003\004\005"; $o->data($short_data); $o->save(changes_only => 1); $o = $object_class->new(id => $o->id)->load; is($o->data, $short_data, "update changes only - $db_type"); $o = $object_class->new(data => $short_data); $o->save(changes_only => 1); $o = $object_class->new(id => $o->id)->load; is($o->data, $short_data, "insert changes only - $db_type"); # On duplicate key update if($o->db->supports_on_duplicate_key_update) { # Force the bind_param code to be triggered (should be harmless) local $object_class->meta->{'dbi_requires_bind_param'}{$o->db->{'id'}} = 1; my $data = "\000\001\002"; $o->data($data); $o->insert(on_duplicate_key_update => 1); $o = $object_class->new(id => $o->id)->load; is($o->data, $data, "on duplicate key update - $db_type"); } else { ok(1, "on duplicate key update not supported - $db_type"); } # # Allow inline column values # $object_class->meta->allow_inline_column_values(1); $manager_class->delete_rose_db_object_test(all => 1); $data = "\000\001\002\003\004\005" x 10; # Standard save $o = $object_class->new(num => 123, data => $data); $o->save; $o = $object_class->new(id => $o->id)->load; is($o->data, $data, "inline - save 1 - $db_type"); $o->save; $o = $object_class->new(id => $o->id)->load; is($o->data, $data, "inline - save 2 - $db_type"); # Changes only $short_data = "\000\001\002\003\004\005"; $o->data($short_data); $o->save(changes_only => 1); $o = $object_class->new(id => $o->id)->load; is($o->data, $short_data, "inline - update changes only - $db_type"); $o = $object_class->new(data => $short_data); $o->save(changes_only => 1); $o = $object_class->new(id => $o->id)->load; is($o->data, $short_data, "inline - insert changes only - $db_type"); # On duplicate key update if($o->db->supports_on_duplicate_key_update) { # Force the bind_param code to be triggered (should be harmless) local $object_class->meta->{'dbi_requires_bind_param'}{$o->db->{'id'}} = 1; my $data = "\000\001\002"; $o->data($data); $o->insert(on_duplicate_key_update => 1); $o = $object_class->new(id => $o->id)->load; is($o->data, $data, "inline - on duplicate key update - $db_type"); } else { ok(1, "inline - on duplicate key update not supported - $db_type"); } # # Manager # my $os = $manager_class->get_rose_db_object_test( query => [ data => $o->data, id => $o->id ]); ok($os && @$os == 1 && $os->[0]->id == $o->id, "manager 1 - $db_type"); $os = $manager_class->get_rose_db_object_test( query => [ data => [ "\000\001", $o->data ], or => [ data => [ "\000\002", $o->data ], id => { ne => [ 123, 456 ] }, ], id => $o->id ]); ok($os && @$os == 1 && $os->[0]->id == $o->id, "manager 2 - $db_type"); #local $Rose::DB::Object::Manager::Debug = 1; $os = $manager_class->get_rose_db_object_test( query => [ data => [ "\000\001", $o->data ], num => undef, or => [ data => [ "\000\002", $o->data ], id => { ne => [ 123, 456 ] }, or => [ data => [ "\001\003", $o->data ], data => { ne => "\000" }, id => { ne => undef }, num => undef, '!data' => "\002\003", data => $o->data, ] ], id => $o->id ]); ok($os && @$os == 1 && $os->[0]->id == $o->id, "manager 3 - $db_type"); } BEGIN { our %Have; # # PostgreSQL # my $dbh; eval { $dbh = Rose::DB->new('pg_admin')->retain_dbh() or die Rose::DB->error; }; if(!$@ && $dbh) { $Have{'pg'} = 1; $Have{'pg_with_schema'} = 1; # Drop existing tables and create schema, ignoring errors { local $dbh->{'RaiseError'} = 0; local $dbh->{'PrintError'} = 0; $dbh->do('DROP TABLE rose_db_object_test'); } $dbh->do(<<"EOF"); CREATE TABLE rose_db_object_test ( id SERIAL PRIMARY KEY, num INT, data BYTEA ) EOF $dbh->disconnect; } # # MySQL # eval { my $db = Rose::DB->new('mysql_admin'); $dbh = $db->retain_dbh or die Rose::DB->error; # Drop existing tables, ignoring errors { local $dbh->{'RaiseError'} = 0; local $dbh->{'PrintError'} = 0; $dbh->do('DROP TABLE rose_db_object_test'); } }; if(!$@ && $dbh) { $Have{'mysql'} = 1; $dbh->do(<<"EOF"); CREATE TABLE rose_db_object_test ( id INT AUTO_INCREMENT PRIMARY KEY, num INT, data BLOB ) EOF } } END { # Delete test table if($Have{'pg'}) { # PostgreSQL my $dbh = Rose::DB->new('pg_admin')->retain_dbh() or die Rose::DB->error; $dbh->do('DROP TABLE rose_db_object_test'); $dbh->disconnect; } if($Have{'mysql'}) { # MySQL my $dbh = Rose::DB->new('mysql_admin')->retain_dbh() or die Rose::DB->error; $dbh->do('DROP TABLE rose_db_object_test'); $dbh->disconnect; } }