From: Peter Rabbitson Date: Wed, 20 May 2015 13:25:06 +0000 (+0200) Subject: Fix oversight in 096ab902 breaking { -value => $array } insertion X-Git-Url: http://git.shadowcat.co.uk/gitweb/gitweb.cgi?a=commitdiff_plain;h=a2c77c97735124a7bf4073cf5cef5480bec752a8;p=dbsrgits%2FDBIx-Class.git Fix oversight in 096ab902 breaking { -value => $array } insertion This was never tested for, but also never shipped --- diff --git a/lib/DBIx/Class/Row.pm b/lib/DBIx/Class/Row.pm index 5425fd8..77628ad 100644 --- a/lib/DBIx/Class/Row.pm +++ b/lib/DBIx/Class/Row.pm @@ -1221,11 +1221,16 @@ sub store_column { $self->throw_exception( "set_column called for ${column} without value" ) if @_ < 3; - # stringify all refs explicitly, guards against overloaded objects + return $self->{_column_data}{$column} = $value + unless length ref $value and my $vref = is_plain_value( $value ); + + # if we are dealing with a value/ref - there are a couple possibilities + # unpack the underlying piece of data and stringify all objects explicitly + # ( to accomodate { -value => ... } and guard against overloaded objects # with defined stringification AND fallback => 0 (ugh!) - $self->{_column_data}{$column} = ( length ref $value and is_plain_value( $value ) ) - ? "$value" - : $value + $self->{_column_data}{$column} = defined blessed $$vref + ? "$$vref" + : $$vref ; } diff --git a/lib/DBIx/Class/Storage/DBI.pm b/lib/DBIx/Class/Storage/DBI.pm index 3e746ad..40ae3f9 100644 --- a/lib/DBIx/Class/Storage/DBI.pm +++ b/lib/DBIx/Class/Storage/DBI.pm @@ -2286,10 +2286,12 @@ sub _dbh_execute_for_fetch { # FIXME SUBOPTIMAL - DBI needs fixing to always stringify regardless of DBD # For the time being forcibly stringify whatever is stringifiable - (length ref $v and is_plain_value $v) - ? "$v" - : $v - ; + my $vref; + + ( !length ref $v or ! ($vref = is_plain_value $v) ) ? $v + : defined blessed( $$vref ) ? "$$vref" + : $$vref + ; } map { $_->[0] } @$proto_bind ]; }; diff --git a/t/72pg.t b/t/72pg.t index e1e8e0e..e03cd2b 100644 --- a/t/72pg.t +++ b/t/72pg.t @@ -287,6 +287,49 @@ for my $use_insert_returning ($test_server_supports_insert_returning $row->discard_changes; is_deeply ($row->arrayfield, [3,4], 'Array value made it to storage'); } + + my $arr = [ 1..10 ]; + # exercise the creation-logic even more (akin to t/100populate.t) + for my $insert_value ( + $arr, + { -value => $arr }, + \[ '?', $arr ], + ) { + $arr_rs->delete; + + my @objs = ( + $arr_rs->create({ arrayfield => $insert_value }), + $arr_rs->populate([ { arrayfield => $insert_value } ]), + $arr_rs->populate([ ['arrayfield'], [ $insert_value ] ]), + ); + + my $loose_obj = $arr_rs->new({ arrayfield => $insert_value }); + + unless (is_literal_value $insert_value) { + is_deeply( $_->arrayfield, $arr, 'array value preserved during set_columns' ) + for ($loose_obj, @objs) + } + + push @objs, $loose_obj->insert; + + $_->discard_changes for @objs; + is_deeply( $_->arrayfield, $arr, 'array value correct after discard_changes' ) + for (@objs); + + # insert couple more in void ctx + $arr_rs->populate([ { arrayfield => $insert_value } ]); + $arr_rs->populate([ ['arrayfield'], [ $insert_value ] ]); + + # should have a total of 6 now, all pristine + my @retrieved_objs = $arr_rs->search({ + arrayfield => ref $insert_value eq 'ARRAY' + ? { -value => $insert_value } + : { '=' => $insert_value } + })->all; + is scalar @retrieved_objs, 6, 'Correct count of inserted rows'; + is_deeply( $_->arrayfield, $arr, 'array value correct after storage retrieval' ) + for (@retrieved_objs); + } } ########## Case check