AFS-Command
view release on metacpan or search on metacpan
lib/AFS/Command/Base.pm view on Meta::CPAN
push (@{$self->{command}},@commands);
} else {
@{$self->{command}} = lc((split(/::/,$class))[2]);
}
bless $self, $class;
return $self;
}
sub errors {
my $self = shift;
return $self->{errors};
}
sub supportsOperation {
my $self = shift;
my $operation = shift;
return $self->_operations($operation);
}
sub supportsArgument {
my $self = shift;
my $operation = shift;
my $argument = shift;
return unless $self->_operations($operation);
return unless $self->_arguments($operation);
return exists $self->{_arguments}->{$operation}->{$argument};
}
sub _Carp {
my $self = shift;
$Carp{carp}->(@_);
}
sub _Croak {
my $self = shift;
$Carp{croak}->(@_);
}
sub _operations {
my $self = shift;
my $operation = shift;
my $class = ref $self;
unless ( $self->{_operations} ) {
my %operations = ();
#
# This hack is necessary to support the offline/online "hidden"
# vos commands. These won't show up in the normal help output,
# so we have to check for them individually. Since offline and
# online are implemented as a pair, we can just check one of
# them, and assume the other is there, too.
#
foreach my $type ( qw(default hidden) ) {
if ( $type eq 'hidden' ) {
next unless $self->isa("AFS::Command::VOS");
}
my $pipe = IO::Pipe->new() || do {
$self->_Carp("Unable to create pipe: $ERRNO\n");
return;
};
my $pid = fork();
unless ( defined $pid ) {
$self->_Carp("Unable to fork: $ERRNO\n");
return;
}
if ( $pid == 0 ) {
STDERR->fdopen( STDOUT->fileno(), "w" ) ||
$self->_Croak("Unable to redirect stderr: $ERRNO\n");
STDOUT->fdopen( $pipe->writer()->fileno(), "w" ) ||
$self->_Croak("Unable to redirect stdout: $ERRNO\n");
if ( $type eq 'default' ) {
exec @{$self->{command}}, 'help';
} else {
exec @{$self->{command}}, 'offline', '-help';
}
die "Unable to exec @{$self->{command}} help: $ERRNO\n";
} else {
$pipe->reader();
while ( defined($_ = $pipe->getline()) ) {
if ( $type eq 'default' ) {
next if /Commands are:/;
my ($command) = split;
next if $command =~ /^(apropos|help)$/;
$operations{$command}++;
} else {
if ( /^Usage:/ ) {
$operations{offline}++;
$operations{online}++;
}
}
}
}
unless ( waitpid($pid,0) ) {
$self->_Carp("Unable to get status of child process ($pid)");
return;
}
if ( $? ) {
$self->_Carp("Error running @{$self->{command}} help. Unable to configure $class");
return;
}
}
$self->{_operations} = \%operations;
}
return $self->{_operations}->{$operation};
}
sub _arguments {
my $self = shift;
my $operation = shift;
my $arguments =
{
optional => {},
required => {},
aliases => {},
};
my @command;
push (@command, @{$self->{command}});
unless ( $self->_operations($operation) ) {
$self->_Carp("Unsupported @command operation '$operation'\n");
return;
}
return $self->{_arguments}->{$operation}
if ref $self->{_arguments}->{$operation} eq 'HASH';
my $pipe = IO::Pipe->new() || do {
$self->_Carp("Unable to create pipe: $ERRNO");
return;
( run in 0.681 second using v1.01-cache-2.11-cpan-140bd7fdf52 )