| line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
|
1
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
2
|
|
|
|
|
|
|
package Pod::Loom::Template; |
|
3
|
|
|
|
|
|
|
# |
|
4
|
|
|
|
|
|
|
# Copyright 2009 Christopher J. Madsen |
|
5
|
|
|
|
|
|
|
# |
|
6
|
|
|
|
|
|
|
# Author: Christopher J. Madsen <perl@cjmweb.net> |
|
7
|
|
|
|
|
|
|
# Created: 6 Oct 2009 |
|
8
|
|
|
|
|
|
|
# |
|
9
|
|
|
|
|
|
|
# This program is free software; you can redistribute it and/or modify |
|
10
|
|
|
|
|
|
|
# it under the same terms as Perl itself. |
|
11
|
|
|
|
|
|
|
# |
|
12
|
|
|
|
|
|
|
# This program is distributed in the hope that it will be useful, |
|
13
|
|
|
|
|
|
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
|
14
|
|
|
|
|
|
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See either the |
|
15
|
|
|
|
|
|
|
# GNU General Public License or the Artistic License for more details. |
|
16
|
|
|
|
|
|
|
# |
|
17
|
|
|
|
|
|
|
# ABSTRACT: Standard base class for Pod::Loom templates |
|
18
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
19
|
|
|
|
|
|
|
|
|
20
|
1
|
|
|
1
|
|
14
|
use 5.008; |
|
|
1
|
|
|
|
|
2
|
|
|
|
1
|
|
|
|
|
44
|
|
|
21
|
|
|
|
|
|
|
our $VERSION = '0.07'; |
|
22
|
|
|
|
|
|
|
# This file is part of Pod-Loom 0.08 (March 23, 2014) |
|
23
|
|
|
|
|
|
|
|
|
24
|
1
|
|
|
1
|
|
3
|
use Moose; |
|
|
1
|
|
|
|
|
1
|
|
|
|
1
|
|
|
|
|
6
|
|
|
25
|
|
|
|
|
|
|
|
|
26
|
1
|
|
|
1
|
|
4811
|
use Pod::Loom::Parser (); |
|
|
1
|
|
|
|
|
2
|
|
|
|
1
|
|
|
|
|
116
|
|
|
27
|
|
|
|
|
|
|
|
|
28
|
|
|
|
|
|
|
|
|
29
|
|
|
|
|
|
|
has tmp_collected => ( |
|
30
|
|
|
|
|
|
|
is => 'rw', |
|
31
|
|
|
|
|
|
|
isa => 'HashRef[ArrayRef]', |
|
32
|
|
|
|
|
|
|
); |
|
33
|
|
|
|
|
|
|
|
|
34
|
|
|
|
|
|
|
has tmp_encoding => ( |
|
35
|
|
|
|
|
|
|
is => 'rw', |
|
36
|
|
|
|
|
|
|
isa => 'Object', |
|
37
|
|
|
|
|
|
|
); |
|
38
|
|
|
|
|
|
|
|
|
39
|
|
|
|
|
|
|
has tmp_groups => ( |
|
40
|
|
|
|
|
|
|
is => 'rw', |
|
41
|
|
|
|
|
|
|
isa => 'HashRef[HashRef]', |
|
42
|
|
|
|
|
|
|
); |
|
43
|
|
|
|
|
|
|
|
|
44
|
|
|
|
|
|
|
has tmp_filename => ( |
|
45
|
|
|
|
|
|
|
is => 'rw', |
|
46
|
|
|
|
|
|
|
isa => 'Str', |
|
47
|
|
|
|
|
|
|
); |
|
48
|
|
|
|
|
|
|
|
|
49
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
50
|
|
|
|
|
|
|
# Tied hashes for interpolating function calls into strings: |
|
51
|
|
|
|
|
|
|
|
|
52
|
|
|
|
|
|
|
{ package Pod::Loom::_Interpolation; |
|
53
|
|
|
|
|
|
|
|
|
54
|
1
|
|
|
1
|
|
3
|
sub TIEHASH { bless $_[1], $_[0] } |
|
55
|
0
|
|
|
0
|
|
0
|
sub FETCH { $_[0]->($_[1]) } |
|
56
|
|
|
|
|
|
|
} # end Pod::Loom::_Interpolation |
|
57
|
|
|
|
|
|
|
|
|
58
|
|
|
|
|
|
|
our %E; |
|
59
|
|
|
|
|
|
|
tie %E, 'Pod::Loom::_Interpolation', sub { $_[0] }; # eval |
|
60
|
|
|
|
|
|
|
|
|
61
|
1
|
|
|
1
|
|
5
|
use Exporter 'import'; |
|
|
1
|
|
|
|
|
1
|
|
|
|
1
|
|
|
|
|
1916
|
|
|
62
|
|
|
|
|
|
|
our @EXPORT_OK = qw(%E); |
|
63
|
|
|
|
|
|
|
|
|
64
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
65
|
|
|
|
|
|
|
has _tmp_warned => ( |
|
66
|
|
|
|
|
|
|
is => 'rw', |
|
67
|
|
|
|
|
|
|
isa => 'Bool', |
|
68
|
|
|
|
|
|
|
); |
|
69
|
|
|
|
|
|
|
|
|
70
|
|
|
|
|
|
|
|
|
71
|
|
|
|
|
|
|
sub warning |
|
72
|
|
|
|
|
|
|
{ |
|
73
|
0
|
|
|
0
|
1
|
0
|
my ($self, $message) = @_; |
|
74
|
|
|
|
|
|
|
|
|
75
|
0
|
0
|
|
|
|
0
|
unless ($self->_tmp_warned) { |
|
76
|
0
|
|
|
|
|
0
|
warn "While processing " . $self->tmp_filename . "\n"; |
|
77
|
0
|
|
|
|
|
0
|
$self->_tmp_warned(1); |
|
78
|
|
|
|
|
|
|
} |
|
79
|
|
|
|
|
|
|
|
|
80
|
0
|
|
|
|
|
0
|
warn " $message"; |
|
81
|
|
|
|
|
|
|
} # end warning |
|
82
|
|
|
|
|
|
|
|
|
83
|
|
|
|
|
|
|
|
|
84
|
|
|
|
|
|
|
sub error |
|
85
|
|
|
|
|
|
|
{ |
|
86
|
0
|
|
|
0
|
1
|
0
|
my ($self, $message) = @_; |
|
87
|
|
|
|
|
|
|
|
|
88
|
0
|
|
|
|
|
0
|
die 'Error procesing ' . $self->tmp_filename . "\n $message"; |
|
89
|
|
|
|
|
|
|
} # end error |
|
90
|
|
|
|
|
|
|
|
|
91
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
92
|
|
|
|
|
|
|
# These methods are likely to be overloaded in subclasses: |
|
93
|
|
|
|
|
|
|
|
|
94
|
|
|
|
|
|
|
|
|
95
|
0
|
|
|
0
|
1
|
0
|
sub collect_commands { [ 'head1' ] } |
|
96
|
0
|
|
|
0
|
1
|
0
|
sub override_section { 0 } |
|
97
|
|
|
|
|
|
|
|
|
98
|
|
|
|
|
|
|
has sections => ( |
|
99
|
|
|
|
|
|
|
is => 'ro', |
|
100
|
|
|
|
|
|
|
isa => 'ArrayRef[Str]', |
|
101
|
|
|
|
|
|
|
required => 1, |
|
102
|
|
|
|
|
|
|
builder => '_build_sections', |
|
103
|
|
|
|
|
|
|
); |
|
104
|
|
|
|
|
|
|
|
|
105
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
106
|
|
|
|
|
|
|
|
|
107
|
|
|
|
|
|
|
|
|
108
|
|
|
|
|
|
|
sub expect_sections |
|
109
|
|
|
|
|
|
|
{ |
|
110
|
13
|
|
|
13
|
1
|
12
|
my ($self) = @_; |
|
111
|
|
|
|
|
|
|
|
|
112
|
13
|
|
|
|
|
371
|
my $collected = $self->tmp_collected; |
|
113
|
|
|
|
|
|
|
|
|
114
|
13
|
|
|
|
|
16
|
my @sections; |
|
115
|
|
|
|
|
|
|
|
|
116
|
13
|
50
|
|
|
|
14
|
foreach my $block (@{ $collected->{'Pod::Loom-sections'} || [] }) { |
|
|
13
|
|
|
|
|
56
|
|
|
117
|
0
|
|
|
|
|
0
|
push @sections, split /\s*\n/, $block; |
|
118
|
|
|
|
|
|
|
} # end foreach $block |
|
119
|
|
|
|
|
|
|
|
|
120
|
13
|
50
|
|
|
|
27
|
@sections = @{ $self->sections } unless @sections; |
|
|
13
|
|
|
|
|
356
|
|
|
121
|
|
|
|
|
|
|
|
|
122
|
13
|
|
|
|
|
38
|
$self->_insert_sections(\@sections, before => -1); |
|
123
|
13
|
|
|
|
|
28
|
$self->_insert_sections(\@sections, after => 0); |
|
124
|
|
|
|
|
|
|
|
|
125
|
13
|
|
|
|
|
12
|
my %omit; |
|
126
|
|
|
|
|
|
|
|
|
127
|
13
|
100
|
|
|
|
12
|
foreach my $block (@{ $collected->{'Pod::Loom-omit'} || [] }) { |
|
|
13
|
|
|
|
|
43
|
|
|
128
|
12
|
|
|
|
|
278
|
$omit{$_} = 1 for split /\s*\n/, $block; |
|
129
|
|
|
|
|
|
|
} # end foreach $block |
|
130
|
|
|
|
|
|
|
|
|
131
|
13
|
|
|
|
|
23
|
return [ grep { not $omit{$_} } @sections ]; |
|
|
208
|
|
|
|
|
270
|
|
|
132
|
|
|
|
|
|
|
} # end expect_sections |
|
133
|
|
|
|
|
|
|
|
|
134
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
135
|
|
|
|
|
|
|
# Insert sections before or after other sections: |
|
136
|
|
|
|
|
|
|
|
|
137
|
|
|
|
|
|
|
sub _insert_sections |
|
138
|
|
|
|
|
|
|
{ |
|
139
|
26
|
|
|
26
|
|
31
|
my ($self, $sectionsList, $type, $index) = @_; |
|
140
|
|
|
|
|
|
|
|
|
141
|
26
|
50
|
|
|
|
636
|
my $blocks = $self->tmp_collected->{"Pod::Loom-insert_$type"} |
|
142
|
|
|
|
|
|
|
or return; |
|
143
|
|
|
|
|
|
|
|
|
144
|
0
|
|
|
|
|
0
|
my @empty; |
|
145
|
|
|
|
|
|
|
|
|
146
|
0
|
|
|
|
|
0
|
foreach my $block (@$blocks) { |
|
147
|
0
|
|
|
|
|
0
|
my @list = split /\s*\n/, $block; |
|
148
|
|
|
|
|
|
|
|
|
149
|
0
|
0
|
|
|
|
0
|
next unless @list; |
|
150
|
|
|
|
|
|
|
|
|
151
|
0
|
|
|
|
|
0
|
$self->error("Can't insert $type nonexistent section $list[$index]") |
|
152
|
0
|
0
|
|
|
|
0
|
unless grep { $_ eq $list[$index] } @$sectionsList; |
|
153
|
|
|
|
|
|
|
|
|
154
|
|
|
|
|
|
|
|
|
155
|
|
|
|
|
|
|
# We remove each section listed: |
|
156
|
0
|
|
|
|
|
0
|
my %remap = map { $_ => \@empty } @list; |
|
|
0
|
|
|
|
|
0
|
|
|
157
|
|
|
|
|
|
|
|
|
158
|
|
|
|
|
|
|
# Except the one at $index, where we insert the entire list: |
|
159
|
0
|
|
|
|
|
0
|
$remap{ $list[$index] } = \@list; |
|
160
|
|
|
|
|
|
|
|
|
161
|
0
|
0
|
|
|
|
0
|
@$sectionsList = map { $remap{$_} ? @{$remap{$_}} : $_ } @$sectionsList; |
|
|
0
|
|
|
|
|
0
|
|
|
|
0
|
|
|
|
|
0
|
|
|
162
|
|
|
|
|
|
|
} # end foreach $block |
|
163
|
|
|
|
|
|
|
|
|
164
|
|
|
|
|
|
|
} # end _insert_sections |
|
165
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
166
|
|
|
|
|
|
|
|
|
167
|
|
|
|
|
|
|
|
|
168
|
|
|
|
|
|
|
sub required_attr |
|
169
|
|
|
|
|
|
|
{ |
|
170
|
24
|
|
|
24
|
1
|
28
|
my $self = shift; |
|
171
|
24
|
|
|
|
|
21
|
my $section = shift; |
|
172
|
|
|
|
|
|
|
|
|
173
|
46
|
|
|
|
|
1279
|
map { |
|
174
|
24
|
|
|
|
|
29
|
my $v = $self->$_; |
|
175
|
46
|
50
|
|
|
|
128
|
defined $v |
|
176
|
|
|
|
|
|
|
? $v |
|
177
|
|
|
|
|
|
|
: $self->error("The $section section requires you to set `$_'\n") |
|
178
|
|
|
|
|
|
|
} @_; |
|
179
|
|
|
|
|
|
|
} # end required_attr |
|
180
|
|
|
|
|
|
|
|
|
181
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
182
|
|
|
|
|
|
|
# Sort each arrayref in tmp_collected (if appropriate): |
|
183
|
|
|
|
|
|
|
|
|
184
|
|
|
|
|
|
|
sub _sort_collected |
|
185
|
|
|
|
|
|
|
{ |
|
186
|
13
|
|
|
13
|
|
15
|
my $self = shift; |
|
187
|
|
|
|
|
|
|
|
|
188
|
13
|
|
|
|
|
343
|
my $collected = $self->tmp_collected; |
|
189
|
13
|
|
|
|
|
299
|
my $groups = $self->tmp_groups; |
|
190
|
|
|
|
|
|
|
|
|
191
|
13
|
|
|
|
|
13
|
foreach my $type (@{ $self->collect_commands }) { |
|
|
13
|
|
|
|
|
31
|
|
|
192
|
|
|
|
|
|
|
# Is this type of entry sorted at all? |
|
193
|
65
|
50
|
|
|
|
91
|
my $sort = $self->_find_sort_order($type) or next; |
|
194
|
|
|
|
|
|
|
|
|
195
|
0
|
|
|
|
|
0
|
foreach my $group ($type, map { "$type-$_" } keys %{ $groups->{$type} }) { |
|
|
0
|
|
|
|
|
0
|
|
|
|
0
|
|
|
|
|
0
|
|
|
196
|
|
|
|
|
|
|
# Begin Schwartzian transform (entry_name => entry): |
|
197
|
|
|
|
|
|
|
# We convert the keys to lower case to make it case insensitive. |
|
198
|
0
|
0
|
|
|
|
0
|
my @sortable = map { /^=\S+ \s+ (\S (?:.*\S)? )/x |
|
|
0
|
|
|
|
|
0
|
|
|
199
|
|
|
|
|
|
|
? [ lc $1 => $_ ] |
|
200
|
|
|
|
|
|
|
: [ '' => $_ ] # Should this even be allowed? |
|
201
|
0
|
|
|
|
|
0
|
} @{ $collected->{$group} }; |
|
202
|
|
|
|
|
|
|
|
|
203
|
|
|
|
|
|
|
# Set up %special to handle any top-of-the-list entries: |
|
204
|
0
|
|
|
|
|
0
|
my $count = 1; |
|
205
|
0
|
|
|
|
|
0
|
my %special; |
|
206
|
0
|
0
|
|
|
|
0
|
%special = map { lc $_ => $count++ } @$sort if ref $sort; |
|
|
0
|
|
|
|
|
0
|
|
|
207
|
|
|
|
|
|
|
|
|
208
|
|
|
|
|
|
|
# Sort specials first, then the rest ASCIIbetically: |
|
209
|
0
|
|
|
|
|
0
|
my @sorted = |
|
210
|
0
|
0
|
0
|
|
|
0
|
map { $_->[1] } # finish the Schwartzian transform |
|
|
|
|
0
|
|
|
|
|
|
|
|
|
0
|
|
|
|
|
|
211
|
0
|
|
|
|
|
0
|
sort { ($special{$a->[0]} || $count) <=> ($special{$b->[0]} || $count) |
|
212
|
|
|
|
|
|
|
or $a->[0] cmp $b->[0] # if the keys match |
|
213
|
|
|
|
|
|
|
or $a->[1] cmp $b->[1] } # compare the whole entry |
|
214
|
|
|
|
|
|
|
@sortable; |
|
215
|
|
|
|
|
|
|
|
|
216
|
0
|
|
|
|
|
0
|
$collected->{$group} = \@sorted; |
|
217
|
|
|
|
|
|
|
} # end foreach $group of $type |
|
218
|
|
|
|
|
|
|
} # end foreach $type of $collected entry |
|
219
|
|
|
|
|
|
|
} # end _sort_collected |
|
220
|
|
|
|
|
|
|
|
|
221
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
222
|
|
|
|
|
|
|
# Determine whether a collected command should be sorted: |
|
223
|
|
|
|
|
|
|
# |
|
224
|
|
|
|
|
|
|
# Returns false if they should remain in document order |
|
225
|
|
|
|
|
|
|
# Returns true if they should be sorted |
|
226
|
|
|
|
|
|
|
# |
|
227
|
|
|
|
|
|
|
# If the return value is a reference, it is an arrayref of entry names |
|
228
|
|
|
|
|
|
|
# that should appear (in order) before any other entries. |
|
229
|
|
|
|
|
|
|
|
|
230
|
|
|
|
|
|
|
sub _find_sort_order |
|
231
|
|
|
|
|
|
|
{ |
|
232
|
65
|
|
|
65
|
|
63
|
my ($self, $type) = @_; |
|
233
|
|
|
|
|
|
|
|
|
234
|
|
|
|
|
|
|
# First, see if the document specifies the sort order: |
|
235
|
65
|
|
|
|
|
1503
|
my $blocks = $self->tmp_collected->{"Pod::Loom-sort_$type"}; |
|
236
|
|
|
|
|
|
|
|
|
237
|
65
|
50
|
|
|
|
1456
|
if ($self->tmp_collected->{"Pod::Loom-no_sort_$type"}) { |
|
238
|
0
|
0
|
|
|
|
0
|
$self->error("You used both no_sort_$type and sort_$type\n") |
|
239
|
|
|
|
|
|
|
if $blocks; |
|
240
|
|
|
|
|
|
|
|
|
241
|
0
|
|
|
|
|
0
|
return; |
|
242
|
|
|
|
|
|
|
} # end if document says no sorting |
|
243
|
|
|
|
|
|
|
|
|
244
|
65
|
50
|
|
|
|
89
|
if ($blocks) { |
|
245
|
0
|
|
|
|
|
0
|
my @sortFirst; |
|
246
|
0
|
|
|
|
|
0
|
foreach my $block (@$blocks) { |
|
247
|
0
|
|
|
|
|
0
|
push @sortFirst, split /\s*\n/, $block; |
|
248
|
|
|
|
|
|
|
} # end foreach $block |
|
249
|
|
|
|
|
|
|
|
|
250
|
0
|
|
|
|
|
0
|
return \@sortFirst; |
|
251
|
|
|
|
|
|
|
} # end if document specifies sort order |
|
252
|
|
|
|
|
|
|
|
|
253
|
|
|
|
|
|
|
# The document said nothing, so ask the template: |
|
254
|
65
|
100
|
|
|
|
236
|
my $method = $self->can("sort_$type") or return; |
|
255
|
|
|
|
|
|
|
|
|
256
|
52
|
|
|
|
|
1317
|
$self->$method; |
|
257
|
|
|
|
|
|
|
} # end _find_sort_order |
|
258
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
259
|
|
|
|
|
|
|
|
|
260
|
|
|
|
|
|
|
|
|
261
|
|
|
|
|
|
|
sub weave |
|
262
|
|
|
|
|
|
|
{ |
|
263
|
13
|
|
|
13
|
1
|
19
|
my ($self, $podRef, $filename) = @_; |
|
264
|
|
|
|
|
|
|
|
|
265
|
13
|
|
|
|
|
391
|
$self->tmp_filename($filename); |
|
266
|
|
|
|
|
|
|
|
|
267
|
13
|
|
|
|
|
24
|
$self->parse_pod($podRef); |
|
268
|
|
|
|
|
|
|
|
|
269
|
13
|
|
|
|
|
30
|
$self->post_parse; |
|
270
|
|
|
|
|
|
|
|
|
271
|
13
|
|
|
|
|
42
|
my $sectionList = $self->expect_sections; |
|
272
|
|
|
|
|
|
|
|
|
273
|
13
|
|
|
|
|
38
|
$self->generate_pod($sectionList, $self->collect_sections($sectionList)); |
|
274
|
|
|
|
|
|
|
} # end weave |
|
275
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
276
|
|
|
|
|
|
|
|
|
277
|
|
|
|
|
|
|
|
|
278
|
|
|
|
|
|
|
sub parse_pod |
|
279
|
|
|
|
|
|
|
{ |
|
280
|
13
|
|
|
13
|
1
|
19
|
my ($self, $podRef) = @_; |
|
281
|
|
|
|
|
|
|
|
|
282
|
13
|
|
|
|
|
35
|
my $pe = Pod::Loom::Parser->new( $self->collect_commands ); |
|
283
|
|
|
|
|
|
|
# We can't use read_string, because that treats the string as |
|
284
|
|
|
|
|
|
|
# encoded in UTF-8, for which some byte sequences aren't valid. |
|
285
|
|
|
|
|
|
|
# Pod::Loom::Parser will determine the actual encoding. |
|
286
|
13
|
50
|
|
|
|
173
|
open my $handle, '<:encoding(iso-8859-1)', $podRef |
|
287
|
|
|
|
|
|
|
or die "error opening string for reading: $!"; |
|
288
|
13
|
|
|
|
|
270
|
$pe->read_handle($handle); |
|
289
|
13
|
|
|
|
|
221
|
$self->tmp_collected( $pe->collected ); |
|
290
|
13
|
|
|
|
|
36
|
$self->tmp_encoding( $pe->encoding ); |
|
291
|
13
|
|
|
|
|
33
|
$self->tmp_groups( $pe->groups ); |
|
292
|
|
|
|
|
|
|
} # end parse_pod |
|
293
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
294
|
|
|
|
|
|
|
|
|
295
|
|
|
|
|
|
|
|
|
296
|
|
|
|
|
|
|
sub post_parse |
|
297
|
|
|
|
|
|
|
{ |
|
298
|
13
|
|
|
13
|
1
|
16
|
my ($self) = @_; |
|
299
|
|
|
|
|
|
|
|
|
300
|
13
|
|
|
|
|
27
|
$self->_sort_collected; |
|
301
|
|
|
|
|
|
|
} # end post_parse |
|
302
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
303
|
|
|
|
|
|
|
|
|
304
|
|
|
|
|
|
|
|
|
305
|
|
|
|
|
|
|
sub collect_sections |
|
306
|
|
|
|
|
|
|
{ |
|
307
|
13
|
|
|
13
|
1
|
15
|
my ($self, $sectionList) = @_; |
|
308
|
|
|
|
|
|
|
|
|
309
|
|
|
|
|
|
|
# Split out the expected sections: |
|
310
|
|
|
|
|
|
|
|
|
311
|
13
|
|
|
|
|
14
|
my %expectedSection = map { $_ => 1 } @$sectionList; |
|
|
144
|
|
|
|
|
221
|
|
|
312
|
|
|
|
|
|
|
|
|
313
|
13
|
|
|
|
|
362
|
my $heads = $self->tmp_collected->{head1}; |
|
314
|
13
|
|
|
|
|
12
|
my %section; |
|
315
|
|
|
|
|
|
|
|
|
316
|
13
|
|
|
|
|
23
|
foreach my $h (@$heads) { |
|
317
|
7
|
50
|
|
|
|
38
|
$h =~ /^=head1\s+(.+?)(?=\n*\z|\n\n)/ |
|
318
|
|
|
|
|
|
|
or $self->error("Can't find heading in $h"); |
|
319
|
7
|
|
|
|
|
10
|
my $title = $1; |
|
320
|
|
|
|
|
|
|
|
|
321
|
7
|
50
|
|
|
|
14
|
if ($expectedSection{$title}) { |
|
322
|
7
|
50
|
|
|
|
16
|
warn "Duplicate section $title" if $section{$title}; |
|
323
|
7
|
|
|
|
|
18
|
$section{$title} .= $h; |
|
324
|
|
|
|
|
|
|
} else { |
|
325
|
0
|
|
|
|
|
0
|
$section{'*'} .= $h; |
|
326
|
|
|
|
|
|
|
} |
|
327
|
|
|
|
|
|
|
} # end foreach $h in @$heads |
|
328
|
|
|
|
|
|
|
|
|
329
|
13
|
|
|
|
|
60
|
return \%section; |
|
330
|
|
|
|
|
|
|
} # end collect_sections |
|
331
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
332
|
|
|
|
|
|
|
|
|
333
|
|
|
|
|
|
|
|
|
334
|
|
|
|
|
|
|
sub generate_pod |
|
335
|
|
|
|
|
|
|
{ |
|
336
|
13
|
|
|
13
|
1
|
17
|
my ($self, $sectionList, $sectionText) = @_; |
|
337
|
|
|
|
|
|
|
|
|
338
|
|
|
|
|
|
|
# Now build the new POD: |
|
339
|
13
|
|
|
|
|
16
|
my $pod = ''; |
|
340
|
|
|
|
|
|
|
|
|
341
|
13
|
|
|
|
|
17
|
foreach my $title (@$sectionList) { |
|
342
|
144
|
100
|
66
|
|
|
308
|
if ($sectionText->{$title} and not $self->override_section($title)) { |
|
343
|
7
|
|
|
|
|
12
|
$pod .= $sectionText->{$title}; |
|
344
|
|
|
|
|
|
|
} # end if document supplied section and we don't override it |
|
345
|
|
|
|
|
|
|
else { |
|
346
|
137
|
|
|
|
|
201
|
my $method = $self->method_for_section($title); |
|
347
|
|
|
|
|
|
|
|
|
348
|
137
|
100
|
|
|
|
390
|
$pod .= $self->$method($title, $sectionText->{$title}) |
|
349
|
|
|
|
|
|
|
if $method; |
|
350
|
|
|
|
|
|
|
} # end else let method generate section |
|
351
|
|
|
|
|
|
|
|
|
352
|
|
|
|
|
|
|
# Make sure the document ends with a blank line: |
|
353
|
144
|
100
|
|
|
|
1532
|
$pod =~ s/\n*\z/\n\n/ if $pod; |
|
354
|
|
|
|
|
|
|
} # end foreach $title in @$sectionList |
|
355
|
|
|
|
|
|
|
|
|
356
|
13
|
|
|
|
|
324
|
my $encoding = $self->tmp_encoding; |
|
357
|
13
|
50
|
|
|
|
36
|
if (length $pod) { |
|
358
|
13
|
|
|
|
|
92
|
$pod = $encoding->encode($pod); |
|
359
|
13
|
|
|
|
|
45
|
my $name = $encoding->name; |
|
360
|
13
|
100
|
|
|
|
34
|
$pod = "=encoding " . $encoding->encode($name) . "\n\n$pod" |
|
361
|
|
|
|
|
|
|
unless $name eq 'iso-8859-1'; |
|
362
|
|
|
|
|
|
|
} |
|
363
|
|
|
|
|
|
|
|
|
364
|
13
|
|
|
|
|
46
|
$pod; |
|
365
|
|
|
|
|
|
|
} # end generate_pod |
|
366
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
367
|
|
|
|
|
|
|
|
|
368
|
|
|
|
|
|
|
|
|
369
|
|
|
|
|
|
|
sub method_for_section |
|
370
|
|
|
|
|
|
|
{ |
|
371
|
137
|
|
|
137
|
1
|
134
|
my ($self, $title) = @_; |
|
372
|
|
|
|
|
|
|
|
|
373
|
|
|
|
|
|
|
# Generate the method name: |
|
374
|
137
|
|
|
|
|
143
|
my $method = "section_$title"; |
|
375
|
137
|
100
|
|
|
|
162
|
if ($title eq '*') { $method = "other_sections" } |
|
|
13
|
|
|
|
|
13
|
|
|
376
|
|
|
|
|
|
|
else { |
|
377
|
124
|
|
|
|
|
180
|
$method =~ s/[^A-Z0-9_]/_/gi; |
|
378
|
|
|
|
|
|
|
} |
|
379
|
|
|
|
|
|
|
|
|
380
|
|
|
|
|
|
|
# See if we actually have a method by that name: |
|
381
|
137
|
|
|
|
|
329
|
$self->can($method); |
|
382
|
|
|
|
|
|
|
} # end method_for_section |
|
383
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
384
|
|
|
|
|
|
|
|
|
385
|
|
|
|
|
|
|
|
|
386
|
|
|
|
|
|
|
sub joined_section |
|
387
|
|
|
|
|
|
|
{ |
|
388
|
52
|
|
|
52
|
1
|
84
|
my ($self, $cmd, $newcmd, $title, $pod) = @_; |
|
389
|
|
|
|
|
|
|
|
|
390
|
52
|
|
|
|
|
1286
|
my $entries = $self->tmp_collected->{$cmd}; |
|
391
|
52
|
|
|
|
|
1186
|
my $groups = $self->tmp_groups->{$cmd}; |
|
392
|
|
|
|
|
|
|
|
|
393
|
52
|
50
|
50
|
|
|
447
|
return ($pod || '') unless ($entries and @$entries) |
|
|
|
|
33
|
|
|
|
|
|
|
|
|
33
|
|
|
|
|
|
|
|
|
33
|
|
|
|
|
|
394
|
|
|
|
|
|
|
or ($groups and %$groups); |
|
395
|
|
|
|
|
|
|
|
|
396
|
0
|
0
|
|
|
|
|
$pod = "=head1 $title\n" unless $pod; |
|
397
|
|
|
|
|
|
|
|
|
398
|
0
|
0
|
0
|
|
|
|
return $self->_join_groups($cmd, $newcmd, $title, $pod, $groups) |
|
399
|
|
|
|
|
|
|
if $groups and %$groups; |
|
400
|
|
|
|
|
|
|
|
|
401
|
|
|
|
|
|
|
|
|
402
|
0
|
0
|
|
|
|
|
warn("Found Pod::Loom-group_$cmd in " . $self->tmp_filename . |
|
403
|
|
|
|
|
|
|
", but no groups were used\n") |
|
404
|
|
|
|
|
|
|
if $self->tmp_collected->{"Pod::Loom-group_$cmd"}; |
|
405
|
|
|
|
|
|
|
|
|
406
|
0
|
|
|
|
|
|
return $pod . $self->join_entries($newcmd, $entries); |
|
407
|
|
|
|
|
|
|
} # end joined_section |
|
408
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
409
|
|
|
|
|
|
|
|
|
410
|
|
|
|
|
|
|
|
|
411
|
|
|
|
|
|
|
sub join_entries |
|
412
|
|
|
|
|
|
|
{ |
|
413
|
0
|
|
|
0
|
1
|
|
my ($self, $newcmd, $entries) = @_; |
|
414
|
|
|
|
|
|
|
|
|
415
|
0
|
|
|
|
|
|
my $pod = ''; |
|
416
|
|
|
|
|
|
|
|
|
417
|
0
|
0
|
|
|
|
|
$pod .= "\n=over\n" if $newcmd eq 'item'; |
|
418
|
|
|
|
|
|
|
|
|
419
|
0
|
|
|
|
|
|
foreach (@$entries) { |
|
420
|
0
|
0
|
|
|
|
|
s/^=\S+/=$newcmd/ or $self->error("Bad entry $_"); |
|
421
|
0
|
|
|
|
|
|
$pod .= "\n$_"; |
|
422
|
|
|
|
|
|
|
} # end foreach |
|
423
|
|
|
|
|
|
|
|
|
424
|
0
|
0
|
|
|
|
|
$pod .= "\n=back\n" if $newcmd eq 'item'; |
|
425
|
|
|
|
|
|
|
|
|
426
|
0
|
|
|
|
|
|
return $pod; |
|
427
|
|
|
|
|
|
|
} # end join_entries |
|
428
|
|
|
|
|
|
|
|
|
429
|
|
|
|
|
|
|
#--------------------------------------------------------------------- |
|
430
|
|
|
|
|
|
|
# Called by joined_section when it determines there are groups: |
|
431
|
|
|
|
|
|
|
|
|
432
|
|
|
|
|
|
|
sub _join_groups |
|
433
|
|
|
|
|
|
|
{ |
|
434
|
0
|
|
|
0
|
|
|
my ($self, $cmd, $newcmd, $title, $pod, $groups) = @_; |
|
435
|
|
|
|
|
|
|
|
|
436
|
0
|
|
|
|
|
|
my $groupHeaders = $self->tmp_collected->{"Pod::Loom-group_$cmd"}; |
|
437
|
|
|
|
|
|
|
|
|
438
|
|
|
|
|
|
|
|
|
439
|
0
|
0
|
|
|
|
|
die("=$cmd was grouped, but no Pod::Loom-group_$cmd found in " . |
|
440
|
|
|
|
|
|
|
$self->tmp_filename . "\n") |
|
441
|
|
|
|
|
|
|
unless $groupHeaders; |
|
442
|
|
|
|
|
|
|
|
|
443
|
|
|
|
|
|
|
# We might need to go down a level: |
|
444
|
0
|
0
|
|
|
|
|
if ($newcmd =~ /^head\d/) { |
|
445
|
0
|
|
|
|
|
|
for (;;) { |
|
446
|
0
|
|
|
|
|
|
my $re = qr/^=\Q$newcmd\E/m; |
|
447
|
0
|
0
|
|
|
|
|
last unless grep { /$re/ } @$groupHeaders; |
|
|
0
|
|
|
|
|
|
|
|
448
|
0
|
|
|
|
|
|
++$newcmd; |
|
449
|
|
|
|
|
|
|
} # end for as long as $newcmd is used in any header |
|
450
|
|
|
|
|
|
|
} # end if $newcmd is headN |
|
451
|
|
|
|
|
|
|
|
|
452
|
0
|
|
|
|
|
|
my $collected = $self->tmp_collected; |
|
453
|
|
|
|
|
|
|
|
|
454
|
0
|
0
|
|
|
|
|
$groups->{''} = 1 if @{ $collected->{$cmd} }; |
|
|
0
|
|
|
|
|
|
|
|
455
|
|
|
|
|
|
|
|
|
456
|
0
|
|
|
|
|
|
foreach my $header (@$groupHeaders) { |
|
457
|
0
|
0
|
|
|
|
|
$header =~ s/^\s*(\S+)\s*?\n// |
|
458
|
|
|
|
|
|
|
or $self->error("No category in Pod::Loom-group_$cmd\n$header"); |
|
459
|
|
|
|
|
|
|
|
|
460
|
|
|
|
|
|
|
|
|
461
|
0
|
|
|
|
|
|
my $type = $1; |
|
462
|
0
|
|
|
|
|
|
my $collectedUnder = "$cmd-$type"; |
|
463
|
|
|
|
|
|
|
|
|
464
|
0
|
0
|
|
|
|
|
if ($type eq '*') { |
|
465
|
0
|
|
|
|
|
|
$type = ''; |
|
466
|
0
|
|
|
|
|
|
$collectedUnder = $cmd; |
|
467
|
|
|
|
|
|
|
} |
|
468
|
|
|
|
|
|
|
|
|
469
|
0
|
0
|
|
|
|
|
unless (delete $groups->{$type}) { |
|
470
|
0
|
|
|
|
|
|
$self->warning("No entries for =$cmd-$type"); |
|
471
|
0
|
|
|
|
|
|
next; |
|
472
|
|
|
|
|
|
|
} |
|
473
|
|
|
|
|
|
|
|
|
474
|
0
|
|
|
|
|
|
$pod =~ s/\n*\z/\n\n/; # Make sure it ends with a blank line |
|
475
|
0
|
|
|
|
|
|
$pod .= ($header . |
|
476
|
|
|
|
|
|
|
$self->join_entries($newcmd, $collected->{$collectedUnder})); |
|
477
|
|
|
|
|
|
|
} # end foreach $header in @$groupHeaders |
|
478
|
|
|
|
|
|
|
|
|
479
|
0
|
0
|
|
|
|
|
if (%$groups) { |
|
480
|
0
|
0
|
|
|
|
|
$self->warning("You used =$cmd, but had no Pod::Loom-group_$cmd * section\n") |
|
481
|
|
|
|
|
|
|
if delete $groups->{''}; |
|
482
|
|
|
|
|
|
|
|
|
483
|
|
|
|
|
|
|
|
|
484
|
|
|
|
|
|
|
$self->warning("You used =$cmd-$_, but had no Pod::Loom-group_$cmd $_ section\n") |
|
485
|
0
|
|
|
|
|
|
for sort keys %$groups; |
|
486
|
|
|
|
|
|
|
|
|
487
|
0
|
|
|
|
|
|
die "Terminating because of errors\n"; |
|
488
|
|
|
|
|
|
|
} # end if used groups that had no header |
|
489
|
|
|
|
|
|
|
|
|
490
|
0
|
|
|
|
|
|
$pod; |
|
491
|
|
|
|
|
|
|
} # end _join_groups |
|
492
|
|
|
|
|
|
|
|
|
493
|
|
|
|
|
|
|
#===================================================================== |
|
494
|
|
|
|
|
|
|
# Package Return Value: |
|
495
|
|
|
|
|
|
|
|
|
496
|
1
|
|
|
1
|
|
5
|
no Moose; |
|
|
1
|
|
|
|
|
2
|
|
|
|
1
|
|
|
|
|
5
|
|
|
497
|
|
|
|
|
|
|
__PACKAGE__->meta->make_immutable; |
|
498
|
|
|
|
|
|
|
1; |
|
499
|
|
|
|
|
|
|
|
|
500
|
|
|
|
|
|
|
__END__ |
|
501
|
|
|
|
|
|
|
|
|
502
|
|
|
|
|
|
|
=head1 NAME |
|
503
|
|
|
|
|
|
|
|
|
504
|
|
|
|
|
|
|
Pod::Loom::Template - Standard base class for Pod::Loom templates |
|
505
|
|
|
|
|
|
|
|
|
506
|
|
|
|
|
|
|
=head1 VERSION |
|
507
|
|
|
|
|
|
|
|
|
508
|
|
|
|
|
|
|
This document describes version 0.07 of |
|
509
|
|
|
|
|
|
|
Pod::Loom::Template, released March 23, 2014 |
|
510
|
|
|
|
|
|
|
as part of Pod-Loom version 0.08. |
|
511
|
|
|
|
|
|
|
|
|
512
|
|
|
|
|
|
|
=head1 DESCRIPTION |
|
513
|
|
|
|
|
|
|
|
|
514
|
|
|
|
|
|
|
Pod::Loom::Template is intended as the standard base class for |
|
515
|
|
|
|
|
|
|
Pod::Loom templates. It provides the engine that splits apart the POD |
|
516
|
|
|
|
|
|
|
and reassembles it. The subclass needs to specify how the POD is |
|
517
|
|
|
|
|
|
|
reassembled. See the L</"weave"> method for details. |
|
518
|
|
|
|
|
|
|
|
|
519
|
|
|
|
|
|
|
=head2 Controlling the template |
|
520
|
|
|
|
|
|
|
|
|
521
|
|
|
|
|
|
|
A POD document can contain special commands for the template. These |
|
522
|
|
|
|
|
|
|
commands should work with all templates based on Pod::Loom::Template. |
|
523
|
|
|
|
|
|
|
They are placed in a C<=for> command, and must not come in the middle |
|
524
|
|
|
|
|
|
|
of a section. |
|
525
|
|
|
|
|
|
|
|
|
526
|
|
|
|
|
|
|
=over |
|
527
|
|
|
|
|
|
|
|
|
528
|
|
|
|
|
|
|
=item Pod::Loom-insert_after |
|
529
|
|
|
|
|
|
|
|
|
530
|
|
|
|
|
|
|
=item Pod::Loom-insert_before |
|
531
|
|
|
|
|
|
|
|
|
532
|
|
|
|
|
|
|
Insert (or move) one or more sections into the specified position. |
|
533
|
|
|
|
|
|
|
See L</"expect_sections">. |
|
534
|
|
|
|
|
|
|
|
|
535
|
|
|
|
|
|
|
=item Pod::Loom-omit |
|
536
|
|
|
|
|
|
|
|
|
537
|
|
|
|
|
|
|
Omit the specified sections from the document. |
|
538
|
|
|
|
|
|
|
See L</"expect_sections">. |
|
539
|
|
|
|
|
|
|
|
|
540
|
|
|
|
|
|
|
=item Pod::Loom-sections |
|
541
|
|
|
|
|
|
|
|
|
542
|
|
|
|
|
|
|
Specify the complete list of sections for the document. |
|
543
|
|
|
|
|
|
|
See L</"expect_sections">. |
|
544
|
|
|
|
|
|
|
|
|
545
|
|
|
|
|
|
|
=item Pod::Loom-sort_COMMAND |
|
546
|
|
|
|
|
|
|
|
|
547
|
|
|
|
|
|
|
If a template allows pseudo-POD commands like C<=method>, you can have |
|
548
|
|
|
|
|
|
|
the resulting entries sorted alphabetically. For example, to have |
|
549
|
|
|
|
|
|
|
your methods sorted, use |
|
550
|
|
|
|
|
|
|
|
|
551
|
|
|
|
|
|
|
=for Pod::Loom-sort_method |
|
552
|
|
|
|
|
|
|
|
|
553
|
|
|
|
|
|
|
You can also supply a list of entries (one per line) that should come |
|
554
|
|
|
|
|
|
|
first. The list must match the corresponding entry exactly. For |
|
555
|
|
|
|
|
|
|
example: |
|
556
|
|
|
|
|
|
|
|
|
557
|
|
|
|
|
|
|
=for Pod::Loom-sort_method |
|
558
|
|
|
|
|
|
|
new |
|
559
|
|
|
|
|
|
|
|
|
560
|
|
|
|
|
|
|
=method new |
|
561
|
|
|
|
|
|
|
|
|
562
|
|
|
|
|
|
|
or |
|
563
|
|
|
|
|
|
|
|
|
564
|
|
|
|
|
|
|
=for Pod::Loom-sort_method |
|
565
|
|
|
|
|
|
|
C<< $object = Class->new() >> |
|
566
|
|
|
|
|
|
|
|
|
567
|
|
|
|
|
|
|
=method C<< $object = Class->new() >> |
|
568
|
|
|
|
|
|
|
|
|
569
|
|
|
|
|
|
|
=item Pod::Loom-group_COMMAND |
|
570
|
|
|
|
|
|
|
|
|
571
|
|
|
|
|
|
|
If you have a lot of attributes or methods, you might want to group |
|
572
|
|
|
|
|
|
|
them into categories. You do this by appending the category (which is |
|
573
|
|
|
|
|
|
|
an arbitrary string without whitespace) to the command. For example: |
|
574
|
|
|
|
|
|
|
|
|
575
|
|
|
|
|
|
|
=attr-fmt font |
|
576
|
|
|
|
|
|
|
|
|
577
|
|
|
|
|
|
|
says that the font attribute is in the C<fmt> category. You must have |
|
578
|
|
|
|
|
|
|
a C<Pod::Loom-group_COMMAND> block for each category you use. The |
|
579
|
|
|
|
|
|
|
block begins with the category name on a line by itself. The rest of |
|
580
|
|
|
|
|
|
|
the block (which may be blank) is POD that will appear before the |
|
581
|
|
|
|
|
|
|
associated entries. |
|
582
|
|
|
|
|
|
|
|
|
583
|
|
|
|
|
|
|
=begin Pod::Loom-group_attr fmt |
|
584
|
|
|
|
|
|
|
|
|
585
|
|
|
|
|
|
|
=head2 Formatting Attributes |
|
586
|
|
|
|
|
|
|
|
|
587
|
|
|
|
|
|
|
These attributes control formatting. |
|
588
|
|
|
|
|
|
|
|
|
589
|
|
|
|
|
|
|
Note: Because Pod::Eventual is not a full-fledged POD parser, you do |
|
590
|
|
|
|
|
|
|
not actually need a matching C<=end> after the C<=begin>, but it won't |
|
591
|
|
|
|
|
|
|
hurt if you use one. If you don't, the block ends at the next POD |
|
592
|
|
|
|
|
|
|
command in L</"collect_commands">. |
|
593
|
|
|
|
|
|
|
|
|
594
|
|
|
|
|
|
|
Entries that do not contain a category are placed in the special |
|
595
|
|
|
|
|
|
|
category C<*>. |
|
596
|
|
|
|
|
|
|
|
|
597
|
|
|
|
|
|
|
The categories will be listed in the order that the |
|
598
|
|
|
|
|
|
|
Pod::Loom-group_COMMAND blocks appear in the document. The order of |
|
599
|
|
|
|
|
|
|
entries within each category is controlled as usual. See |
|
600
|
|
|
|
|
|
|
L</"Pod::Loom-sort_COMMAND">. (Just ignore the category when defining |
|
601
|
|
|
|
|
|
|
the sort order.) |
|
602
|
|
|
|
|
|
|
|
|
603
|
|
|
|
|
|
|
=item Pod::Loom-template |
|
604
|
|
|
|
|
|
|
|
|
605
|
|
|
|
|
|
|
Specify the template for the document. (This is actually handled by |
|
606
|
|
|
|
|
|
|
L<Pod::Loom>, and applies to all templates, whether or not they |
|
607
|
|
|
|
|
|
|
subclass Pod::Loom::Template.) |
|
608
|
|
|
|
|
|
|
|
|
609
|
|
|
|
|
|
|
=back |
|
610
|
|
|
|
|
|
|
|
|
611
|
|
|
|
|
|
|
=head1 ATTRIBUTES |
|
612
|
|
|
|
|
|
|
|
|
613
|
|
|
|
|
|
|
All attributes beginning with C<tmp_> are reserved and must not be |
|
614
|
|
|
|
|
|
|
defined by subclasses. In addition, attributes beginning with |
|
615
|
|
|
|
|
|
|
C<sort_> are reserved for indicating whether collected entries should |
|
616
|
|
|
|
|
|
|
be sorted. |
|
617
|
|
|
|
|
|
|
|
|
618
|
|
|
|
|
|
|
|
|
619
|
|
|
|
|
|
|
=head2 sections |
|
620
|
|
|
|
|
|
|
|
|
621
|
|
|
|
|
|
|
Subclasses must provide a builder for this attribute named |
|
622
|
|
|
|
|
|
|
C<_build_sections>. It is an |
|
623
|
|
|
|
|
|
|
arrayref of section titles in the order they should appear. The |
|
624
|
|
|
|
|
|
|
special title C<*> indicates where sections that appear in the |
|
625
|
|
|
|
|
|
|
document but are not in this list will be placed. (If C<*> is not in |
|
626
|
|
|
|
|
|
|
this list, such sections will be dropped.) |
|
627
|
|
|
|
|
|
|
|
|
628
|
|
|
|
|
|
|
The list can include sections that the template does not provide. In |
|
629
|
|
|
|
|
|
|
that case, it simply indicates where the section should be placed if |
|
630
|
|
|
|
|
|
|
the document provides it. |
|
631
|
|
|
|
|
|
|
|
|
632
|
|
|
|
|
|
|
|
|
633
|
|
|
|
|
|
|
=head2 tmp_collected |
|
634
|
|
|
|
|
|
|
|
|
635
|
|
|
|
|
|
|
This is a hashref of arrayrefs. The keys are the POD commands |
|
636
|
|
|
|
|
|
|
returned by L</"collect_commands">, plus any format names that begin |
|
637
|
|
|
|
|
|
|
with C<Pod::Loom>. Each value is an arrayref of POD blocks. |
|
638
|
|
|
|
|
|
|
It is filled in by the L</"parse_pod"> method. |
|
639
|
|
|
|
|
|
|
|
|
640
|
|
|
|
|
|
|
|
|
641
|
|
|
|
|
|
|
=head2 tmp_filename |
|
642
|
|
|
|
|
|
|
|
|
643
|
|
|
|
|
|
|
This is the name of the file being processed. This is only for |
|
644
|
|
|
|
|
|
|
informational purposes; it need not represent an actual file on disk. |
|
645
|
|
|
|
|
|
|
(The L</"weave"> method stores the filename here.) |
|
646
|
|
|
|
|
|
|
|
|
647
|
|
|
|
|
|
|
|
|
648
|
|
|
|
|
|
|
=head2 tmp_groups |
|
649
|
|
|
|
|
|
|
|
|
650
|
|
|
|
|
|
|
This is a hashref of hashrefs. The keys are the POD commands returned |
|
651
|
|
|
|
|
|
|
by L</"collect_commands">, Each value is an hashref of group codes. |
|
652
|
|
|
|
|
|
|
It is filled in by the L</"parse_pod"> method. |
|
653
|
|
|
|
|
|
|
|
|
654
|
|
|
|
|
|
|
=head1 METHODS |
|
655
|
|
|
|
|
|
|
|
|
656
|
|
|
|
|
|
|
=head2 collect_commands |
|
657
|
|
|
|
|
|
|
|
|
658
|
|
|
|
|
|
|
$arrayRef = $tmp->collect_commands; |
|
659
|
|
|
|
|
|
|
|
|
660
|
|
|
|
|
|
|
This method should be overriden in subclasses to indicate what POD |
|
661
|
|
|
|
|
|
|
commands should be collected for the template to stitch together. |
|
662
|
|
|
|
|
|
|
This should include C<head1>, or the template is unlikely to work |
|
663
|
|
|
|
|
|
|
properly. The default method indicates only C<head1> is collected. |
|
664
|
|
|
|
|
|
|
|
|
665
|
|
|
|
|
|
|
|
|
666
|
|
|
|
|
|
|
=head2 collect_sections |
|
667
|
|
|
|
|
|
|
|
|
668
|
|
|
|
|
|
|
$section_text = $tmp->collect_sections($section_list) |
|
669
|
|
|
|
|
|
|
|
|
670
|
|
|
|
|
|
|
This method collects the text of each section in the original document |
|
671
|
|
|
|
|
|
|
based on the $section_list (which comes from L</"expect_sections">). |
|
672
|
|
|
|
|
|
|
It returns a hashref keyed on section title. |
|
673
|
|
|
|
|
|
|
|
|
674
|
|
|
|
|
|
|
Any sections that appeared in the original document but are not in |
|
675
|
|
|
|
|
|
|
C<$section_list> are concatenated to form the C<*> section. |
|
676
|
|
|
|
|
|
|
|
|
677
|
|
|
|
|
|
|
|
|
678
|
|
|
|
|
|
|
=head2 error |
|
679
|
|
|
|
|
|
|
|
|
680
|
|
|
|
|
|
|
$tmp->error($message); |
|
681
|
|
|
|
|
|
|
|
|
682
|
|
|
|
|
|
|
This method calls Perl's C<die> builtin with the C<$message> after |
|
683
|
|
|
|
|
|
|
prepending the filename to it. |
|
684
|
|
|
|
|
|
|
|
|
685
|
|
|
|
|
|
|
|
|
686
|
|
|
|
|
|
|
=head2 expect_sections |
|
687
|
|
|
|
|
|
|
|
|
688
|
|
|
|
|
|
|
$section_titles = $tmp->expect_sections; |
|
689
|
|
|
|
|
|
|
|
|
690
|
|
|
|
|
|
|
This method returns an arrayref containing the section titles in the |
|
691
|
|
|
|
|
|
|
order they should appear. By default, this is the list from |
|
692
|
|
|
|
|
|
|
L</"sections">, but it can be overriden by the document: |
|
693
|
|
|
|
|
|
|
|
|
694
|
|
|
|
|
|
|
If the document contains C<=for Pod::Loom-sections>, the sections |
|
695
|
|
|
|
|
|
|
listed there (one per line) replace the template's normal section |
|
696
|
|
|
|
|
|
|
list. |
|
697
|
|
|
|
|
|
|
|
|
698
|
|
|
|
|
|
|
If the document contains C<=for Pod::Loom-omit>, the sections listed |
|
699
|
|
|
|
|
|
|
there will not appear in the final document. (Unless they appeared in |
|
700
|
|
|
|
|
|
|
the document, in which case they will be with the other C<*> |
|
701
|
|
|
|
|
|
|
sections.) |
|
702
|
|
|
|
|
|
|
|
|
703
|
|
|
|
|
|
|
If the document contains C<=for Pod::Loom-insert_before>, the sections |
|
704
|
|
|
|
|
|
|
listed there will be inserted before the last section in the list |
|
705
|
|
|
|
|
|
|
(which must already be in the section list). If the sections were |
|
706
|
|
|
|
|
|
|
already in the section list, they are moved to the new location. |
|
707
|
|
|
|
|
|
|
|
|
708
|
|
|
|
|
|
|
If the document contains C<=for Pod::Loom-insert_after>, the sections |
|
709
|
|
|
|
|
|
|
listed there will be inserted after the first section in the list. |
|
710
|
|
|
|
|
|
|
For example, |
|
711
|
|
|
|
|
|
|
|
|
712
|
|
|
|
|
|
|
=for Pod::Loom-insert_after |
|
713
|
|
|
|
|
|
|
DESCRIPTION |
|
714
|
|
|
|
|
|
|
NOTES |
|
715
|
|
|
|
|
|
|
|
|
716
|
|
|
|
|
|
|
will cause the NOTES section to appear immediately after the DESCRIPTION. |
|
717
|
|
|
|
|
|
|
|
|
718
|
|
|
|
|
|
|
|
|
719
|
|
|
|
|
|
|
=head2 generate_pod |
|
720
|
|
|
|
|
|
|
|
|
721
|
|
|
|
|
|
|
$pod = $tmp->generate_pod($section_list, $section_text) |
|
722
|
|
|
|
|
|
|
|
|
723
|
|
|
|
|
|
|
This method is passed a list of section titles (from |
|
724
|
|
|
|
|
|
|
L</"expect_sections">) and a hash containing the original text of each |
|
725
|
|
|
|
|
|
|
section (from L</"collect_sections">. It then considers each section |
|
726
|
|
|
|
|
|
|
in order: |
|
727
|
|
|
|
|
|
|
|
|
728
|
|
|
|
|
|
|
=over |
|
729
|
|
|
|
|
|
|
|
|
730
|
|
|
|
|
|
|
=item 1. |
|
731
|
|
|
|
|
|
|
|
|
732
|
|
|
|
|
|
|
If the section appeared in the original document, it calls |
|
733
|
|
|
|
|
|
|
C<< $tmp->override_section($title) >>. If that returns false, |
|
734
|
|
|
|
|
|
|
it copies the section from the original document to the new document |
|
735
|
|
|
|
|
|
|
and proceeds to the next section. Otherwise, it continues to step 2. |
|
736
|
|
|
|
|
|
|
|
|
737
|
|
|
|
|
|
|
=item 2. |
|
738
|
|
|
|
|
|
|
|
|
739
|
|
|
|
|
|
|
It calls C<< $tmp->method_for_section($title) >> to get the method |
|
740
|
|
|
|
|
|
|
that will handle that section. If that returns no method, it proceeds |
|
741
|
|
|
|
|
|
|
to the next section. |
|
742
|
|
|
|
|
|
|
|
|
743
|
|
|
|
|
|
|
=item 3. |
|
744
|
|
|
|
|
|
|
|
|
745
|
|
|
|
|
|
|
It calls the method from step 2, passing it two parameters: the |
|
746
|
|
|
|
|
|
|
section title and the text of the section from the original document |
|
747
|
|
|
|
|
|
|
(or undef). Whatever text the method returns is appended to the new |
|
748
|
|
|
|
|
|
|
document. (The method may return the empty string, but should not |
|
749
|
|
|
|
|
|
|
return undef). |
|
750
|
|
|
|
|
|
|
|
|
751
|
|
|
|
|
|
|
=back |
|
752
|
|
|
|
|
|
|
|
|
753
|
|
|
|
|
|
|
|
|
754
|
|
|
|
|
|
|
=head2 join_entries |
|
755
|
|
|
|
|
|
|
|
|
756
|
|
|
|
|
|
|
$podText = $tmp->join_entries($newcmd, \@entries); |
|
757
|
|
|
|
|
|
|
|
|
758
|
|
|
|
|
|
|
This method is used by L</"joined_section">, but may be useful to |
|
759
|
|
|
|
|
|
|
subclasses also. Each element of C<@entries> must begin with a POD |
|
760
|
|
|
|
|
|
|
command, which will be changed to C<$newcmd>. It returns the entries |
|
761
|
|
|
|
|
|
|
joined together, surrounded by C<=over> and C<=back> if C<$newcmd> is |
|
762
|
|
|
|
|
|
|
C<item>. |
|
763
|
|
|
|
|
|
|
|
|
764
|
|
|
|
|
|
|
|
|
765
|
|
|
|
|
|
|
=head2 joined_section |
|
766
|
|
|
|
|
|
|
|
|
767
|
|
|
|
|
|
|
$podText = $tmp->joined_section($oldcmd, $newcmd, $title, $pod); |
|
768
|
|
|
|
|
|
|
|
|
769
|
|
|
|
|
|
|
This method may be useful to subclasses that want to build sections |
|
770
|
|
|
|
|
|
|
out of collected commands. C<$oldcmd> must be one of the entries from |
|
771
|
|
|
|
|
|
|
L</"collect_commands">. C<$newcmd> is the POD command that should be |
|
772
|
|
|
|
|
|
|
used for each entry (like C<head2> or C<item>). C<$title> is the |
|
773
|
|
|
|
|
|
|
section title, and C<$pod> is the text of that section from the |
|
774
|
|
|
|
|
|
|
original document (if any). |
|
775
|
|
|
|
|
|
|
|
|
776
|
|
|
|
|
|
|
Each collected entry is appended to the original section. If there |
|
777
|
|
|
|
|
|
|
was no original section, a simple C<=head1 $title> command is added. |
|
778
|
|
|
|
|
|
|
If C<$newcmd> is C<item>, then C<=over> and C<=back> are added |
|
779
|
|
|
|
|
|
|
automatically. |
|
780
|
|
|
|
|
|
|
|
|
781
|
|
|
|
|
|
|
If the document divided this section into groups (see |
|
782
|
|
|
|
|
|
|
L</"Pod::Loom-group_COMMAND">), that is handled automatically by this |
|
783
|
|
|
|
|
|
|
method. If C<$newcmd> is a C<headN>, and any of the category headers |
|
784
|
|
|
|
|
|
|
contains a C<=headN> command, then C<$newcmd> is automatically |
|
785
|
|
|
|
|
|
|
incremented. (E.g., C<head2> becomes C<head3>). |
|
786
|
|
|
|
|
|
|
|
|
787
|
|
|
|
|
|
|
|
|
788
|
|
|
|
|
|
|
=head2 method_for_section |
|
789
|
|
|
|
|
|
|
|
|
790
|
|
|
|
|
|
|
$methodRef = $tmp->method_for_section($section_title); |
|
791
|
|
|
|
|
|
|
|
|
792
|
|
|
|
|
|
|
This associates a section title with the template method that |
|
793
|
|
|
|
|
|
|
implements it. By default, it prepends C<section_> to the title, and |
|
794
|
|
|
|
|
|
|
then converts any non-alphanumeric characters to underscores. |
|
795
|
|
|
|
|
|
|
|
|
796
|
|
|
|
|
|
|
The special C<*> section is associated with the method C<other_sections>. |
|
797
|
|
|
|
|
|
|
|
|
798
|
|
|
|
|
|
|
|
|
799
|
|
|
|
|
|
|
=head2 override_section |
|
800
|
|
|
|
|
|
|
|
|
801
|
|
|
|
|
|
|
$boolean = $tmp->override_section($section_title); |
|
802
|
|
|
|
|
|
|
|
|
803
|
|
|
|
|
|
|
Normally, if a section appears in the document, it remains unchanged |
|
804
|
|
|
|
|
|
|
by the template. However, a template may want to rewrite certain |
|
805
|
|
|
|
|
|
|
sections. C<override_section> is called when the specified section is |
|
806
|
|
|
|
|
|
|
present in the document. If it returns true, then the normal |
|
807
|
|
|
|
|
|
|
C<section_TITLE> method will be called. (If it returns true but the |
|
808
|
|
|
|
|
|
|
C<section_TITLE> method doesn't exist, the section will be dropped.) |
|
809
|
|
|
|
|
|
|
|
|
810
|
|
|
|
|
|
|
|
|
811
|
|
|
|
|
|
|
=head2 parse_pod |
|
812
|
|
|
|
|
|
|
|
|
813
|
|
|
|
|
|
|
$tmp->parse_pod(\$pod); |
|
814
|
|
|
|
|
|
|
|
|
815
|
|
|
|
|
|
|
Parse the document, which is passed by reference. The default |
|
816
|
|
|
|
|
|
|
implementation splits up the POD using L<Pod::Loom::Parser>, breaking |
|
817
|
|
|
|
|
|
|
it up according to L</"collect_commands">. The resulting chunks are |
|
818
|
|
|
|
|
|
|
stored in the C<tmp_collected> attribute. |
|
819
|
|
|
|
|
|
|
|
|
820
|
|
|
|
|
|
|
|
|
821
|
|
|
|
|
|
|
=head2 post_parse |
|
822
|
|
|
|
|
|
|
|
|
823
|
|
|
|
|
|
|
$tmp->post_parse() |
|
824
|
|
|
|
|
|
|
|
|
825
|
|
|
|
|
|
|
This method is called after C<parse_pod>. The default implementation |
|
826
|
|
|
|
|
|
|
sorts the collected POD chunks if requested to by the document or the |
|
827
|
|
|
|
|
|
|
C<sort_> attributes. |
|
828
|
|
|
|
|
|
|
|
|
829
|
|
|
|
|
|
|
|
|
830
|
|
|
|
|
|
|
=head2 required_attr |
|
831
|
|
|
|
|
|
|
|
|
832
|
|
|
|
|
|
|
@values = $tmp->required_attr($section_title, @attribute_names); |
|
833
|
|
|
|
|
|
|
|
|
834
|
|
|
|
|
|
|
Returns the value of each attribute specified in C<@attribute_names>. |
|
835
|
|
|
|
|
|
|
If any attribute is C<undef>, dies with a message that |
|
836
|
|
|
|
|
|
|
C<$section_title> requires that attribute. |
|
837
|
|
|
|
|
|
|
|
|
838
|
|
|
|
|
|
|
|
|
839
|
|
|
|
|
|
|
=head2 warning |
|
840
|
|
|
|
|
|
|
|
|
841
|
|
|
|
|
|
|
$tmp->warning($message); |
|
842
|
|
|
|
|
|
|
|
|
843
|
|
|
|
|
|
|
This method calls Perl's C<warn> builtin with the C<$message>. If |
|
844
|
|
|
|
|
|
|
this is the first warning, it first prints a warning with the filename. |
|
845
|
|
|
|
|
|
|
|
|
846
|
|
|
|
|
|
|
|
|
847
|
|
|
|
|
|
|
=head2 weave |
|
848
|
|
|
|
|
|
|
|
|
849
|
|
|
|
|
|
|
$new_pod = $tmp->weave(\$old_pod, $filename); |
|
850
|
|
|
|
|
|
|
|
|
851
|
|
|
|
|
|
|
This is the primary entry point, normally called by Pod::Loom's |
|
852
|
|
|
|
|
|
|
C<weave> method. |
|
853
|
|
|
|
|
|
|
|
|
854
|
|
|
|
|
|
|
First, it stores the filename in the C<tmp_filename> attribute. |
|
855
|
|
|
|
|
|
|
|
|
856
|
|
|
|
|
|
|
It then calls: |
|
857
|
|
|
|
|
|
|
|
|
858
|
|
|
|
|
|
|
=over |
|
859
|
|
|
|
|
|
|
|
|
860
|
|
|
|
|
|
|
=item 1. |
|
861
|
|
|
|
|
|
|
|
|
862
|
|
|
|
|
|
|
L</"parse_pod"> to parse the POD. |
|
863
|
|
|
|
|
|
|
|
|
864
|
|
|
|
|
|
|
=item 2. |
|
865
|
|
|
|
|
|
|
|
|
866
|
|
|
|
|
|
|
L</"post_parse"> to do additional processing. |
|
867
|
|
|
|
|
|
|
|
|
868
|
|
|
|
|
|
|
=item 3. |
|
869
|
|
|
|
|
|
|
|
|
870
|
|
|
|
|
|
|
L</"expect_sections"> to get the list of section titles. |
|
871
|
|
|
|
|
|
|
|
|
872
|
|
|
|
|
|
|
=item 4. |
|
873
|
|
|
|
|
|
|
|
|
874
|
|
|
|
|
|
|
L</"collect_sections"> to get the text of each section from |
|
875
|
|
|
|
|
|
|
the original document. |
|
876
|
|
|
|
|
|
|
|
|
877
|
|
|
|
|
|
|
=item 5. |
|
878
|
|
|
|
|
|
|
|
|
879
|
|
|
|
|
|
|
L</"generate_pod"> to produce the new document. |
|
880
|
|
|
|
|
|
|
|
|
881
|
|
|
|
|
|
|
=back |
|
882
|
|
|
|
|
|
|
|
|
883
|
|
|
|
|
|
|
=head1 DIAGNOSTICS |
|
884
|
|
|
|
|
|
|
|
|
885
|
|
|
|
|
|
|
The following errors are classified like Perl's built-in diagnostics |
|
886
|
|
|
|
|
|
|
(L<perldiag>): |
|
887
|
|
|
|
|
|
|
|
|
888
|
|
|
|
|
|
|
(S) A severe warning |
|
889
|
|
|
|
|
|
|
(F) A fatal error (trappable) |
|
890
|
|
|
|
|
|
|
|
|
891
|
|
|
|
|
|
|
=over |
|
892
|
|
|
|
|
|
|
|
|
893
|
|
|
|
|
|
|
=item C<< %s was grouped, but no Pod::Loom-group_%s found in %s >> |
|
894
|
|
|
|
|
|
|
|
|
895
|
|
|
|
|
|
|
(F) You used categories with a command (like C<=method-cat>), but didn't |
|
896
|
|
|
|
|
|
|
have any Pod::Loom-group_COMMAND blocks. See L</"Pod::Loom-group_COMMAND">. |
|
897
|
|
|
|
|
|
|
|
|
898
|
|
|
|
|
|
|
|
|
899
|
|
|
|
|
|
|
=item C<< Can't find heading in %s >> |
|
900
|
|
|
|
|
|
|
|
|
901
|
|
|
|
|
|
|
(F) Pod::Loom couldn't determine the section title for the specified |
|
902
|
|
|
|
|
|
|
section. Is it formatted properly? |
|
903
|
|
|
|
|
|
|
|
|
904
|
|
|
|
|
|
|
|
|
905
|
|
|
|
|
|
|
=item C<< Can't insert before/after nonexistent section %s >> |
|
906
|
|
|
|
|
|
|
|
|
907
|
|
|
|
|
|
|
(F) You can't insert sections near a section title that isn't already in |
|
908
|
|
|
|
|
|
|
the list of sections. Make sure you spelled it right. |
|
909
|
|
|
|
|
|
|
|
|
910
|
|
|
|
|
|
|
|
|
911
|
|
|
|
|
|
|
=item C<< Found Pod::Loom-group_%s in %s, but no groups were used >> |
|
912
|
|
|
|
|
|
|
|
|
913
|
|
|
|
|
|
|
(S) You indicated that a command (like C<=method>) was going to be |
|
914
|
|
|
|
|
|
|
grouped, but didn't actually use any groups. |
|
915
|
|
|
|
|
|
|
See L</"Pod::Loom-group_COMMAND">. |
|
916
|
|
|
|
|
|
|
|
|
917
|
|
|
|
|
|
|
|
|
918
|
|
|
|
|
|
|
=item C<< No category in Pod::Loom-group_%s >> |
|
919
|
|
|
|
|
|
|
|
|
920
|
|
|
|
|
|
|
(F) A Pod::Loom-group_COMMAND block must begin with the category. |
|
921
|
|
|
|
|
|
|
|
|
922
|
|
|
|
|
|
|
|
|
923
|
|
|
|
|
|
|
=item C<< The %s section requires you to set `%s' >> |
|
924
|
|
|
|
|
|
|
|
|
925
|
|
|
|
|
|
|
(F) The specified section of the template requires an attribute that |
|
926
|
|
|
|
|
|
|
you did not set. |
|
927
|
|
|
|
|
|
|
|
|
928
|
|
|
|
|
|
|
|
|
929
|
|
|
|
|
|
|
=item C<< You used =%s, but had no Pod::Loom-group_$cmd %s section >> |
|
930
|
|
|
|
|
|
|
|
|
931
|
|
|
|
|
|
|
(F) You must have one Pod::Loom-group_COMMAND block for each category |
|
932
|
|
|
|
|
|
|
you use. Entries without a category are placed in the C<*> category. |
|
933
|
|
|
|
|
|
|
|
|
934
|
|
|
|
|
|
|
|
|
935
|
|
|
|
|
|
|
=back |
|
936
|
|
|
|
|
|
|
|
|
937
|
|
|
|
|
|
|
=head1 CONFIGURATION AND ENVIRONMENT |
|
938
|
|
|
|
|
|
|
|
|
939
|
|
|
|
|
|
|
Pod::Loom::Template requires no configuration files or environment variables. |
|
940
|
|
|
|
|
|
|
|
|
941
|
|
|
|
|
|
|
=head1 INCOMPATIBILITIES |
|
942
|
|
|
|
|
|
|
|
|
943
|
|
|
|
|
|
|
None reported. |
|
944
|
|
|
|
|
|
|
|
|
945
|
|
|
|
|
|
|
=head1 BUGS AND LIMITATIONS |
|
946
|
|
|
|
|
|
|
|
|
947
|
|
|
|
|
|
|
No bugs have been reported. |
|
948
|
|
|
|
|
|
|
|
|
949
|
|
|
|
|
|
|
=head1 AUTHOR |
|
950
|
|
|
|
|
|
|
|
|
951
|
|
|
|
|
|
|
Christopher J. Madsen S<C<< <perl AT cjmweb.net> >>> |
|
952
|
|
|
|
|
|
|
|
|
953
|
|
|
|
|
|
|
Please report any bugs or feature requests |
|
954
|
|
|
|
|
|
|
to S<C<< <bug-Pod-Loom AT rt.cpan.org> >>> |
|
955
|
|
|
|
|
|
|
or through the web interface at |
|
956
|
|
|
|
|
|
|
L<< http://rt.cpan.org/Public/Bug/Report.html?Queue=Pod-Loom >>. |
|
957
|
|
|
|
|
|
|
|
|
958
|
|
|
|
|
|
|
You can follow or contribute to Pod-Loom's development at |
|
959
|
|
|
|
|
|
|
L<< https://github.com/madsen/pod-loom >>. |
|
960
|
|
|
|
|
|
|
|
|
961
|
|
|
|
|
|
|
=head1 COPYRIGHT AND LICENSE |
|
962
|
|
|
|
|
|
|
|
|
963
|
|
|
|
|
|
|
This software is copyright (c) 2014 by Christopher J. Madsen. |
|
964
|
|
|
|
|
|
|
|
|
965
|
|
|
|
|
|
|
This is free software; you can redistribute it and/or modify it under |
|
966
|
|
|
|
|
|
|
the same terms as the Perl 5 programming language system itself. |
|
967
|
|
|
|
|
|
|
|
|
968
|
|
|
|
|
|
|
=head1 DISCLAIMER OF WARRANTY |
|
969
|
|
|
|
|
|
|
|
|
970
|
|
|
|
|
|
|
BECAUSE THIS SOFTWARE IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY |
|
971
|
|
|
|
|
|
|
FOR THE SOFTWARE, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN |
|
972
|
|
|
|
|
|
|
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES |
|
973
|
|
|
|
|
|
|
PROVIDE THE SOFTWARE "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER |
|
974
|
|
|
|
|
|
|
EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
|
975
|
|
|
|
|
|
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE |
|
976
|
|
|
|
|
|
|
ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE SOFTWARE IS WITH |
|
977
|
|
|
|
|
|
|
YOU. SHOULD THE SOFTWARE PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL |
|
978
|
|
|
|
|
|
|
NECESSARY SERVICING, REPAIR, OR CORRECTION. |
|
979
|
|
|
|
|
|
|
|
|
980
|
|
|
|
|
|
|
IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING |
|
981
|
|
|
|
|
|
|
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR |
|
982
|
|
|
|
|
|
|
REDISTRIBUTE THE SOFTWARE AS PERMITTED BY THE ABOVE LICENSE, BE |
|
983
|
|
|
|
|
|
|
LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL, |
|
984
|
|
|
|
|
|
|
OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE |
|
985
|
|
|
|
|
|
|
THE SOFTWARE (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING |
|
986
|
|
|
|
|
|
|
RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A |
|
987
|
|
|
|
|
|
|
FAILURE OF THE SOFTWARE TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF |
|
988
|
|
|
|
|
|
|
SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF |
|
989
|
|
|
|
|
|
|
SUCH DAMAGES. |
|
990
|
|
|
|
|
|
|
|
|
991
|
|
|
|
|
|
|
=cut |