1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
|
** Getopt::Long
[[http://search.cpan.org/perldoc?Getopt::Long][Getopt::long]] is a
useful module to parse command line arguements.
A basic usage is something like this:
#+BEGIN_SRC perl
#!/usr/bin/perl -w
use strict;
use YAML::Syck;
use Getopt::Long;
GetOptions('config=s' => \my $cfg_file,);
my $config = LoadFile $cfg_file
#+END_SRC
In *GetOptions*, we require a value for config with *config=s*. If we
wante an integer, we replace 's' with 'i', and for a floating point,
with 'f'.
Call your script :
#+BEGIN_EXAMPLE
% script.pl --config=file.yml #this one works
% script.pl --config file.yml #this one too!
% script.pl -c file.yml #and this one too
#+END_EXAMPLE
The three syntaxes are understood.
A good practices is to combine this module with
[[http://search.cpan.org/perldoc?Pod::Usage][Pod::Usage]]. Let's do some
modifications on the example:
#+BEGIN_SRC perl
#!/usr/bin/perl -w
use strict;
use YAML::Syck;
use Getopt::Long;
use Pod::Usage;
GetOptions('config=s' => \my $cfg_file,) or pod2usage(2);
pod2usage(2) unless @ARGV > 0;
my $config = LoadFile $cfg_file
__END__
=head1 NAME
uberscript
=head1 SYNOPSIS
uberscript [options]
Options:
--config config file
=head1 Options
=over 4
=item B<config>
Path to the config file
#+END_SRC
then
#+BEGIN_EXAMPLE
% perl uberscript
Usage:
uberscript [options]
Options:
--config config file
#+END_EXAMPLE
From now if we call our script without argument, the POD will be printed
on STDIN.
** MooseX::Getopt
[[http://search.cpan.org/perldoc?MooseX::Getopt][MooseX::Getopt]] is a
Role that add a =new_with_options= to your object. We create a basic
Object :
#+BEGIN_SRC perl
package OurShinyObject;
use Moose;
with qw/MooseX::Getopt/;
has 'config' => (isa => 'Str', is => 'ro', required => 1);
has 'context' => (
isa => 'HashRef',
is => 'rw',
lazy => 1,
traits => ['NoGetopt'],
default => sub { LoadFile shift->config }
);
...
#+END_SRC
create a script to call this object
#+BEGIN_SRC perl
#!/usr/bin/perl -w
use strict;
use OurShinyObject;
my $obj = OurShinyObject->new_from_options();
#+END_SRC
#+BEGIN_SRC sh
% script.pl --config file.yml
#+END_SRC
The role will set our attribute *context* using the value from the
argument set on the command line.
The =traits => ['NoGetopt']= indicate that this attributes will be not
be read from the command line. An alternate way to do this is to prefix
the attributes with **\_**.
** conclusion (?)
When you write a script, even if you're sure you will never need to have
more than one argument, or that you never will have to update the code,
/please/ consider to use of *Getopt::Long* instead of a =shift @ARGV=,
because we all know that you will at a certain point update this script
and you will more than one argument :).
|