File Coverage

lib/Templer/Plugin/FileContents.pm
Criterion Covered Total %
statement 35 42 83.3
branch 7 12 58.3
condition 1 3 33.3
subroutine 6 6 100.0
pod 1 3 33.3
total 50 66 75.7


line stmt bran cond sub pod time code
1              
2             =head1 NAME
3            
4             Templer::Plugin::FileContents - A plugin to read file contents.
5            
6             =cut
7              
8             =head1 SYNOPSIS
9            
10             The following is a good example use of this plugin
11            
12             title: About my site
13             passwd: read_file( /etc/passwd )
14             ----
15             <p>This is my password file:</p>
16             <!-- tmpl_var name='passwd' -->
17            
18             =cut
19              
20             =head1 DESCRIPTION
21            
22             This plugin reads the contents of files from the local system,
23             and allows files to be included inline in templates.
24            
25             =cut
26              
27             =head1 LICENSE
28            
29             This module is free software; you can redistribute it and/or modify it
30             under the terms of either:
31            
32             a) the GNU General Public License as published by the Free Software
33             Foundation; either version 2, or (at your option) any later version,
34             or
35            
36             b) the Perl "Artistic License".
37            
38             =cut
39              
40             =head1 AUTHOR
41            
42             Steve Kemp <steve@steve.org.uk>
43            
44             =cut
45              
46             =head1 COPYRIGHT AND LICENSE
47            
48             Copyright (C) 2012-2015 Steve Kemp <steve@steve.org.uk>.
49            
50             This library is free software. You can modify and or distribute it under
51             the same terms as Perl itself.
52            
53             =cut
54              
55             =head1 METHODS
56            
57             =cut
58              
59              
60 11     11   5313 use strict;
  11         13  
  11         242  
61 11     11   28 use warnings;
  11         12  
  11         302  
62              
63              
64             package Templer::Plugin::FileContents;
65              
66 11     11   36 use File::Basename;
  11         8  
  11         4010  
67              
68              
69              
70             =head2
71            
72             Constructor. No arguments are required/supported.
73            
74             =cut
75              
76             sub new
77             {
78 11     11 0 20     my ( $proto, %supplied ) = (@_);
79 11   33     53     my $class = ref($proto) || $proto;
80              
81 11         16     my $self = {};
82 11         15     bless( $self, $class );
83 11         75     return $self;
84             }
85              
86              
87              
88             =head2 expand_variables
89            
90             This is the method which is called by the L<Templer::Plugin::Factory>
91             to expand the variables contained in a L<Templer::Site::Page> object.
92            
93             Variables are written in the file in the form "key: value", and are
94             internally stored within the Page object as a hash.
95            
96             This method iterates over each key & value and updates any that
97             seem to refer to file-inclusion.
98            
99             =cut
100              
101             sub expand_variables
102             {
103 9     9 1 15     my ( $self, $site, $page, $data ) = (@_);
104              
105             #
106             # Get the page-variables in the template.
107             #
108 9         33     my %hash = %$data;
109              
110             #
111             # Look for a value of "read_file" in each key.
112             #
113 9         31     foreach my $key ( keys %hash )
114                 {
115 66 100       109         if ( $hash{ $key } =~ /^read_file\((.*)\)/ )
116                     {
117              
118             #
119             # Get the filename specified.
120             #
121 2         4             my $file = $1;
122              
123             #
124             # Strip leading/trailing quotes and whitespace.
125             #
126 2         6             $file =~ s/['"]//g;
127 2         6             $file =~ s/^\s+|\s+$//g;
128              
129              
130             #
131             # Are we reading the input page itself?
132             #
133 2 100       8             if ( $file eq "SELF" )
    50          
134                         {
135 1         2                 $file = $page->source();
136                         }
137                         elsif ( $file =~ /^\// )
138                         {
139              
140             # File is absolute - no handling.
141                         }
142                         else
143                         {
144              
145             #
146             # Relative file. We want to look for the file based upon the
147             # global include-path with the current directory appended.
148             #
149             # In the case of multiple matches the last one
150             # wins. i.e. The non-global one.
151             #
152             #
153              
154             #
155             # Get the global variables from the configuration object.
156             #
157 0         0                 my $dirs = $site->get("include-path");
158 0         0                 my @dirs = @$dirs;
159              
160             #
161             # Append the directory from the input page.
162             #
163 0         0                 push( @dirs, File::Basename::dirname( $page->source() ) );
164              
165             #
166             # Iterate
167             #
168 0         0                 foreach my $dir (@dirs)
169                             {
170 0 0       0                     if ( -e $dir . "/" . $file )
171                                 {
172 0         0                         $file = $dir . "/" . $file;
173                                 }
174                             }
175                         }
176              
177 2         4             $hash{ $key } = $self->file_contents($file);
178              
179             #
180             # The page dependency also includes the filename now.
181             #
182 2         5             $page->add_dependency($file);
183                     }
184                 }
185              
186 9         17     return ( \%hash );
187             }
188              
189              
190             #
191             # Return the contents of the named file.
192             #
193             sub file_contents
194             {
195 2     2 0 2     my ( $self, $name ) = (@_);
196              
197 2         1     my $content = "";
198              
199 2 50       28     if ( -e $name )
200                 {
201 2 50       42         open( my $handle, "<:utf8", $name ) or
202                       return "";
203              
204 2         5         binmode( $handle, ":utf8" );
205              
206 2         15         while ( my $line = <$handle> )
207                     {
208 27         45             $content .= $line;
209                     }
210 2         11         close($handle);
211                 }
212                 else
213                 {
214 0         0         print "WARNING: Attempting to read a file that doesn't exist: $name\n";
215                 }
216              
217 2         5     $content;
218             }
219              
220             #
221             # Register the plugin.
222             #
223             Templer::Plugin::Factory->new()
224               ->register_plugin("Templer::Plugin::FileContents");
225