Re: DBD::ODBC fails after "Execute immediate success with info"

"Martin J. Evans" <[email protected]>
Newsgroups gmane.comp.lang.perl.modules.dbi.general
Message-ID <[email protected]>
On 06/11/13 14:36, Jan Holčapek wrote:
> Hi Martin,
>
> On Wed, Nov 6, 2013 at 3:05 PM, Martin J. Evans <[email protected]> wrote:
>> I believe this is a bug in your ODBC driver.
>
> I kind of expected that. I'll file a bugreport to Vertica Support.

good, that was part of what I was hoping to achieve when I did this.

>> However, I took the decision in DBD::ODBC to report this an error and some
>> might argue differently. In this case it is fairly innocuous as you tried to
>> drop a table which did not exist and afterwards it does not exist - although
>> what happens if it was an error in your application and the table should
>> have existed? In other cases it is more clear cut - what if you tried to set
>> a statement attribute like a cursor to type A and the driver said, I've set
>> a cursor, but not to type A, I've set it to type B - an app would likely
>> want to know this.
>
> IMO current behavior is correct.
>
>> I can see it might be inconvenient for you the way it is now as your forced
>> to do something like:
>>
>> $h->{RaiseError} = 1;
>> eval {
>>    $h->do(q/drop table foo/);
>> };
>> if ($@ && $h->errstr =~ /Unable to fetch information about the error/) {
>>      # assume the drop was ok and the table did not exist
>>      # but that is not really a safe assumption to make
>> } elsif ($@) {
>>      # it is a real error
>> }
>
> I've already adjusted the code with this, I also narrowed the
> if-condition with $dbh->state eq 'IM008',
> as I'm getting this state along with the error. Not that it's neat,
> but allows me to work
> around this driver issue for the moment.
>
> BTW I found out IM008 is returned by DBD::ODBC, then checked
> http://www.easysoft.com/developer/interfaces/odbc/sqlstate_status_return_codes.html#IM008
> and must admit I can't see a relationship between the actual error and
> the state.

hah, my own document comes back to haunt me.

You are right, it is down to:

     if (!error_found && (err_rc != SQL_NO_DATA_FOUND)) {
         if (DBIc_TRACE(imp_xxh, DBD_TRACING, 0, 3))
             TRACE1(imp_dbh, "    ** No error found %d **\n", err_rc);
         DBIh_SET_ERR_CHAR(
             h, imp_xxh, Nullch, 1,
             "    Unable to fetch information about the error", "IM008", Nullch);
     }

and I'm guessing a cut and paste. DBD::ODBC has to invent a state here and I guess it should be HY000. If I were you I'd not rely on IM008 as now you've pointed it out I may change it to HY000 so you might be better looking for IM008|HY000 or "No error found" in errstr. I've just added a comment to the source, not to change that string.

  
>> I could be swayed to change this to a warning (which would be less
>> inconvenient to you since you could disable warnings when you are dropping a
>> table) but I'd need to be persuaded. This is one of those occasions when I'm
>> damned either way. If I don't report it as an error I end up debugging
>> peoples ODBC logs only to tell them their driver is broken and if I do
>> report an error people come back to me saying why is this an error.
>
> Agree.
>
>> BTW, are you sure your db can actually rollback a drop table, and if it
>> cannot, then why bother doing it in a txn?
>
> This is due to the code being used to handle data both in PostgreSQL database
> (which supports transactional DDL) and Vertica (which does not support that).
> We are likely about to consider changing the application logic.
>
> Thank very much for the explanation!
>
> Cheers
> Jan
>

np.

Martin
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.