[SCM] Debian package checker branch, lab-refactor, updated. 2.5.3-48-ga78de70
The following commit has been merged in the lab-refactor branch:
commit a78de70cab489b8461c2d0c828c43311d758e099
Author: Niels Thykier <niels@thykier.net>
Date: Mon Sep 19 17:05:11 2011 +0200
Extending the new Lab API
Renamed is_valid_lab to lab_exists. Added is_open, open_lab,
create_lab and close_lab. Not all of them are fully implemented.
Signed-off-by: Niels Thykier <niels@thykier.net>
diff --git a/lib/Lintian/Lab.pm b/lib/Lintian/Lab.pm
index fd2b8b3..1f143c2 100644
--- a/lib/Lintian/Lab.pm
+++ b/lib/Lintian/Lab.pm
@@ -29,10 +29,16 @@ use base qw(Class::Accessor Exporter);
use Carp qw(croak);
use Cwd();
+use File::Temp qw(tempdir); # For temporary labs
+
# Lab format Version Number increased whenever incompatible changes
# are done to the lab so that all packages are re-unpacked
use constant LAB_FORMAT => 10.1;
+# Constants to avoid semantic errors due to typos in the $lab->{'mode'}
+# field values.
+use constant LAB_MODE_STATIC => 'static';
+use constant LAB_MODE_TEMP => 'temporary';
# Export now due to cicular depends between Lab and Lab::Package.
our (@EXPORT, @EXPORT_OK, %EXPORT_TAGS);
@@ -47,6 +53,8 @@ BEGIN {
);
};
+use Util qw/delete_dir/; # Used by $lab->remove_lab
+
=head1 NAME
Lintian::Lab -- Interface to the Lintian Lab
@@ -67,16 +75,23 @@ lab will be in temporary mode and will point to a temporary directory.
sub new {
my ($class, $dir) = @_;
my $absdir;
- my $mode = 'temporary';
+ my $mode = LAB_MODE_TEMP;
if ($dir) {
$absdir = Cwd::abs_path($dir);
croak "Cannot resolve $dir: $!" unless $absdir;
- $mode = 'static';
+ $mode = LAB_MODE_STATIC;
+ } else {
+ $absdir = ''; #Ensure it is defined.
}
my $self = {
- 'dir' => $absdir,
- 'state' => {},
- 'mode' => $mode,
+ # Must be absolute (frontend/lintian depends on it)
+ # - also $self->dir promises this
+ # - it may be the empty string (see $self->dir)
+ 'dir' => $absdir,
+ 'state' => {},
+ 'mode' => $mode,
+ 'is_open' => 0,
+ 'keep-lab' => 0,
};
bless $self, $class;
$self->_init ($dir);
@@ -87,30 +102,32 @@ sub new {
Returns the absolute path to the base of the lab.
-=cut
+Note: This may return the empty string if either the lab has been
+deleted or this is a temporary lab that has not been created yet.
+In the latter case, $lab->create_lab should be run to get a
+non-empty value from this method.
-Lintian::Lab->mk_ro_accessors (qw(dir));
+=item $lab->is_open
-=item $lab->auto_remove ([$val])
+Returns a truth value if this lab is open.
-Whether or not to auto-remove the lab. By default, temporary labs will
-be auto-removed and static labs will not. The removal will happen when
-C<$lab> goes out of scope.
+Note: This does not imply that the underlying does not exists.
=cut
-Lintian::Lab->mk_accessors (qw(auto_remove));
+Lintian::Lab->mk_ro_accessors (qw(dir is_open));
-=item $lab->is_valid_lab
+=item $lab->lab_exists
-Returns a truth value if B<$lab> points to a valid and existing
-lab.
+Returns a truth value if B<$lab> points to an existing lab.
+
+Note: This does not imply whether or not the lab is open.
=cut
-sub is_valid_lab {
+sub lab_exists {
my ( $self ) = @_;
- my $dir = $self->{dir};
+ my $dir = $self->dir;
return unless $dir;
# New style lab?
return 1 if -d "$dir/info" && -d "$dir/pool";
@@ -140,6 +157,124 @@ sub _pool_path {
return $path;
}
+=item $lab->create_lab ([$opts])
+
+Creates a new lab. It will create $self->dir if it does not
+exists. It will also create a basic lab empty lab. If this is
+a temporary lab, this method will also setup the temporary dir
+for the lab.
+
+B<$opts> (if present) is a hashref containing options. Currently only
+"keep-lab" is recognized. If "keep-lab" points to a truth value the
+temporary directory will I<not> be removed by closing the lab (nor
+exiting the application). However, explicitly calling
+$self->remove_lab will remove the lab.
+
+Note: This will not create parent directories of $self->dir and will
+croak if these does not exists.
+
+=cut
+
+sub create_lab {
+ my ($self, $opts) = @_;
+ my $dir = $self->dir;
+ my $mid = 0;
+ $opts = {} unless $opts;
+ if ( !$dir or $self->{'mode'} eq LAB_MODE_TEMP) {
+ if ($self->{'mode'} eq LAB_MODE_TEMP) {
+ my $keep = $opts->{'keep-lab'}//0;
+ my $topts = { CLEAN => !$keep, TMPDIR => 1 };
+ my $t = tempdir ('temp-lintian-lab-XXXXXX', $topts);
+ $dir = Cwd::abs_path ($t);
+ croak "Could not resolve $dir: $!" unless $dir;
+ $self->{'dir'} = $dir;
+ $self->{'keep-lab'} = $keep;
+ } else {
+ croak 'Labs cannot be re-opened'
+ }
+ }
+ # Create the top dir if needed - note due to Lintian::Lab->new
+ # and the above tempdir creation code, we know that $dir is
+ # absolute.
+ croak "Cannot create $dir: $!" unless -d $dir or mkdir $dir;
+
+ # Top dir exists, time to create the minimal directories.
+ unless (-d "$dir/info") {
+ mkdir "$dir/info" or croak "mkdir $dir/info: $!";
+ $mid = 1; # remember we created the info dir
+ }
+ unless (-d "$dir/pool") {
+ unless (mkdir "$dir/pool") {
+ my $err = $!; # store the error
+ # Remove the info dir if we made it. This attempts to
+ # prevent a semi-created lab that the API cannot remove
+ # again.
+ #
+ # ignore the error (if any) - we can only do so much
+ rmdir "$dir/info" if $mid;
+ $! = $err;
+ croak "mkdir $dir/pool: $!";
+ }
+ }
+ # Okay - $dir/info and $dir/pool exists... The subdirs in
+ # $dir/pool will be created as needed.
+
+ # TODO: populate $dir/info
+ return 1;
+}
+
+=item $lab->open_lab
+
+Opens the lab and reads the contents into caches. If the Lab is
+temporary this will create a temporary dir to store the contents of
+the lab.
+
+This will croak if the lab is already open. It may also croak for
+the same reasons as $lab->create_lab if this is a temporary lab.
+
+Note: for static labs, $lab->dir must point to an existing consistent
+lab or this will croak. To open a new lab, please use
+$lab->create_lab.
+
+Note: It is not possible to pass options to the creation of the
+temporary lab. If special options are required, please use
+$lab->create_lab.
+
+=cut
+
+sub open_lab {
+ my ($self) = @_;
+ croak 'Lab is already open' if $self->is_open();
+ if ($self->{'mode'} eq LAB_MODE_TEMP) {
+ $self->create_lab() unless $self->lab_exists();
+ }
+ $self->{'is_open'} = 1;
+ return 1;
+}
+
+=item $lab->close_lab
+
+Close the lab - all state caches will be flushed to the disk and the
+lab can no longer be used. All references to entries in the lab
+should be considered invalid.
+
+Note: if the lab is a temporary one, this will be deleted unless it
+was created with "keep-lab" (see $lab->create_lab).
+
+=cut
+
+sub close_lab {
+ my ($self) = @_;
+ return unless $self->lab_exists();
+ if ($self->{'mode'} eq LAB_MODE_TEMP && !$self->{'keep-lab'}) {
+ # Temporary lab (without "keep-lab" property)
+ $self->remove_lab();
+ } else {
+ # TODO flush/write stuff
+ }
+ return 1;
+}
+
=item $lab->remove_lab
Removes the lab and everything in it. Any reference to an entry
@@ -151,11 +286,12 @@ not be removed by this call.
On success, this will return a truth value and the directory path will
be set to the empty string (that is, $lab->dir will return ''). It
-will not be possible to use B<$lab> to create a new lab.
+will generally not be possible to use B<$lab> to create a new lab.
On error, this method will croak.
-If the lab has already been removed, this will return a truth value.
+If the lab has already been removed (or does not exists), this will
+return a truth value.
=cut
@@ -196,20 +332,21 @@ sub remove_lab {
}
# dynamic lab?
- if ($self->{mode} eq 'temporary') {
- croak "rmdir $dir: $!";
+ if ($self->{'mode'} eq LAB_MODE_TEMP) {
+ rmdir $dir or croak "rmdir $dir: $!";
}
- $self->{dir} = '';
+ $self->{'dir'} = '';
return 1;
}
# initialize the instance
#
-# May be overriden by a sub-class
+# May be overriden by a sub-class.
+#
+# $self->dir may be the empty string if this is a temporary lab.
sub _init {
- my ($self, $dir) = @_;
-
+ my ($self) = @_;
}
=back
--
Debian package checker
Reply to: