6

Update from FMc

I'm putting a bounty on this question, because I'm puzzling over the same problem. To rephrase the question, how do you implement application-level options (those that apply to an entire program, script.pl), as opposed to those that apply to individual commands (search in this example).

The original question

How can I use App::Cmd to create an interface like this

script.pl --config <file> search --options args

?

I can do:

./script.pl search --options args
./script.pl search args
./script.pl search --options

What I'm trying to achieve is getting an option for the config file like so:

./script.pl --config file.conf search --options args

I've looked at App::Cmd::Tutorial on cpan but so far I haven't had any luck getting it to work.

Community
  • 1
  • 1
user419056
  • 61
  • 2
  • Could you show a little bit more about what you're expecting would be in file.conf vs. what's passed in the command line for the search command (--options, anything else?)? My initial understanding is that you want to set default values in file.conf and then allow for command line args to optionally override those values, plus set some amount of configurations to be used by all commands. I have a solution for that second part, but don't want to supply that if it's not what you are looking for. – mrk May 26 '11 at 00:31
  • @Mark Koopman Perhaps I've unfairly highjacked the original question, but I'm simply stuck on the issue of how to achieve global program options. That's how I read the original question, too, but perhaps I glossed over an implicit goal regarding the config file itself. – FMc May 26 '11 at 09:39

1 Answers1

6

You can specify global options in App::Cmd like below. We need three files:

script.pl:

use Tool;
Tool->run;

Tool.pm:

package Tool;
use strict; use warnings;
use base 'App::Cmd';

sub global_opt_spec {
    ['config=s' => "Specify configuration file"];
}

1;

and Tool/Command/search.pm:

package Tool::Command::search;
use strict; use warnings;
use base 'App::Cmd::Command';

sub opt_spec {
    ["option" => "switch on something"],
}

sub execute {
    my ($self, $opt, $args) = @_;

    warn "Running some action\n";
    warn 'Config file = ' . $self->app->global_options->{config}, "\n";
    warn 'Option      = ' . $opt->{option}, "\n";
}

1;

The example shows how to define global option and access it from within search action.

bvr
  • 9,687
  • 22
  • 28
  • A couple of additional notes for completeness. (1) One can also use an OO style to access the option values: `$self->app->global_options->config` and `$opt->option`. (2) The docs for `App::Cmd` appear to encourage `use App::Cmd::Setup -app` and `use Tool -command`, rather than `use base`. Not entirely sure why. – FMc May 26 '11 at 10:12
  • @FMc - (1) good point, I did not notice it has also accessor. (2) In documentation for [App::Cmd::Setup](http://search.cpan.org/perldoc?App::Cmd::Setup) it is mentioned that the sugar is especially useful in combination with plugins. The test suite examples are mostly without it. – bvr May 26 '11 at 12:07
  • How do you get script.pl to document that it has a global --option? No "--option" in output from "script.pl --help" or "script.pl help" or "script.pl help search" – Peter V. Mørch Jan 11 '17 at 05:04