File Coverage

blib/lib/OptArgs2/SubCmd.pm
Criterion Covered Total %
statement 55 62 88.7
branch 11 20 55.0
condition 6 11 54.5
subroutine 8 9 88.8
pod 0 3 0.0
total 80 105 76.1


line stmt bran cond sub pod time code
1             package OptArgs2::SubCmd;
2 6     6   44 use strict;
  6         10  
  6         261  
3 6     6   29 use warnings;
  6         10  
  6         326  
4 6     6   34 use parent 'OptArgs2::CmdBase';
  6         10  
  6         34  
5             ### START Class::Inline ### v0.0.1 Wed Dec 3 10:44:53 2025
6             require Carp;
7             our ( @_CLASS, $_FIELDS, %_NEW );
8              
9             sub new {
10 5     5 0 9 my $class = shift;
11 5   33     21 my $CLASS = ref $class || $class;
12 5   66     17 $_NEW{$CLASS} //= do {
13 2         4 my ( %seen, @new, @build );
14 2         6 my @possible = ($CLASS);
15 2         6 while (@possible) {
16 4         8 my $c = shift @possible;
17 6     6   1159 no strict 'refs';
  6         12  
  6         5370  
18 4 50       6 push @new, $c . '::_NEW' if exists &{ $c . '::_NEW' };
  4         23  
19 4 100       5 push @build, $c . '::BUILD' if exists &{ $c . '::BUILD' };
  4         20  
20 4         8 $seen{$c}++;
21 4 50       6 if ( exists &{ $c . '::DOES' } ) {
  4         11  
22 0         0 push @possible, grep { not $seen{$_}++ } $c->DOES('*');
  0         0  
23             }
24 4         7 push @possible, grep { not $seen{$_}++ } @{ $c . '::ISA' };
  2         11  
  4         12  
25             }
26 2         12 [ [ reverse(@new) ], [ reverse(@build) ] ];
27             };
28 5 50       44 my $self = { @_ ? @_ > 1 ? @_ : %{ $_[0] } : () };
  0 50       0  
29 5         11 bless $self, $CLASS;
30 5         75 my $attrs = { map { ( $_ => 1 ) } keys %$self };
  30         48  
31 5         12 map { $self->$_($attrs) } @{ $_NEW{$CLASS}->[0] };
  10         33  
  5         13  
32             {
33 5         11 local $Carp::CarpLevel = 3;
  5         11  
34             Carp::carp("OptArgs2::SubCmd: unexpected argument '$_'")
35 5         18 for keys %$attrs
36             }
37 5         9 map { $self->$_ } @{ $_NEW{$CLASS}->[1] };
  5         18  
  5         16  
38 5         13 $self;
39             }
40              
41             sub _NEW {
42 5     5   10 CORE::state $fix_FIELDS = do {
43 2 50       24 $_FIELDS = { @_CLASS > 1 ? @_CLASS : %{ $_CLASS[0] } };
  0         0  
44 2 50       21 $_FIELDS = $_FIELDS->{'FIELDS'} if exists $_FIELDS->{'FIELDS'};
45             };
46 5 50       11 if ( my @missing = grep { not exists $_[0]->{$_} } 'parent' ) {
  5         23  
47 0         0 Carp::croak( 'OptArgs2::SubCmd required initial argument(s): '
48             . join( ', ', @missing ) );
49             }
50 5         14 map { delete $_[1]->{$_} } 'parent';
  5         17  
51             }
52              
53             sub __RO {
54 0     0   0 my ( undef, undef, undef, $sub ) = caller(1);
55 0         0 Carp::confess("attribute $sub is read-only");
56             }
57              
58             sub name {
59 20 50   20 0 51 __RO() if @_ > 1;
60 20   66     83 $_[0]{'name'} //= $_FIELDS->{'name'}->{'default'}->( $_[0] );
61             }
62 12 50 50 12 0 32 sub parent { __RO() if @_ > 1; $_[0]{'parent'} // undef }
  12         44  
63             @_CLASS = grep 1, ### END Class::Inline ###
64             name => { # once legacy code goes move this into CmdBase
65             init_arg => undef,
66             default => sub {
67             my $x = $_[0]->class;
68             $x =~ s/.*://;
69             $x =~ s/_/-/g;
70             $x;
71             },
72             },
73             parent => { required => 1, },
74             ;
75              
76             our @CARP_NOT = @OptArgs2::CARP_NOT;
77              
78             1;
79              
80             __END__