1
  2   	ˆ0_’I|¥‰ÓMjqØ‚¦ð¬÷a–Ü4ý(&”ÔD¨ 	Å ÕÀ†à‚¦-ÿÂ  0   ˆl–Ãa¾”TËmJiAã.Ü TÅ£Á„Î¼÷_‹uÐb&=LV[(ÀÄ ?÷     #============================================================= -*-Perl-*-
#
# Template::Stash
#
# DESCRIPTION
#   Definition of an object class which stores and manages access to
#   variables for the Template Toolkit.
#
# AUTHOR
#   Andy Wardley   <abw@wardley.org>
#
# COPYRIGHT
#   Copyright (C) 1996-2022 Andy Wardley.  All Rights Reserved.
#
#   This module is free software; you can redistribute it and/or
#   modify it under the same terms as Perl itself.
#
#============================================================================

package Template::Stash;

use strict;
use warnings;
use Template::VMethods;
use Template::Exception;
use Scalar::Util qw( blessed reftype );

our $VERSION    = '3.100';
our $DEBUG      = 0 unless defined $DEBUG;
our $PRIVATE    = qr/^[_.]/;
our $UNDEF_TYPE = 'var.undef';
our $UNDEF_INFO = 'undefined variable: %s';

# alias _dotop() to dotop() so that we have a consistent method name
# between the Perl and XS stash implementations
*dotop = \&_dotop;


#------------------------------------------------------------------------
# Virtual Methods
#
# If any of $ROOT_OPS, $SCALAR_OPS, $HASH_OPS or $LIST_OPS are already
# defined then we merge their contents with the default virtual methods
# define by Template::VMethods.  Otherwise we can directly alias the
# corresponding Template::VMethod package vars.
#------------------------------------------------------------------------

our $ROOT_OPS = defined $ROOT_OPS
    ? { %{$Template::VMethods::ROOT_VMETHODS}, %$ROOT_OPS }
    : $Template::VMethods::ROOT_VMETHODS;

our $SCALAR_OPS = defined $SCALAR_OPS
    ? { %{$Template::VMethods::TEXT_VMETHODS}, %$SCALAR_OPS }
    : $Template::VMethods::TEXT_VMETHODS;

our $HASH_OPS = defined $HASH_OPS
    ? { %{$Template::VMethods::HASH_VMETHODS}, %$HASH_OPS }
    : $Template::VMethods::HASH_VMETHODS;

our $LIST_OPS = defined $LIST_OPS
    ? { %{$Template::VMethods::LIST_VMETHODS}, %$LIST_OPS }
    : $Template::VMethods::LIST_VMETHODS;


#------------------------------------------------------------------------
# define_vmethod($type, $name, \&sub)
#
# Defines a virtual method of type $type (SCALAR, HASH, or LIST), with
# name $name, that invokes &sub when called.  It is expected that &sub
# be able to handle the type that it will be called upon.
#------------------------------------------------------------------------

sub define_vmethod {
    my ($class, $type, $name, $sub) = @_;
    my $op;
    $type = lc $type;

    if ($type eq 'scalar' || $type eq 'item') {
        $op = $SCALAR_OPS;
    }
    elsif ($type eq 'hash') {
        $op = $HASH_OPS;
    }
    elsif ($type eq 'list' || $type eq 'array') {
        $op = $LIST_OPS;
    }
    else {
        die "invalid vmethod type: $type\n";
    }

    $op->{ $name } = $sub;

    return 1;
}


#========================================================================
#                      -----  CLASS METHODS -----
#========================================================================

#------------------------------------------------------------------------
# new(\%params)
#
# Constructor method which creates a new Template::Stash object.
# An optional hash reference may be passed containing variable
# definitions that will be used to initialise the stash.
#
# Returns a reference to a newly created Template::Stash.
#------------------------------------------------------------------------

sub new {
    my $class  = shift;
    my $params = ref $_[0] eq 'HASH' ? shift(@_) : { @_ };

    my $self   = {
        global  => { },
        %$params,
        %$ROOT_OPS,
        '_PARENT' => undef,
    };

    bless $self, $class;
}


#========================================================================
#                   -----  PUBLIC OBJECT METHODS -----
#========================================================================

#------------------------------------------------------------------------
# clone(\%params)
#
# Creates a copy o