BioPerl-DB
view release on metacpan or search on metacpan
lib/Bio/DB/BioSQL/BaseDriver.pm view on Meta::CPAN
}
# bind foreign key values
if($fkobjs) {
foreach my $o (@$fkobjs) {
# If it's an object, the value to bind is the primary key.
# Otherwise bind undef.
my $fk = $o && ref($o) ? $o->primary_key() : undef;
if($adp->verbose > 0) {
$adp->debug(substr(ref($adp),rindex(ref($adp),"::")+2).
"::insert: ".
"binding column $j to \"", $fk,
"\" (FK to ",
($o ?
(ref($o) ? ref($o->obj()) : $o) : "<unknown>"),
")\n");
}
$self->bind_param($sth, $j, $fk);
$j++;
}
}
# execute
my $rv = $sth->execute();
my $pk;
# Note: $rv may be 0E0 (evaluates to TRUE as a string) to indicate
# success, but zero rows affected, which means no row was inserted.
# This may be (hopefully will be) due to an RDBMS having internally
# (by means of triggers [Oracle, Pg] or rules [Pg]) encapsulated and
# caught the already-exists condition.
if($rv && ($rv != 0)) {
# get the primary key that was just inserted
$pk = $adp->dbcontext()->dbi()->last_id_value(
$dbh, $self->sequence_name($table));
} elsif(! $rv) { # note this is *not* equivalent to $rv == 0 !
# the statement failed
$self->report_execute_failure(-sth => $sth, -adaptor => $adp,
-op => 'insert',
-vals => $slotvals, -fkobjs => $fkobjs);
}
# done, return
return $pk;
}
=head2 update_object
Title : update_object
Usage :
Function:
Example :
Returns : The number of updated rows
Args : A Bio::DB::BioSQL::BasePersistenceAdaptor derived object
(basically, it needs to implement dbh(), sth($key, $sth),
dbcontext(), and get_persistent_slots()).
The object to be updated.
A reference to an array of foreign key objects; if any of those
foreign key values is NULL (some foreign keys may be nullable),
then give the class name.
=cut
sub update_object{
my ($self,$adp,$obj,$fkobjs) = @_;
# obtain the object's slots to be serialized
my @slots = $adp->get_persistent_slots($obj);
# get the UPDATE statement
# is it cached?
my $cache_key = 'UPDATE '.ref($adp).' '.join(';',@slots);
my $sth = $self->get_sth($adp,$obj,$fkobjs,$cache_key,'update_object');
# we need the slot map regardless of whether we need to construct the
# SQL or not, because we need to know which slots do not map to a column
# (indicated by them being mapped to undef)
my $table = $self->table_name($adp);
my $slotmap = $self->slot_attribute_map($table);
$self->throw("no slot/attribute map for table $table") unless $slotmap;
# if not cached, create SQL and prepare statement
if(! $sth) {
$sth = $self->prepare_update_sth($adp, \@slots, $fkobjs);
# and cache
$adp->sth($cache_key, $sth);
# and give interceptors a chance to do their work
$sth = $self->get_sth($adp,$obj,$fkobjs,$cache_key,'update_object');
}
# bind paramater values
my $slotvals = $adp->get_persistent_slot_values($obj, $fkobjs);
if(@$slotvals != @slots) {
$self->throw("number of slots must equal the number of values");
}
my $i = 0; # slots and slot values index
my $j = 1; # column index
while($i < @slots) {
if($slotmap->{$slots[$i]} &&
(substr($slotmap->{$slots[$i]},0,2) ne '=>')) {
if($adp->verbose > 0) {
$adp->debug(sprintf("%s::update: binding column %d to \"%s\"(%s)\n",
substr(ref($adp),rindex(ref($adp),"::")+2),
$j,
$slotvals->[$i] || '',
($slots[$i])));
}
$self->bind_param($sth, $j, $slotvals->[$i]);
$j++;
}
$i++;
}
# bind foreign key values
if($fkobjs) {
foreach my $o (@$fkobjs) {
# If it's an object, the value to bind is the primary key. If it's
# numeric, the value is the number. Otherwise bind undef.
my $fk = ref($o) ?
$o->primary_key() :
$o =~ /^\d+$/ ? $o : undef;
if($adp->verbose > 0) {
$adp->debug(substr(ref($adp),rindex(ref($adp),"::")+2).
"::update: ".
"binding column $j to \"$fk\" (FK to ".
$self->table_name($o) . ")\n");
}
$self->bind_param($sth, $j, $fk);
$j++;
( run in 1.704 second using v1.01-cache-2.11-cpan-5b529ec07f3 )