"Dean Arnold" <[EMAIL PROTECTED]> writes:

> > Does DBI 1.38 have an API that takes an array of rows (which should be
> > the usual end-user interface rather than the more abstract callback
> > method of execute_for_fetch())? If not, it should probably be added, I
> > think I put in a row-wise option in my execute_array patch.
> 
> Was this ever resolved ? Was a new API i/f deemed neccesary,
> or was some hack on bind_param_array/execute_array considered ?
> Or is ArrayTupleFetch the solution to all the above ?

It has not been resolved yet (that I know of).

So here is my suggestion, based on my work on the DBD::Oracle
execute_array patch:

DBI interface:

The main user-level interface is execute_array(). Four different ways to
use:

1. Column-wise, using $sth->bind_param_array() for each column, then
   $sth->execute_array(\%attr). This is the only method that supports
   named placeholders (:foo style).
2. Column-wise, using $sth->execute_array(\%attr, [EMAIL PROTECTED], [EMAIL 
PROTECTED]).
3. Row-wise, using execute_array({ArrayTupleFetch => sub { ... } }).
   This is the only row-wise method supported in DBI 1.37. This permits
   calling execute_array() with a very large number of rows without
   having to keep them all in memory at once (subject to driver support;
   Oracle will buffer rows and send them off to Oracle in batches
   because of OCI restrictions).
4. Row-wise, using execute_array({ArrayTuple => [ [1,'A'], [2,'B'] ]}).
   Useful in the common case where the user already has a list
   of tuples. Less memory-efficient than column-wise, though.

Method 1 and 2 are the ones supported by older DBI versions. Method 3
was added in DBI 1.36. Method 4 is not in DBI now, but I suggest adding
it for the next version (and it is implemented in my DBD::Oracle
execute_array patch).


DBD::xxx interface:

Low-level methods implemented by drivers and usually only called by the
DBI implementation of execute_array():

1. The execute_for_fetch() method. The implementation of this in the
   driver is mandatory (in the sense that without it no native
   execute_array() will be available; DBI will emulate it with an
   execute() for each row).
2. A new $sth->execute_array_rowwise([EMAIL PROTECTED], [EMAIL PROTECTED])
   for direct implementation of row-wise array execution. Optional; if
   implemented it will be used by DBI::execute_array() when an array of
   tuples is already available (ie. execute_array() method 4 above).
3. A new $sth->execute_array_colwise([EMAIL PROTECTED], [EMAIL PROTECTED], ..., [EMAIL 
PROTECTED])
   for direct implementation of column-wise array execution. Optional;
   if implemented it will be used by DBI for execute_array() method 1
   and 2 above. If we want to implement named placeholders this method
   needs to be extended to take a mapping { 'foo' => [EMAIL PROTECTED],
   'bar' => [EMAIL PROTECTED] }, but maybe that is not so important.

The execute_array_rowwise() and execute_array_colwise() would only be
implemented in drivers like DBD::Oracle where they would provide better
performance than execute_for_fetch() (since they avoid building extra
temporary arrays). It could be that the extra performance obtained in
this way is not worth pursuing so that we would be better off with just
execute_for_fetch() in the drivers. Opinions, anyone? In any case, my
DBD::Oracle patch more or less implements them, so it is just a matter
of deciding style, not of implementing it.

 - Kristian.

-- 
Kristian Nielsen   [EMAIL PROTECTED]
Development Manager, Sifira A/S

Reply via email to