File Coverage

blib/lib/Pod/Loom/Template.pm
Criterion Covered Total %
statement 101 186 54.3
branch 27 86 31.4
condition 6 26 23.0
subroutine 18 25 72.0
pod 14 14 100.0
total 166 337 49.2


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