I forgot to include the patch to HTML::Template 2.6. Sorry.
Roman Porizka
--- Template.pm.orig 2002-10-14 13:44:04.000000000 +0200
+++ Template.pm 2002-10-14 13:47:01.000000000 +0200
@@ -901,6 +901,7 @@
sub WHICH () { 4 };
sub WHICH_IF () { 0 };
sub WHICH_UNLESS () { 1 };
+sub DEFAULT () { 5 };
# back to the main package scope.
package HTML::Template;
@@ -946,6 +947,8 @@
no_includes => 0,
case_sensitive => 0,
filter => [],
+ overwrite_idefaults => 1,
+ recursive_idefaults => 0,
);
# load in options supplied to new()
@@ -1685,8 +1688,8 @@
# setup the stacks and maps - they're accessed by typeglobs that
# reference the top of the stack. They are masked so that a loop
# can transparently have its own versions.
- use vars qw(@pstack %pmap @ifstack @ucstack %top_pmap);
- local (*pstack, *ifstack, *pmap, *ucstack, *top_pmap);
+ use vars qw(@pstack %pmap @ifstack @ucstack %top_pmap %fdmap);
+ local (*pstack, *ifstack, *pmap, *ucstack, *top_pmap, *fdmap);
# the pstack is the array of scalar refs (plain text from the
# template file), VARs, LOOPs, IFs and ELSEs that output() works on
@@ -1704,6 +1707,10 @@
*top_pmap = $pmaps[0];
$self->{param_map} = $pmaps[0];
+ # fdmap -- hash of DEFAULT variables in actual include
+ my @fdmaps = ({});
+ *fdmap = $fdmaps[0];
+
# the ifstack is a temporary stack containing pending ifs and elses
# waiting for a /if.
my @ifstacks = ([]);
@@ -1726,14 +1733,16 @@
# of which file we're in and where we are in it. This allows
# accurate error messages even inside included files!
# fcounter, fmax and fname are aliases for the current file's info
- use vars qw($fcounter $fname $fmax);
- local (*fcounter, *fname, *fmax);
+ # fdefaults is alias for hash of defaults, which were passed to current
+ # TMPL_INCLUDE tag
+ use vars qw($fcounter $fdefaults $fname $fmax);
+ local (*fcounter, *fdefaults, *fname, *fmax);
my @fstack = ([$options->{filepath} || "/fake/path/for/non/file/template",
- 1,
+ 1, {},
scalar @{[$self->{template} =~ m/(\n)/g]} + 1
]);
- (*fname, *fcounter, *fmax) = \ ( @{$fstack[0]} );
+ (*fname, *fcounter, *fdefaults, *fmax) = \ ( @{$fstack[0]} );
my $NOOP = HTML::Template::NOOP->new();
my $ESCAPE = HTML::Template::ESCAPE->new();
@@ -1935,24 +1944,46 @@
die "HTML::Template->new() : ESCAPE option invalid in a $which tag at $fname :
line $fcounter." if ( $escape and ($which ne 'TMPL_VAR'));
# die if we got a default but can't use one
- die "HTML::Template->new() : DEFAULT option invalid in a $which tag at $fname :
line $fcounter." if ( defined $default and ($which ne 'TMPL_VAR'));
+ die "HTML::Template->new() : DEFAULT option invalid in a $which tag at $fname :
+line $fcounter." if ( defined $default and ($which ne 'TMPL_VAR' and $which ne
+'TMPL_INCLUDE'));
# take actions depending on which tag found
if ($which eq 'TMPL_VAR') {
$options->{debug} and print STDERR "### HTML::Template Debug ### $fname : line
$fcounter : parsed VAR $name\n";
- # if we already have this var, then simply link to the existing
- # HTML::Template::VAR, else create a new one.
my $var;
- if (exists $pmap{$name}) {
- $var = $pmap{$name};
- (ref($var) eq 'HTML::Template::VAR') or
- die "HTML::Template->new() : Already used param name $name as a TMPL_LOOP,
found in a TMPL_VAR at $fname : line $fcounter.";
+ # If it is some of the "include defaults", we aren't in loop and it
+ # should not be overwritten by calling "param()".
+ if (exists($fdefaults->{$name}) and !$options->{overwrite_idefaults} and
+ (!scalar(@loopstack) or $options->{global_vars})) {
+ if (exists($fdmap{$name})) {
+ $var = $fdmap{$name};
+ } else {
+ $var = HTML::Template::VAR->new();
+ $fdmap{$name} = $var;
+ ${$var} = $fdefaults->{$name};
+ undef($default);
+ }
+ # we won't dying for bad params in loops
+ $pmap{$name} = HTML::Template::VAR->new() if
+ (!exists($pmap{$name}) and scalar(@loopstack));
} else {
- $var = HTML::Template::VAR->new();
- $pmap{$name} = $var;
- $top_pmap{$name} = HTML::Template::VAR->new()
- if $options->{global_vars} and not exists $top_pmap{$name};
+ # if we already have this var, then simply link to the existing
+ # HTML::Template::VAR, else create a new one.
+ if (exists $pmap{$name}) {
+ $var = $pmap{$name};
+ (ref($var) eq 'HTML::Template::VAR') or
+ die "HTML::Template->new() : Already used param name $name as a
+TMPL_LOOP, found in a TMPL_VAR at $fname : line $fcounter.";
+ } else {
+ $var = HTML::Template::VAR->new();
+ $pmap{$name} = $var;
+ $top_pmap{$name} = HTML::Template::VAR->new()
+ if $options->{global_vars} and not exists $top_pmap{$name};
+ }
+ # If a DEFAULT in TMPL_INCLUDE was provided and we want, that it
+ # could be overwritten by calling "param()". So we set DEFAULT for
+ # this variable
+ ($default = $fdefaults->{$name})
+ if (exists($fdefaults->{$name}) and (!scalar(@loopstack) or
+$options->{global_vars}));
}
# if a DEFAULT was provided, push a DEFAULT object on the
@@ -2077,15 +2108,28 @@
# if we already have this var, then simply link to the existing
# HTML::Template::VAR/LOOP, else defer the mapping
- my $var;
- if (exists $pmap{$name}) {
- $var = $pmap{$name};
+ my $var;
+ if (exists($fdefaults->{$name}) and !$options->{overwrite_idefaults}) {
+ if (exists($fdmap{$name})) {
+ $var = $fdmap{$name};
+ } else {
+ $var = HTML::Template::VAR->new();
+ $fdmap{$name} = $var;
+ ${$var} = $fdefaults->{$name};
+ }
} else {
- $var = $name;
+ if (exists $pmap{$name}) {
+ $var = $pmap{$name};
+ } else {
+ $var = $name;
+ }
}
-
+
# connect the var to a conditional
my $cond = HTML::Template::COND->new($var);
+ # there is defined fdefault for the var and it could be overwritten by
+ # setting it with param function
+ $cond->[HTML::Template::COND::DEFAULT] = $fdefaults->{$name} if
+($options->{overwrite_idefaults} and exists($fdefaults->{$name}));
if ($which eq 'TMPL_IF') {
$cond->[HTML::Template::COND::WHICH] = HTML::Template::COND::WHICH_IF;
$cond->[HTML::Template::COND::JUMP_IF_TRUE] = 0;
@@ -2139,6 +2183,7 @@
my $else = HTML::Template::COND->new($cond->[HTML::Template::COND::VARIABLE]);
$else->[HTML::Template::COND::WHICH] = $cond->[HTML::Template::COND::WHICH];
$else->[HTML::Template::COND::JUMP_IF_TRUE] = not
$cond->[HTML::Template::COND::JUMP_IF_TRUE];
+ $else->[HTML::Template::COND::DEFAULT] =
+$cond->[HTML::Template::COND::DEFAULT];
# need end-block resolution?
if (defined($cond->[HTML::Template::COND::VARIABLE_TYPE])) {
@@ -2199,11 +2244,23 @@
$self->{included_mtimes}{$filepath} = (stat($filepath))[9];
}
- # adjust the fstack to point to the included file info
- push(@fstack, [$filepath, 1,
+ # resolve the default values
+ my %hash = ();
+ %hash = %{$fdefaults} if ($options->{recursive_idefaults});
+ if (defined($default)) {
+ my @array = map(split(/=/),split(/,/,$default));
+
+ for (my $x = 0; $x <= $#array; $x += 2) {
+ $hash{$array[$x]} = $array[($x+1)];
+ }
+ }
+ push(@fdmaps,{});
+ *fdmap = $fdmaps[$#fdmaps];
+ # adjust the fstack to point to the included file info
+ push(@fstack, [$filepath, 1, \%hash,
scalar @{[$included_template =~ m/(\n)/g]} + 1]);
- (*fname, *fcounter, *fmax) = \ ( @{$fstack[$#fstack]} );
-
+ (*fname, *fcounter, *fdefaults, *fmax) = \ ( @{$fstack[$#fstack]} );
+
# make sure we aren't infinitely recursing
die "HTML::Template->new() : likely recursive includes - parsed
$options->{max_includes} files deep and giving up (set max_includes higher to allow
deeper recursion)." if ($options->{max_includes} and (scalar(@fstack) >
$options->{max_includes}));
@@ -2256,7 +2313,7 @@
$fcounter += scalar(@{[$chunk =~ m/(\n)/g]});
# if we just crossed the end of an included file
# pop off the record and re-alias to the enclosing file's info
- pop(@fstack), (*fname, *fcounter, *fmax) = \ ( @{$fstack[$#fstack]} )
+ pop(@fstack), (*fname, *fcounter, *fdefaults, *fmax) = \ ( @{$fstack[$#fstack]}),
+pop(@fdmaps), *fdmap = $fdmaps[$#fdmaps]
if ($fcounter > $fmax);
} # next CHUNK
@@ -2596,6 +2653,7 @@
if defined $args{print_to} and not tied $args{print_to};
my $type;
+
my $parse_stack_length = $#parse_stack;
for (my $x = 0; $x <= $parse_stack_length; $x++) {
*line = \$parse_stack[$x];
@@ -2622,7 +2680,10 @@
} else {
$x = $line->[HTML::Template::COND::JUMP_ADDRESS] if
${$line->[HTML::Template::COND::VARIABLE]};
}
- }
+ } else {
+ $x = $line->[HTML::Template::COND::JUMP_ADDRESS] if
+ (defined($line->[HTML::Template::COND::DEFAULT]) and
+$line->[HTML::Template::COND::DEFAULT]);
+ }
} else {
$x = $line->[HTML::Template::COND::JUMP_ADDRESS] if
(defined
$line->[HTML::Template::COND::VARIABLE][HTML::Template::LOOP::PARAM_SET] and
@@ -2637,7 +2698,12 @@
$x = $line->[HTML::Template::COND::JUMP_ADDRESS] unless
${$line->[HTML::Template::COND::VARIABLE]};
}
} else {
- $x = $line->[HTML::Template::COND::JUMP_ADDRESS];
+ if (defined($line->[HTML::Template::COND::DEFAULT])) {
+ $x = $line->[HTML::Template::COND::JUMP_ADDRESS] unless
+ $line->[HTML::Template::COND::DEFAULT];
+ } else {
+ $x = $line->[HTML::Template::COND::JUMP_ADDRESS];
+ }
}
} else {
$x = $line->[HTML::Template::COND::JUMP_ADDRESS] if