Skip to content
master
Go to file
Code

Latest commit

 

Git stats

Files

Permalink
Failed to load latest commit information.
Type
Name
Latest commit message
Commit time
 
 
t
 
 
xt
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

README.pod

package App::CLI::Extension; =pod =head1 NAME App::CLI::Extension - for App::CLI extension module =head1 VERSION 1.422 =head1 SYNOPSIS # MyApp.pm package MyApp; use strict; use base qw(App::CLI::Extension); # extension method # load App::CLI::Plugin::Foo, MyApp::Plugin::Bar __PACKAGE__->load_plugins(qw(Foo +MyApp::Plugin::Bar)); # extension method __PACKAGE__->config( name => "kurt" ); 1; # MyApp/Hello.pm package MyApp::Hello; use strict; use base qw(App::CLI::Command); use constant options => ("age=i" => "age"); sub run { my($self, @args) = @_; # config - App::CLI::Extension extension method(App::CLI::Extension::Component::Config) print "Hello! my name is " . $self->config->{name} . "\n"; print "age is " . "$self->{age}\n"; } # myapp #!/usr/bin/perl use strict; use MyApp; MyApp->dispatch; # execute [kurt@localhost ~] myapp hello --age=27 Hello! my name is kurt age is 27 =head1 DESCRIPTION The expansion module which added plug in, initial setting mechanism to App::CLI App::CLI::Extension::Component::* modules is automatic, and it is done require (It is now Config and Stash is automatic, and it is done require) =head2 RUN PHASE +----------------------+ | ** run_method ** | | +----------------+ | | | setup phase | | | +----------------+ | | || | | +----------------+ | | | prerun phase | | | +----------------+ | | || | | +----------------+ | if anything error... +----------------+ | | run phase | | ======================> | fail phase | | +----------------+ | +----------------+ | || | set exit_value(default: 255) | +----------------+ | | | | postrun phase | | | | +----------------+ | | +----------------------+ | | | | | +----------------+ | | finish phase | <================================== + +----------------+ | exit =head2 SETUP If you define initialization and initialization of each plug-in =head2 PRERUN If you want the process to run before you run something in the main processing =head2 RUN Process to define the main(require). however, $self->finished non-zero if not executed =head2 POSTRUN After the run method to execute. however, $self->finished non-zero if not executed =head2 FINISH At the end of all processing =head2 FAIL setup/prerun/run/postrun/finish processing to be executed if an exception occurs somewhere in the phase error $self->e is the App::CLI::Extension::Exception or Error::Simple instance is set =cut use strict; use warnings; use base qw(App::CLI Class::Accessor::Grouped); use 5.008000; use UNIVERSAL::require; use Carp qw/croak/; our $VERSION = '1.422'; our @COMPONENTS = qw( Config ErrorHandler InstallCallback OriginalArgv Stash RunCommand ); __PACKAGE__->mk_group_accessors(inherited => "_config", "_components", "_orig_argv", "_plugins"); __PACKAGE__->_config({}); __PACKAGE__->_plugins([]); =pod =head1 METHOD =head2 import() This is automatically called by Perl, but still bears mentioning. Here we load all of the components for our module into memory and register them into our own namespace. =head3 Possible Room for Improvement =over 4 =item Use Module::Load to load modules instead of C followed by C. =back This method takes no parameters and has no returns. =cut sub import { my ($class) = @_; my @loaded_components; foreach my $component (@COMPONENTS) { $component = sprintf "%s::Component::%s", __PACKAGE__, $component; $component->require or croak "load component error: $UNIVERSAL::require::ERROR"; $component->import; push @loaded_components, $component; } $class->_components(\@loaded_components); return; } =head2 dispatch() Start the dispatch chain, passing any arguments along. This method takes a list of arguments to C and returns the result of C. This should be called as a class method. =cut sub dispatch { my ($class, @dispatch_arguments) = @_; # save original argv my @argv = @ARGV; $class->_orig_argv(\@argv); my $cmd = $class->prepare(@dispatch_arguments); $cmd->subcommand; { no strict "refs"; ## no critic (strict) no warnings "uninitialized"; ## no critic (warnings) my $pkg = ref($cmd); # component and plugin set value unshift @{"${pkg}::ISA"}, @{$class->_components}; if (scalar(@{$class->_plugins}) != 0) { unshift @{"${pkg}::ISA"}, @{$class->_plugins}; } $cmd->config($class->_config); $cmd->orig_argv($class->_orig_argv); } return $cmd->run_command(@ARGV); } =pod =head2 load_plugins auto load and require plugin modules Example # MyApp.pm # MyApp::Plugin::GoodMorning and App::CLI::Plugin::Config::YAML::Syck require __PACKAGE__->load_plugins(qw(+MyApp::Plugin::GoodMorning Config::YAML::Syck)); # MyApp/Plugin/GoodMorning.pm package MyApp::Plugin::GoodMorning; use strict; sub good_morning { my $self = shift; print "Good monring!\n"; } # MyApp/Hello.pm package MyApp::Hello; use strict; use base qw(App::CLI::Command); sub run { my($self, @args) = @_; $self->good_morning; } # myapp #!/usr/bin/perl use strict; use MyApp; MyApp->dispatch; # execute [kurt@localhost ~] myapp hello Good morning! =cut sub load_plugins { my($class, @load_plugins) = @_; my @loaded_plugins = @{$class->_plugins}; foreach my $plugin(@load_plugins){ if ($plugin =~ /^\+/x) { $plugin =~ s/^\+//x; } else { $plugin = "App::CLI::Plugin::$plugin"; } $plugin->require or croak "plugin load error: $UNIVERSAL::require::ERROR"; $plugin->import; push @loaded_plugins, $plugin; } return $class->_plugins(\@loaded_plugins); } =pod =head2 config configuration method Example # MyApp.pm __PACKAGE__->config( name => "kurt", favorite_group => "nirvana", favorite_song => ["Lounge Act", "Negative Creep", "Radio Friendly Unit Shifter", "You Know You're Right"] ); # MyApp/Hello.pm package MyApp::Hello; use strict; use base qw(App::CLI::Command); sub run { my($self, @args) = @_; print "My name is " . $self->config->{name} . "\n"; print "My favorite group is " . $self->config->{favorite_group} . "\n"; print "My favorite song is " . join(",", @{$self->config->{favorite_song}}); print " and Smells Like Teen Spirit\n" } # myapp #!/usr/bin/perl use strict; use MyApp; MyApp->dispatch; # execute [kurt@localhost ~] myapp hello My name is kurt My favorite group is nirvana My favorite song is Lounge Act,Negative Creep,Radio Friendly Unit Shifter,You Know You're Right and Smells Like Teen Spirit =cut sub config { my($class, %config) = @_; $class->_config(\%config); return $class->_config; } =head1 COMPONENT METHOD =head2 argv0 my script name Example: # MyApp/Hello.pm package MyApp::Hello; use strict; use feature ":5.10.0"; use base qw(App::CLI::Command); sub run { my($self, @args) = @_; say "my script name is " . $self->argv0; } 1; # execute [kurt@localhost ~] myapp hello my script name is myapp =head2 full_argv0 my script fullname Example: # MyApp/Hello.pm package MyApp::Hello; use strict; use feature ":5.10.0"; use base qw(App::CLI::Command); sub run { my($self, @args) = @_; say "my script full name is " . $self->full_argv0; } 1; # execute [kurt@localhost ~] myapp hello my script name is /home/kurt/myapp =head2 cmdline my execute cmdline string Example: # MyApp/Hello.pm package MyApp::Hello; use strict; use feature ":5.10.0"; use base qw(App::CLI::Command); sub run { my($self, @args) = @_; say "my script cmdline is [" . $self->cmdline . "]"; } 1; # execute [kurt@localhost ~] myapp hello --verbose --num=10 my script cmdline is [/home/kurt/myapp hello --verbose --num=10] =head2 orig_argv my execute script original argv Example: # MyApp/Hello.pm package MyApp::Hello; use strict; use feature ":5.10.0"; use base qw(App::CLI::Command); sub run { my($self, @args) = @_; say "my script original argv is [" join(", ", @{$self->orig_argv}) . "]"; } 1; # execute [kurt@localhost ~] myapp hello --verbose --num=10 my script original argv is [hello,--verbose, --num=10] =head2 stash like global variable in Command package Example: # MyApp/Hello.pm package MyApp::Hello; use strict; use feature ":5.10.0"; use base qw(App::CLI::Command); sub run { my($self, @args) = @_; $self->stash->{name} = "kurt"; say "stash value: " . $self->stash->{name}; } 1; =head2 new_callback install new callback phase Example: $self->new_callback("some_phase"); # registered callback argument pattern $self->new_callback("some_phase", sub { $self = shift; "anything to do..." }); =head2 add_callback install callback Example: $self->add_callback("some_phase", sub { my $self = shift; say "some_phase method No.1" }); $self->add_callback("some_phase", sub { my $self = shift; say "some_phase method No.1" }); $self->add_callback("any_phase", sub { my($self, @args) = @_; say "any_phase args: @args"; }); =cut =head2 exec_callback execute callback Example: $self->execute_callback("some_phase"); # some_phase method method No.1 # some_phase method method No.2 $self->execute_callback("any_phase", qw(one two three)); # any_phase args: one two three =head2 exists_callback exists callback check Example: if ($self->exists_callback("some_phase")) { $self->exec_callback("some_phase"); } else { die "some_phase is not exists callback phase"; } =head2 exit_value set exit value Example: # program exit value is 1(ex. echo $?) $self->exit_value(1); =head2 finished setup or prepare phase and 1 set, run and postrun phase will not run. default 0 Example: # MyApp/Hello.pm package MyApp::Hello; use strict; use base qw(App::CLI::Command); sub prerun { my($self, @args) = @_; $self->finished(1); } # non execute sub run { my($self, @args) = @_; print "hello\n"; } =head2 throw raises an exception, fail phase transitions Example: # MyApp/Hello.pm package MyApp::Hello; use strict; use base qw(App::CLI::Command); sub run { my($self, @args) = @_; my $file = "/path/to/file"; open my $fh, "< $file" or $self->throw("can not open file:$file"); while ( my $line = <$fh> ) { chomp $line; print "$line\n"; } close $fh; } # transitions fail phase method sub fail { my($self, @args) = @_; # e is App:CLI::Extension::Exception instance printf "ERROR: %s", $self->e; printf "STACKTRACE: %s", $self->e->stacktrace; } # myapp #!/usr/bin/perl use strict; use MyApp; MyApp->dispatch; # execute [kurt@localhost ~] myapp hello ERROR: can not open file:/path/to/file at lib/MyApp/Throw.pm line 10. STACKTRACE: can not open file:/path/to/file at lib/MyApp/Throw.pm line 10 MyApp::Throw::run('MyApp::Throw=HASH(0x81bd6b4)') called at /usr/lib/perl5/site_perl/5.8.8/App/CLI/Extension/Component/RunCommand.pm line 36 App::CLI::Extension::Component::RunCommand::run_command('MyApp::Throw=HASH(0x81bd6b4)') called at /usr/lib/perl5/site_perl/5.8.8/App/CLI/Extension.pm line 177 App::CLI::Extension::dispatch('MyApp') called at ./myapp line 7 when you run throw method, App::CLI::Extension::Exception instance that $self->e is set to. App::CLI::Extension::Exception is the Error::Simple is inherited. refer to the to documentation of C throw method without running CORE::die if you run the $self->e is the Error::Simple instance will be set =head2 e App::CLI::Extension::Exception or Error::Simple instance. There is a ready to use, fail phase only =head1 RUN PHASE METHOD =head2 setup =head2 prerun =head2 postrun =head2 finish program last phase. By default, the exit will be executed automatically, exit if you do not want the APPCLI_NON_EXIT environment valiable how do I set the (value is whatever) =head2 fail error phase. default exit value is 255. if you want to change exit_value, see exit_value manual =cut 1; __END__ =head1 SEE ALSO L L L =head1 AUTHOR Akira Horimoto =head1 COPYRIGHT AND LICENSE This library is free software; you can redistribute it and/or modify it under the same terms as Perl itself. Copyright (C) 2009 Akira Horimoto =cut

About

perl command line interface framework

Resources

Languages

You can’t perform that action at this time.