better output, read fixes, ctime preserved (so that vi won't complain that
[Fuse-DBI] / fuse_dbi.pl
index a19c92c..e4570bf 100755 (executable)
@@ -1,6 +1,6 @@
 #!/usr/bin/perl
 
-use POSIX qw(ENOENT EISDIR EINVAL O_RDWR);
+use POSIX qw(ENOENT EISDIR EINVAL ENOSYS O_RDWR);
 use Fuse;
 
 use DBI;
@@ -30,9 +30,10 @@ my $sql_update = q{
 
 my $connect = "DBI:Pg:dbname=webgui";
 
-my $dbh = DBI->connect($connect,"","") || die $DBI::errstr;
+my $dbh = DBI->connect($connect,"","", { AutoCommit => 0 }) || die $DBI::errstr;
 
-print STDERR "$sql_filenames\n";
+print "start transaction\n";
+#$dbh->begin_work || die $dbh->errstr;
 
 my $sth_filenames = $dbh->prepare($sql_filenames) || die $dbh->errstr();
 $sth_filenames->execute() || die $sth_filenames->errstr();
@@ -40,8 +41,6 @@ $sth_filenames->execute() || die $sth_filenames->errstr();
 my $sth_read = $dbh->prepare($sql_read) || die $dbh->errstr();
 my $sth_update = $dbh->prepare($sql_update) || die $dbh->errstr();
 
-print "#",join(",",@{ $sth_filenames->{NAME} }),"\n";
-
 my $ctime_start = time();
 
 my (%files) = (
@@ -88,7 +87,7 @@ while (my $row = $sth_filenames->fetchrow_hashref() ) {
        }
 }
 
-print scalar (keys %dirs), " dirs:",join(" ",keys %dirs),"\n";
+print "found ",scalar(keys %files)-scalar(keys %dirs)," files, ",scalar(keys %dirs), " dirs\n";
 
 sub filename_fixup {
        my ($file) = shift;
@@ -130,17 +129,14 @@ sub e_getdir {
                } else {
                        $out{$f}++ if ($f =~ /^[^\/]+$/);
                }
-               print "f: $_ -> $f\n";
        }
        if (! %out) {
                $out{'no files? bug?'}++;
        }
-       print scalar keys %out," files found for '$dirname': ",keys %out,"\n";
+       print scalar keys %out," files in dir '$dirname'\n";
        return (keys %out),0;
 }
 
-my $in_transaction = 0;
-
 sub e_open {
        # VFS sanity check; it keeps all the necessary state, not much to do here.
        my $file = filename_fixup(shift);
@@ -149,19 +145,10 @@ sub e_open {
        return -ENOENT() unless exists($files{$file});
        return -EISDIR() unless exists($files{$file}{id});
 
-       if (! $in_transaction) {
-               # begin transaction
-               if (! $dbh->begin_work) {
-                       print "transaction begin: ",$dbh->errstr;
-                       return -ENOENT();
-               }
-       }
-       $in_transaction++;
-       print "files opened: $in_transaction\n";
-
        if (!exists($files{$file}{cont})) {
                $sth_read->execute($files{$file}{id}) || die $sth_read->errstr;
                $files{$file}{cont} = $sth_read->fetchrow_array;
+               print "file '$file' content read in cache\n";
        }
        print "open '$file' ",length($files{$file}{cont})," bytes\n";
        return 0;
@@ -172,45 +159,47 @@ sub e_read {
        # (note: 0 means EOF, "0" will give a byte (ascii "0")
        # to the reading program)
        my ($file) = filename_fixup(shift);
-       my ($buf,$off) = @_;
+       my ($buf_len,$off) = @_;
 
        return -ENOENT() unless exists($files{$file});
 
        my $len = length($files{$file}{cont});
 
-       print "read '$file' [$len bytes] offset $off length $buf\n";
+       print "read '$file' [$len bytes] offset $off length $buf_len\n";
 
        return -EINVAL() if ($off > $len);
        return 0 if ($off == $len);
 
-       $buf = $len-$off if ($off+$buf > $len);
+       $buf_len = $buf_len-$off if ($off+$buf_len > $len);
 
-       return substr($files{$file}{cont},$off,$buf);
+       return substr($files{$file}{cont},$off,$buf_len);
 }
 
 sub clear_cont {
+       print "transaction rollback\n";
+       $dbh->rollback || die $dbh->errstr;
        print "invalidate all cached content\n";
        foreach my $f (keys %files) {
                delete $files{$f}{cont};
        }
+       print "begin new transaction\n";
+       $dbh->begin_work || die $dbh->errstr;
 }
 
 
 sub update_db {
        my $file = shift || die;
 
+       $files{$file}{ctime} = time();
+
        if (!$sth_update->execute($files{$file}{cont},$files{$file}{id})) {
                print "update problem: ",$sth_update->errstr;
-               $dbh->rollback;
                clear_cont;
-               $dbh->begin_work;
                return 0;
        } else {
-               if ($dbh->commit) {
-                       print "commit problem: ",$sth_update->errstr;
-                       $dbh->rollback;
+               if (! $dbh->commit) {
+                       print "ERROR: commit problem: ",$sth_update->errstr;
                        clear_cont;
-                       $dbh->begin_work;
                        return 0;
                }
                print "updated '$file' [",$files{$file}{id},"]\n";
@@ -220,23 +209,23 @@ sub update_db {
 
 sub e_write {
        my $file = filename_fixup(shift);
-       my ($buf,$off) = @_;
+       my ($buf_len,$off) = @_;
 
        return -ENOENT() unless exists($files{$file});
 
        my $len = length($files{$file}{cont});
 
-       print "write '$file' [$len bytes] offset $off length $buf\n";
+       print "write '$file' [$len bytes] offset $off length\n";
 
        $files{$file}{cont} =
                substr($files{$file}{cont},0,$off) .
-               $buf .
-               substr($files{$file}{cont},$off+length($buf));
+               $buf_len .
+               substr($files{$file}{cont},$off+length($buf_len));
 
        if (! update_db($file)) {
                return -ENOSYS();
        } else {
-               return length($buf);
+               return length($buf_len);
        }
 }
 
@@ -255,6 +244,8 @@ sub e_utime {
 
        return -ENOENT() unless exists($files{$file});
 
+       print "utime '$file' $atime $mtime\n";
+
        $files{$file}{time} = $mtime;
        return 0;
 }
@@ -275,5 +266,5 @@ Fuse::main(
        write=>\&e_write,
        utime=>\&e_utime,
        truncate=>\&e_truncate,
-       debug=>1,
+       debug=>0,
 );