package PhotoPub::FileInfo;
require Exporter;
@ISA = qw(Exporter);
@EXPORT_OK = qw(&mtime &isregfile &isdir &getfiles &existsfile);

use PhotoPub::Global qw(&register_init $error);

use Carp;
use POSIX qw(&S_ISREG &S_ISDIR);

my %filestatcache;
my %dirlistcache;

&register_init('startup',sub {
		 %filestatcache=();
		 %dirlistcache=();
	       });

sub doreaddir($) {
  my ($dirname)=@_;

  if(!exists $dirlistcache{$dirname}) {
    opendir DIR,$dirname 
       or return undef;
    $dirlistcache{$dirname}={};
    foreach my $entry (readdir DIR) {
      $dirlistcache{$dirname}->{$entry}=1;
    }
    closedir DIR;
  }
  return $dirlistcache{$dirname};
}
  
sub getfiles($) {
  my ($dirname)=@_;
  my $direntries=&doreaddir($dirname);
  &$error(type => 'config',message => "Couldn't open $dirname")
    unless defined $direntries;
  return (keys %$direntries);
}

sub existsfile($) {
  my ($fullpath)=@_;
  my ($dirname,$filename)=($fullpath =~ /^(.*)\/([^\/]+)\/?$/)
    or &$error(type => 'internal',
	       message => "Must pass absolute file path to "
	                    ."&FileInfo::existsfile (path was $fullpath)");


  my $dir=&doreaddir($dirname);
  if(defined $dir) {
    return (exists $dir->{$filename});
  } else {
    return -e $fullpath;
  }
}

sub dostat($) {
  my ($filename)=@_;

  if(!exists $filestatcache{$filename}) {
    my @statdetails=stat($filename)
      or &$error(type => 'config',message => "Couldn't stat $filename");

    $filestatcache{$filename}=\@statdetails;
  }
  return $filestatcache{$filename};
}

sub mtime($) {
  my ($filename)=@_;

  if(!defined $filename) {
    &croak('Undefined file passed to &FileInfo::mtime');
  }

  return &dostat($filename)->[9];
}

sub isregfile($) {
  my ($filename)=@_;

  if(!defined $filename) {
    &croak('Undefined file passed to &FileInfo::isregfile');
  }

  # This is actually faster than using the cache!
  return -f $filename;
#  return &existsfile($filename) && &S_ISREG(&dostat($filename)->[2]);
}

sub isdir($) {
  my ($filename)=@_;

  if(!defined $filename) {
    &croak('Undefined file passed to &FileInfo::isdir');
  }

  # This is actually faster than using the cache!
  return -d $filename;
#  return &existsfile($filename) && &S_ISDIR(&dostat($filename)->[2]);
}

1;
