Subject: | Strange interaction between File::Temp and DBD::SQLite |
I get the following output from the attached tests:
1..4
DBD::SQLite::db do failed: database is locked(5) at dbdimp.c line 271 at
sqlite_temp.pl line 38.
not ok 1 - CREATE TABLE works for tempfile() with 2 LHS and UNLINK
# Failed test (sqlite_temp.pl at line 42)
DBD::SQLite::db do failed: database is locked(5) at dbdimp.c line 271 at
sqlite_temp.pl line 38.
not ok 2 - CREATE TABLE works for tempfile() with 2 LHS
# Failed test (sqlite_temp.pl at line 42)
ok 3 - CREATE TABLE works for tempfile() with 1 list context LHS
ok 4 - CREATE TABLE works for tmpnam()
# Looks like you failed 2 tests of 4.
Basically, calling tempfile() in subtly different ways does something
strange with file locking that upsets SQLite. It's not just a case of
having an open filehandle, as the fourth test shows.
I don't know enough to figure out if the fundamental problem exists in
DBD::SQLite, the sqlite C code, File::Temp or elsewhere. But it strikes
me as odd that small changes in calls to File::Temp have very different
results.
I see this happen with Perl 5.8.7 (on FreeBSD 5.x) and 5.8.8 (on FreeBSD
6.x).
Please let me know if I can help resolve this problem.
Tom
Subject: | sqlite_and_file_temp.pl |
#!perl
use strict;
use warnings;
use DBI ();
use File::Temp qw(tempfile tmpnam);
use Test::More tests => 4;
{
my($fh, $filename) = tempfile(UNLINK => 1); # FAILS
db_do($filename, 'tempfile() with 2 LHS and UNLINK');
}
{
my($fh, $filename) = tempfile; # FAILS
db_do($filename, 'tempfile() with 2 LHS');
}
{
my(undef, $filename) = tempfile; # WORKS
db_do($filename, 'tempfile() with 1 list context LHS');
}
{
my $filename = tmpnam(); # WORKS
open (my $fh, '>', $filename);
db_do($filename, 'tmpnam()');
}
sub db_do {
my $filename = shift;
my $test_type = shift;
my $dbh = DBI->connect(
"DBI:SQLite:dbname=$filename",
'',
'',
{ RaiseError => 1 }
);
eval {
$dbh->do(
"CREATE TABLE foo ( id INTEGER NOT NULL, PRIMARY KEY (id) )"
);
};
ok ! $@, "CREATE TABLE works for $test_type";
$dbh->disconnect();
}