use C4::Languages qw(getTranslatedLanguages get_bidi regex_lang_subtags language_get_description accept_language );
use C4::Dates qw(format_date);
use C4::Budgets qw(GetCurrency);
+use C4::Templates;
-use HTML::Template::Pro;
+#use HTML::Template::Pro;
use vars qw($VERSION @ISA @EXPORT @EXPORT_OK %EXPORT_TAGS);
BEGIN {
my $opacstylesheet = C4::Context->preference('opacstylesheet');
my ( $htdocs, $theme, $lang, $filename ) = _get_template_file( $tmplbase, $interface, $query );
- my $template = HTML::Template::Pro->new(
- filename => $filename,
- die_on_bad_params => 1,
- global_vars => 1,
- case_sensitive => 1,
- loop_context_vars => 1, # enable: __first__, __last__, __inner__, __odd__, __counter__
- path => ["$htdocs/$theme/$lang/$path"]
- );
+# my $template = HTML::Template::Pro->new(
+# filename => $filename,
+# die_on_bad_params => 1,
+# global_vars => 1,
+# case_sensitive => 1,
+# loop_context_vars => 1, # enable: __first__, __last__, __inner__, __odd__, __counter__
+# path => ["$htdocs/$theme/$lang/$path"]
+# );
+ $filename =~ s/\.tmpl$/.tt/;
+ my $template = C4::Templates->new( $interface, $filename);
my $themelang=( $interface ne 'intranet' ? '/opac-tmpl' : '/intranet-tmpl' )
. "/$theme/$lang";
$template->param(
--- /dev/null
+package C4::Templates;
+
+use strict;
+use warnings;
+use Carp;
+
+# Copyright 2009 Chris Cormack and The Koha Dev Team
+#
+# This file is part of Koha.
+#
+# Koha is free software; you can redistribute it and/or modify it under the
+# terms of the GNU General Public License as published by the Free Software
+# Foundation; either version 2 of the License, or (at your option) any later
+# version.
+#
+# Koha is distributed in the hope that it will be useful, but WITHOUT ANY
+# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
+# A PARTICULAR PURPOSE. See the GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License along with
+# Koha; if not, write to the Free Software Foundation, Inc., 59 Temple Place,
+# Suite 330, Boston, MA 02111-1307 USA
+
+=head1 NAME
+
+ Koha::Templates - Object for manipulating templates for use with Koha
+
+=cut
+
+use base qw(Class::Accessor);
+use Template;
+use Template::Constants qw( :debug );
+
+use C4::Context;
+
+__PACKAGE__->mk_accessors(qw( theme lang filename htdocs interface vars));
+
+sub new {
+ my $class = shift;
+ my $interface = shift;
+ my $filename = shift;
+ my $htdocs;
+ if ( $interface ne "intranet" ) {
+ $htdocs = C4::Context->config('opachtdocs');
+ }
+ else {
+ $htdocs = C4::Context->config('intrahtdocs');
+ }
+
+# my ( $theme, $lang ) = themelanguage( $htdocs, $tmplbase, $interface, $query );
+ my $theme = 'prog';
+ my $lang = 'en';
+ my $template = Template->new(
+ {
+ EVAL_PERL => 1,
+ ABSOLUTE => 1,
+ INCLUDE_PATH => "$htdocs/$theme/$lang/includes",
+ FILTERS => {},
+
+ }
+ ) or die Template->error();
+ my $self = {
+ TEMPLATE => $template,
+ VARS => {},
+ };
+ bless $self, $class;
+ $self->theme($theme);
+ $self->lang($lang);
+ $self->filename($filename);
+ $self->htdocs($htdocs);
+ $self->interface($interface);
+ $self->{VARS}->{"test"} = "value";
+ return $self;
+
+}
+
+sub output {
+ my $self = shift;
+ my $vars = shift;
+# my $file = $self->htdocs . '/' . $self->theme .'/'.$self->lang.'/'.$self->filename;
+ my $template = $self->{TEMPLATE};
+ if ($self->interface eq 'intranet'){
+ $vars->{themelang} = '/intranet-tmpl';
+ }
+ else {
+ $vars->{themelang} = '/opac-tmpl';
+ }
+ $vars->{lang} = $self->lang;
+ $vars->{themelang} .= '/' . $self->theme . '/' . $self->lang;
+ $vars->{yuipath} = (C4::Context->preference("yuipath") eq "local"?$self->{themelang}."/lib/yui":C4::Context->preference("yuipath"));
+ $vars->{interface} = ( $vars->{interface} ne 'intranet' ? '/opac-tmpl' : '/intranet-tmpl' );
+ $vars->{theme} = $self->theme;
+ $vars->{opaccolorstylesheet} = C4::Context->preference('opaccolorstylesheet');
+ $vars->{opacsmallimage} = C4::Context->preference('opacsmallimage');
+ $vars->{opacstylesheet} = C4::Context->preference('opacstylesheet');
+ #add variables set via param to $vars for processing
+ for my $k(keys %{$self->{VARS}}){
+ $vars->{$k} = $self->{VARS}->{$k};
+ }
+ my $data;
+ $template->process( $self->filename, $vars, \$data) || die "Template process failed: ", $template->error();;
+ return $data;
+}
+
+# wrapper method to allow easier transition from HTML template pro to Template Toolkit
+sub param{
+ my $self = shift;
+ while(@_){
+ my $key = shift;
+ my $val = shift;
+ $self->{VARS}->{$key} = $val;
+ }
+}
+
+1;
--- /dev/null
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+use Carp;
+use Data::Dumper;
+
+use Getopt::Long;
+use File::Basename;
+use File::Copy;
+
+my $help_msg = <<EOH;
+This script does a first-cut conversion of koha HTML::Template template files (.tmpl).
+It creates a mirror of koha-tmpl called koha-tt where converted files will be placed.
+By default all files will be converted: use the --file (-f) argument to specify
+ individual files to process.
+
+Options:
+ --koharoot (-r): Root directory of koha installation.
+ --type (-t): template file extenstions to match
+ (defaults to tmpl|inc|xsl).
+ --copyall (-c): Also copy across all files in template directory
+ --file (-f): specify individual files to process
+ --debug (-d): output more information.
+EOH
+
+my $tmpl_in_dir = 'koha-tmpl';
+my $tmpl_out_dir = 'koha-tt';
+
+# Arguments:
+my $KOHA_ROOT;
+my $tmpl_extn_match = "tmpl|inc|xsl|pref"; # Type match defaults to *.tmpl plus *.inc if not specified
+my $copy_other_files = 0;
+my @template_files;
+my @files_w_tmpl_loops;
+my $verbose = 0;
+GetOptions (
+ "koharoot=s" => \$KOHA_ROOT,
+ "type|t=s" => \$tmpl_extn_match,
+ "copyall|c" => \$copy_other_files,
+ "file|f=s" => \@template_files, # array of filenames
+ "verbose+" => \$verbose, # incremental flag
+) or die $help_msg;
+
+if ( ! $KOHA_ROOT || ! -d $KOHA_ROOT ) {
+ croak "Koha root not passed or is not correct.";
+}
+if ( ! -d "$KOHA_ROOT/$tmpl_in_dir" ) {
+ croak "Cannot find template dir ($tmpl_in_dir)";
+}
+
+# Attempt to create koha-tt dir..
+if ( ! -d "$KOHA_ROOT/$tmpl_out_dir" ) {
+ mkdir("$KOHA_ROOT/$tmpl_out_dir") #, '0755'
+ or croak "Cannot create $tmpl_out_dir directory in $KOHA_ROOT: $!";
+}
+
+# Obtain list of files to process - go recursively through tmpl_in_dir and subdirectories..
+unless ( scalar(@template_files) ) {
+ @template_files = mirror_template_dir_structure_return_files("$KOHA_ROOT/$tmpl_in_dir", "$tmpl_extn_match");
+}
+foreach my $file (@template_files) {
+ (my $new_path = $file) =~ s/$tmpl_in_dir/$tmpl_out_dir/;
+ $new_path =~ s/\.tmpl/.tt/;
+ $new_path = "$KOHA_ROOT/$new_path" unless ( $new_path =~ m/^$KOHA_ROOT/ );
+
+ open my $ITMPL, '<', $file or croak "Can't open $file for input: $!";
+ open my $OTT, '>', $new_path or croak "Can't open $new_path for output: $!";
+
+ # Slurp in input file..
+ my $input_tmpl = do { local $/; <$ITMPL> };
+ close $ITMPL;
+
+ # handle poorly names variable such as f1!, f1+, f1-, f1| and mod
+ $input_tmpl =~ s/"(\w+)\|"/"$1pipe"/ig;
+ $input_tmpl =~ s/"(\w+)\+"/"$1plus"/ig;
+ $input_tmpl =~ s/"(\w+)\-"/"$1minus"/ig;
+ $input_tmpl =~ s/"(\w+)!"/"$1exclamation"/ig;
+ $input_tmpl =~ s/"(\w+),(\w+)"/"$1comma$2"/ig;
+ $input_tmpl =~ s/NAME="mod"/NAME="modname"/ig;
+ # handle 'naked' TMPL_VAR "parameter" by turning them into what they should be, TMPL_VAR NAME="parameter"
+ $input_tmpl =~ s/TMPL_VAR\s+"(\w+)"/TMPL_VAR NAME="$1"/ig;
+ # make an end (ESCAPE NAME DEFAULT) into a ned (NAME ESCAPE DEFAULT)
+ $input_tmpl =~ s/ESCAPE="(\w+?)"\s+NAME=['"](\w+?)['"]\s+DEFAULT=['"](.+?)['"]/NAME="$2" ESCAPE="$1" DEFAULT="$3"/ig;
+
+ # Process..
+ # NB: if you think you're seeing double, you probably are, *some* (read:most) patterns appear twice: once with quotations marks, once without.
+ # trying to combine them into a single pattern proved troublesome as a regex like ['"]?(.*?)['"]? was causing problems and fixing the problem caused (alot) more complex regex
+ # variables
+ $input_tmpl =~ s/<[!-]*\s*TMPL_VAR\s+NAME\s?=\s?['"]?\s*(\w*?)\s*['"]?\s+ESCAPE=['"](\w*?)['"]\s+DEFAULT=['"]?(.*?)['"]?\s*-*>/[% DEFAULT $1="$3" |$2 %]/ig; # CHECK ME PLEASE
+ $input_tmpl =~ s/<[!-]*\s*TMPL_VAR\s+NAME\s?=\s?['"]\s*(\w*?)\s*['"]\s+ESCAPE=['"]?(\w*?)['"]?\s*-*>/[% $1 |$2 %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_VAR\s+NAME\s?=\s?(\w*?)\s+ESCAPE=['"]?(\w*?)['"]?\s*-*>/[% $1 |$2 %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_VAR\s+ESCAPE=['"]?(\w*?)['"]?\s+NAME\s?=\s?['"]?([\w-]*?)['"]?\s*-*>/[% $2 |$1 %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_VAR\s+NAME\s?=\s?['"]?(\w*?)['"]?\s+DEFAULT=['"](.*?)['"]\s*-*>/[% DEFAULT $1="$2" %]/ig; # if a value being assigned is wrapped in quotes, keep them intact
+ $input_tmpl =~ s/<[!-]*\s*TMPL_VAR\s+NAME\s?=\s?['"]?\s*(\w*?)\s*['"]?\s+DEFAULT=(.*?)\s*-*>/[% DEFAULT $1=$2 %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL[_\s]VAR\s+NAME\s?=\s?['"]?\s*(\w*?)\s*['"]?\s*-*>/[% $1 %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL[_\s]VAR\s+EXPR\s?=\s?['"](.*?)['"]\s*-*>/[% $1 %]/ig; # TMPL_VAR NAME and TMPL_VAR EXPR are logically equiv, see http://search.cpan.org/~samtregar/HTML-Template-Expr-0.07/Expr.pm
+ $input_tmpl =~ s/<[!-]*\s*TMPL[_\s]VAR\s+EXPR\s?=\s?(.*?)\s*-*>/[% $1 %]/ig;
+
+ # if, elseif and unless blocks
+ $input_tmpl =~ s/<[!-]*\s*TMPL_IF\s+EXPR\s?=\s?['"](.*?)['"]\s*-*>/[% IF ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_IF\s+EXPR\s?=\s?(.*?)\s*-*>/[% IF ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_IF\s+NAME\s?=\s?['"]\s*(\w*?)\s*['"]\s*-*>/[% IF ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_IF\s+NAME\s?=\s?(\w*?)\s*-*>/[% IF ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_IF\s+['"](.*?)['"]\s*-*>/[% IF ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_IF\s+([\w\s]*?)\s*-*>/[% IF ( $1 ) %]/ig;
+
+ $input_tmpl =~ s/<[!-]*\s*TMPL_ELSIF\s+EXPR\s?=\s?['"](.*?)['"]\s*-*>/[% ELSEIF ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_ELSIF\s+EXPR\s?=\s?(.*?)\s*-*>/[% ELSEIF ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_ELSIF\s+NAME\s?=\s?['"](\w*?)['"]\s*-*>/[% ELSEIF ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_ELSIF\s+NAME\s?=\s?(\w*?)\s*-*>/[% ELSEIF ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_ELSIF\s+['"](\w*?)['"]\s*-*>/[% ELSEIF ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_ELSIF\s+(\w*?)\s*-*>/[% ELSEIF ( $1 ) %]/ig;
+
+ $input_tmpl =~ s/<[!-]*\s*TMPL_ELSE\s*-*>/[% ELSE %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*\/TMPL_IF\s*-*>/[% END %]/ig;
+
+ $input_tmpl =~ s/<[!-]*\s*TMPL_UNLESS\s+NAME\s?=\s?['"]?(\w*?)['"]?\s*-*>/[% UNLESS ( $1 ) %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*\/TMPL_UNLESS\s*-*>/[% END %]/ig;
+ # includes
+ $input_tmpl =~ s/<[!-]*\s*TMPL_INCLUDE\s+NAME\s?=\s?"(.*?\.inc)"\s*-*>/[% INCLUDE '$1' %]/ig;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_INCLUDE\s+NAME\s?=\s?"(.*?)"\s*-*>/[% INCLUDE $1 %]/ig;
+
+ if ( $input_tmpl =~ m/<!--[\s\/]*TMPL_LOOP\s*-->/i ) {
+ push(@files_w_tmpl_loops, $new_path);
+ }
+
+ $input_tmpl =~ s/<[!-]*\s*TMPL_LOOP\s+NAME\s?=\s?['"](.*?)['"]\s*-*>/"[% FOREACH ".substr($1, 0 , -1)." = ".$1." %]"/ieg;
+ $input_tmpl =~ s/<[!-]*\s*TMPL_LOOP\s+NAME\s?=\s?(.*?)\s*-*>/"[% FOREACH ".substr($1, 0 , -1)." = ".$1." %]"/ieg;
+ $input_tmpl =~ s/<[!-]*\s*\/TMPL_LOOP\s*-*>/[% END %]/ig;
+
+ # misc 'patches'
+ $input_tmpl =~ s/\seq\s/ == /ig;
+ $input_tmpl =~ s/HTML/html/ig;
+ $input_tmpl =~ s/URL/url/ig;
+
+ #hack to get around lack of javascript filter
+ $input_tmpl =~ s/\|JS/|replace("'", "\\'") |replace('"', '\\"') |replace('\\n', '\\\\n') |replace('\\r', '\\\\r')/ig;
+
+ # Write out..
+ print $OTT $input_tmpl;
+ close $OTT;
+}
+
+if ( scalar(@files_w_tmpl_loops) && $verbose ) {
+ print "\nThese files contain TMPL_LOOPs that need double checking:\n";
+ foreach my $file (@files_w_tmpl_loops) {
+ print "$file\n";
+ }
+}
+
+## SUB-ROUTINES ##
+
+# Create new directory structure and return list of template files
+sub mirror_template_dir_structure_return_files {
+ my($dir, $type) = @_;
+
+ my @files = ();
+ if ( opendir(DIR, $dir) ) {
+ my @dirent = readdir DIR; # because DIR is shared when recursing
+ closedir DIR;
+ for my $dirent (@dirent) {
+ my $path = "$dir/$dirent";
+ if ( $dirent =~ /^\./ ) {
+ ;
+ }
+ elsif ( -f $path ) {
+ (my $new_path = $path) =~ s/$tmpl_in_dir/$tmpl_out_dir/;
+ $new_path = "$KOHA_ROOT/$new_path" unless ( $new_path =~ m/^$KOHA_ROOT/ );
+ if ( !defined $type || $dirent =~ /\.(?:$type)$/) {
+ push(@files, $path);
+ }
+ elsif ( $copy_other_files ) {
+ copy($path, $new_path)
+ or croak "Failed to copy $path to $new_path: $!";
+ }
+ }
+ elsif ( -d $path ) {
+ (my $new_path = $path) =~ s/$tmpl_in_dir/$tmpl_out_dir/;
+ $new_path = "$KOHA_ROOT/$new_path" unless ( $new_path =~ m/^$KOHA_ROOT/ );
+ if ( ! -d $new_path ) {
+ mkdir($new_path) #, '0755'
+ or croak "Failed to create " . $new_path ." directory: $!";
+ }
+ my @sub_files = mirror_template_dir_structure_return_files($path, $type);
+ push(@files, @sub_files) if ( scalar(@sub_files) );
+ }
+ }
+ } else {
+ warn("Cannot open $dir: $! ... skipping");
+ }
+
+ return @files;
+}