File Coverage

blib/lib/App/hopen/Gen/Ninja/AssetGraphNode.pm
Criterion Covered Total %
statement 61 68 89.7
branch 9 10 90.0
condition 0 2 0.0
subroutine 12 12 100.0
pod n/a
total 82 92 89.1


line stmt bran cond sub pod time code
1             # App::hopen::Gen::Ninja::AssetGraphNode - AssetOp for Gen::Ninja
2             package App::hopen::Gen::Ninja::AssetGraphNode;
3 1     1   6 use Data::Hopen qw(getparameters *VERBOSE);
  1         2  
  1         85  
4 1     1   13 use strict; use warnings;
  1     1   2  
  1         18  
  1         7  
  1         2  
  1         23  
5 1     1   10 use Data::Hopen::Base;
  1         2  
  1         16  
6              
7             our $VERSION = '0.000013'; # TRIAL
8              
9 1     1   1318 use parent 'App::hopen::G::AssetOp';
  1         3  
  1         5  
10             use Class::Tiny {
11 0         0 _rules => sub { +{} },
12 1     1   85 };
  1         2  
  1         8  
13              
14 1     1   304 use App::hopen::BuildSystemGlobals; # for $DestDir
  1         2  
  1         104  
15 1     1   6 use Quote::Code;
  1         2  
  1         5  
16 1     1   46 use String::Print;
  1         2  
  1         8  
17              
18             # Docs {{{1
19              
20             =head1 NAME
21              
22             App::hopen::Gen::Ninja::AssetGraphNode - AssetOp for Gen::Ninja
23              
24             =head1 SYNOPSIS
25              
26             TODO
27              
28             =head1 ATTRIBUTES
29              
30             =head2 _rules
31              
32             TODO? Store mapping from command lines to rules? Don't want to generate
33             a separate rule for every command if we can help it.
34              
35             =head1 FUNCTIONS
36              
37             =cut
38              
39             # }}}1
40              
41 1     1   187 use vars::i '&OUTPUT' => sub { '__R_Ninjafile' };
  1     5   2  
  1         17  
  5         36  
42              
43             =head2 _run
44              
45             Generate a piece of a C<build.ninja> file and write it to the filehandle in
46             C<__R_Ninjafile>.
47              
48             If the `how` of a node is defined but falsy, it's a goal.
49             If `how` is defined and truthy, it's a file.
50              
51             =cut
52              
53             sub _run {
54 4     4   1115 state $ruleidx=0;
55              
56 4         17 my ($self, %args) = getparameters('self', [qw(; phase visitor)], @_);
57 4         246 my $fh = $self->scope->find(OUTPUT);
58             # TODO deal with multiple inputs being merged in DAG::_run()
59              
60 4         4063 my @inputs = $self->input_assets;
61 4         18 my $output = $self->asset->target;
62 4 100       9 $output = $output->path_wrt($DestDir) if eval { $output->DOES('App::hopen::Util::BasedPath') };
  4         52  
63             # TODO refactor this processing into a utility module/function
64              
65             # Debugging output
66 4 50       1207 if($VERBOSE) {
67 0         0 print $fh qc'\n# From node {$self->name}:\n';
  0         0  
68 0   0     0 print $fh qc' # {$self->how//"<nothing to be done>"}\n';
  0         0  
69 0         0 print $fh qc' # Depends on {$_->target}\n' foreach @inputs;
  0         0  
70             }
71              
72 4 100       88 if(defined $self->how) {
73 3         36 my @paths = map { $_->target->path_wrt($DestDir) } @inputs;
  3         11  
74 3         1087 my $recipe = $self->how;
75             # TODO refactor this processing into a utility module/function
76 3 100       102 warn "I don't yet support #first very well (in ``$recipe'')" if $recipe =~ /#first/;
77 3         29 $recipe =~ s<#first\b><\$in>g; # first input # TODO FIXME
78 3         14 $recipe =~ s<#all\b><\$in>g; # all inputs
79 3         9 $recipe =~ s<#out\b><\$out>g;
80              
81             # Emit the entry. If the recipe is defined but falsy,
82             # this is a goal, so it gets a `phony` and a `default`.
83              
84             # TODO FIXME ugly hack: for now, each command gets its own rule.
85              
86 3 100       56 if($self->how) { # File target
87              
88 2         29 my $rulename = 'rule_' . ++$ruleidx;
89 2         7 print $fh qc_to <<"EOT"
90 2         5 rule #{$rulename}
91             command = #{$recipe}
92 2         6  
  2         8  
  2         16  
  2         6  
93             build #{$output}: #{$rulename} #{join(" ", @paths)}
94              
95             EOT
96             } else { # Goal target
97              
98 1         6 print $fh qc_to <<"EOT"
  1         6  
99 1         14 build #{$output}: phony #{join(" ", @paths)}
  1         11  
100             default #{$output}
101              
102             EOT
103             }
104              
105             } #endif defined $self->how
106              
107 4         63 $self->make($self->asset);
108 4         17 return {};
109             } #_run()
110              
111             1;
112             __END__
113             # vi: set fdm=marker: #