Jemplate
view release on metacpan or search on metacpan
if ((my $slot = $self->{ LOOKUP }->{ $name })) {
# cached entry exists, so refresh slot and extract data
my ($data, $error) = $self->_refresh($slot);
return $error
? ($data, $error)
: ($slot->[ DATA ], $error );
}
my $paths = $self->paths
|| return ( $self->error, Template::Constants::STATUS_ERROR );
# search the INCLUDE_PATH for the file, in cache or on disk
foreach my $dir (@$paths) {
my $path = File::Spec->catfile($dir, $name);
$self->debug("searching path: $path\n") if $self->{ DEBUG };
my ($data, $error) = $self->_fetch( $path, $name );
# Return if no error or if a serious error.
return ( $data, $error )
if !$error || $error == Template::Constants::STATUS_ERROR;
}
# not found in INCLUDE_PATH, now try DEFAULT
return $self->_fetch_path( $self->{DEFAULT} )
if defined $self->{DEFAULT} && $name ne $self->{DEFAULT};
# We could not handle this template name
return (undef, Template::Constants::STATUS_DECLINED);
}
sub _compiled_filename {
my ($self, $file) = @_;
my ($compext, $compdir) = @$self{ qw( COMPILE_EXT COMPILE_DIR ) };
my ($path, $compiled);
return undef
unless $compext || $compdir;
$path = $file;
$path =~ /^(.+)$/s or die "invalid filename: $path";
$path =~ s[:][]g if $^O eq 'MSWin32';
$compiled = "$path$compext";
$compiled = File::Spec->catfile($compdir, $compiled) if length $compdir;
return $compiled;
}
sub _load_compiled {
my ($self, $file) = @_;
my $compiled;
# load compiled template via require(); we zap any
# %INC entry to ensure it is reloaded (we don't
# want 1 returned by require() to say it's in memory)
delete $INC{ $file };
eval { $compiled = require $file; };
return $@
? $self->error("compiled template $compiled: $@")
: $compiled;
}
sub _load {
my ($self, $name, $alias) = @_;
my ($data, $error);
my $tolerant = $self->{ TOLERANT };
my $now = time;
$alias = $name unless defined $alias or ref $name;
$self->debug("_load($name, ", defined $alias ? $alias : '<no alias>',
')') if $self->{ DEBUG };
# SCALAR ref is the template text
if (ref $name eq 'SCALAR') {
# $name can be a SCALAR reference to the input text...
return {
name => defined $alias ? $alias : 'input text',
path => defined $alias ? $alias : 'input text',
text => $$name,
time => $now,
load => 0,
};
}
# Otherwise, assume GLOB as a file handle
if (ref $name) {
local $/;
my $text = <$name>;
$text = $self->_decode_unicode($text) if $self->{ UNICODE };
return {
name => defined $alias ? $alias : 'input file handle',
path => defined $alias ? $alias : 'input file handle',
text => $text,
time => $now,
load => 0,
};
}
# Otherwise, it's the name of the template
if ( $self->_template_modified( $name ) ) { # does template exist?
my ($text, $error, $mtime ) = $self->_template_content( $name );
unless ( $error ) {
$text = $self->_decode_unicode($text) if $self->{ UNICODE };
return {
name => $alias,
path => $name,
text => $text,
time => $mtime,
load => $now,
};
}
return ( $error, Template::Constants::STATUS_ERROR )
unless $tolerant;
}
close MODULE;
return 1;
}
sub compile_module_cached {
my ($self, $module_path, $template_file_paths) = @_;
my $m = -M $module_path;
return 0 unless grep { -M($_) < $m } @$template_file_paths;
return $self->compile_module($module_path, $template_file_paths);
}
sub compile_template_files {
my $self = shift;
my $output = $self->_preamble;
for my $filepath (@_) {
my $filename = $filepath;
$filename =~ s/.*[\/\\]//;
open FILE, $filepath
or die "Can't open '$filepath' for input:\n$!";
my $template_input = do {local $/; <FILE>};
close FILE;
$output .=
$self->compile_template_content($template_input, $filename);
}
return $output;
}
sub compile_template_content {
die "Invalid arguments in call to Jemplate->compile_template_content"
unless @_ == 3;
my ($self, $template_content, $template_name) = @_;
my $parser = Jemplate::Parser->new( ref($self) ? %$self : () );
my $parse_tree = $parser->parse(
$template_content, {name => $template_name}
) or die $parser->error;
my $output =
"Jemplate.templateMap['$template_name'] = " .
$parse_tree->{BLOCK} .
"\n";
for my $function_name (sort keys %{$parse_tree->{DEFBLOCKS}}) {
$output .=
"Jemplate.templateMap['$function_name'] = " .
$parse_tree->{DEFBLOCKS}{$function_name} .
"\n";
}
return $output;
}
sub _preamble {
return <<'...';
/*
This JavaScript code was generated by Jemplate, the JavaScript
Template Toolkit. Any changes made to this file will be lost the next
time the templates are compiled.
Copyright 2006-2014 - Ingy döt Net - All rights reserved.
*/
var Jemplate;
if (typeof(exports) == 'object') {
Jemplate = require("jemplate").Jemplate;
}
if (typeof(Jemplate) == 'undefined')
throw('Jemplate.js must be loaded before any Jemplate template files');
...
}
1;
}
#BOOTSTRAP-END
Jemplate->main(@ARGV);
__END__
=encoding UTF-8
=head1 Usage:
jemplate --runtime [runtime-opt]
jemplate --compile [compile-opt] template-list
jemplate --runtime [runtime-opt] --compile [compile-opt] template-list
jemplate --list template-list
Where C<--runtime> and C<runtime-opt> can include:
--runtime Equivalent to --ajax=ilinsky --json=json2
--runtime=standard
--runtime=lite Same as --ajax=none --json=none
--runtime=jquery Same as --ajax=jquery --json=none
--runtime=yui Same as --ajax=yui --json=yui
--runtime=legacy Same as --ajax=gregory --json=json2
--json By itself, equivalent to --json=json2
--json=json2 Include http://www.json.org/json2.js for parsing/stringifying
--json=yui Use YUI: YAHOO.lang.JSON (requires external YUI)
--json=none Doesn't provide any JSON functionality except a warning
--ajax By itself, equivalent to --ajax=xhr
--ajax=jquery Use jQuery for Ajax get and post (requires external jQuery)
--ajax=yui Use YUI: yui/connection/connection.js (requires external YUI)
--ajax=xhr Use XMLHttpRequest (will automatically use --xhr=ilinsky if --xhr is not set)
--ajax=none Doesn't provide any Ajax functionality except a warning
--xhr By itself, equivalent to --xhr=ilinsky
--xhr=ilinsky Include http://code.google.com/p/xmlhttprequest/
--xhr=gregory Include http://www.scss.com.au/family/andrew/webdesign/xmlhttprequest/
--xxx Include XXX and JJJ helper functions
--compact Use the YUICompressor compacted version of the runtime
Where C<compile-opt> can include:
( run in 0.819 second using v1.01-cache-2.11-cpan-5a3173703d6 )