-
-
31 Oct 2021 01:13:03 UTC
- Distribution: Text-Xslate
- Source (raw)
- Browse (raw)
- Changes
- Homepage
- How to Contribute
- Repository
- Issues (35)
- Testers
- Kwalitee
Bus factor: 6- License: perl_5
- Perl: v5.8.1
- Activity
24 month- Tools
- Download (211.29KB)
- MetaCPAN Explorer
- Permissions
- Subscribe to distribution
- Permalinks
- This version
- Latest version
and 38 contributors-
Fuji, Goro (gfx).
-
André Walker
-
Anirvan Chatterjee
-
Ashley Pond V
-
Brian Fraser
-
Christian Walde
-
David Steinbrunner
-
Fuji, Goro (gfx)
-
Fuji, Goro
-
Hao Wu
-
James E Keenan
-
Jesse Luehrs
-
Justin Cook
-
Kazuhiro Osawa
-
Kenichi Ishigaki
-
Kentaro Horio
-
Kevin M. Goess
-
Konstantin S. Uvarin
-
Mariano Wahlmann
-
Masahiro Chiba
-
Michael Kröll
-
Mike Raynham
-
Mons Anderson
-
Nick Morrott
-
Olaf Alders
-
Shigeki Morimoto
-
Syohei YOSHIDA
-
Tasuku SUENAGA a.k.a. gunyarakun
-
Tokuhiro Matsuno
-
Ueda Satoshi
-
Yoshiki Kurihara
-
c9s
-
hiratara
-
hitode909
-
lestrrat
-
makamaka
-
moznion
-
punytan
- NAME
- DESCRIPTION
- RECIPES
- How to manage HTML forms
- How to use Template Toolkit's WRAPPER feature in Kolon
- How to map __DATA__ sections to the include path
- How to interpolate data into JavaScript sections without XSS
- How to interpolate structured texts into HTML without XSS
- How to manage localization in templates
- How to load templates before fork()ing?
- SEE ALSO
NAME
Text::Xslate::Manual::Cookbook - How to cook Xslate templates
DESCRIPTION
The Xslate cookbook is a set of recipes showing Xslate features.
RECIPES
How to manage HTML forms
Managing HTML forms is an important issue for web applications. You're better off using modules that manage HTML forms rather than managing this yourself in your templates. This section proposes two basic solutions: using FillInForm and HTML form builders.
In both solutions, you should not use the
mark_raw
filter in templates, which easily creates security holes. Instead, application code should be responsible for calling themark_raw
function thatText::Xslate
can export.Using FillInForm
One solution to manage HTML forms is to use FillInForm modules with the block filter syntax.
Example code using
HTML::FillInForm
:#!perl -w use strict; use Text::Xslate qw(html_builder); use HTML::FillInForm; # HTML::FillInForm::Lite is okay sub fillinform { my($q) = @_; my $fif = HTML::FillInForm->new(); return html_builder { my($html) = @_; return $fif->fill(\$html, $q); }; } my $tx = Text::Xslate->new( function => { fillinform => \&fillinform, }, ); my %vars = ( q => { foo => "<filled value>" }, ); print $tx->render_string(<<'T', \%vars); FillInForm: : block form | fillinform($q) -> { <form> <input type="text" name="foo" /> </form> : } T
Output:
FillInForm: <form> <input type="text" name="foo" value="<filled value>" /> </form>
Because HTML::FillInForm::Lite provides a
fillinform
function, it becomes even simpler:use HTML::FillInForm::Lite qw(fillinform); my $tx = Text::Xslate->new( function => { fillinform => html_builder(\&fillinform) }, );
From 1.5018 on,
html_builder_module
is supported for HTML builder modules likeHTML::FillInForm
. Just import HTML builder functions withhtml_builder_module
option.my $tx = Text::Xslate->new( html_builder_module => [ 'HTML::FillInForm::Lite' => [qw(fillinform)] ], );
See also HTML::FillInForm or HTML::FillInForm::Lite for details.
Using HTML form builders
Another solution to manage HTML forms is to use form builders. In such cases, all you have to do is to apply
mark_raw()
to HTML parts.Here is a PSGI application that uses
HTML::Shakan
:#!psgi use strict; use warnings; use Text::Xslate qw(mark_raw); use HTML::Shakan; use Plack::Request; my $tx = Text::Xslate->new(); sub app { my($env) = @_; my $req = Plack::Request->new($env); my $shakan = HTML::Shakan->new( request => $req, fields => [ TextField(name => 'name', label => 'Your name: ') ], ); my $res = $req->new_response(200); # do mark_raw here, not in templates my $form = mark_raw($shakan->render()); $res->body( $tx->render_string(<<'T', { form => $form }) ); <!doctype html> <html> <head><title>Building form</title></head> <body> <form> <p> Form:<br /> <: $form :> </p> </body> </html> T return $res->finalize(); } return \&app;
Output:
<!doctype html> <html> <head><title>Building form</title></head> <body> <form> <p> Form:<br /> <label for="id_name">Your name</label> <input id="id_name" name="name" type="text" value="<Xslate>" /> </p> </body> </html>
See also HTML::Shakan for details.
How to use Template Toolkit's WRAPPER feature in Kolon
Use template cascading, which is a super-set of the
WRAPPER
directive.wrapper.tx:
<div class="wrapper"> block content -> { } </div>
content.tx
: cascade wrapper : override content -> { Hello, world! : }
Output:
<div class="wrapper"> Hello, world! </div>
Template cascading
Xslate supports template cascading, which allows you to extend templates with block modifiers. It is like traditional template inclusion, but is more powerful.
This mechanism is also called as template inheritance.
See also "Template cascading" in Text::Xslate.
How to map __DATA__ sections to the include path
Use
Data::Section::Simple
, and thepath
option ofnew()
, which accepts HASH references which contain$file_name => $content
mapping.use Text::Xslate; use Data::Section::Simple; my $vpath = Data::Section::Simple->new()->get_data_section(); my $tx = Text::Xslate->new( path => [$vpath], ); print $tx->render('child.tx'); __DATA__ @@ base.tx <html> <body><: block body -> { :>default body<: } :></body> </html> @@ child.tx : cascade base; : override body -> { child body : } # endblock body
This feature is directly inspired by Text::MicroTemplate::DataSection, and originated from Mojolicious.
See also Data::Section::Simple, Text::MicroTemplate::DataSection, and Mojolicious.
How to interpolate data into JavaScript sections without XSS
Because Xslate escapes only HTML meta characters, you must escape JavaScript meta characters by yourself when you put data into
<script> ... </script>
sections.The
JSON
module is not suitable because it doesn't escape some meta characters such as"</script>"
.It is better to use utilities proven to be secure for JavaScript escaping to avoid XSS. JavaScript::Value::Escape helps you in this regard.
my $tx = Text::Xslate->new( module => ['JavaScript::Value::Escape' => [qw(js)]], ); my %params = ( user_input => '</script><script>alert("XSS")</script>', ); print $tx->render_string(<<'T', \%params); <script> document.write('<: $user_input | html | js :>'); var user_input = '<: $user_input | js :>'; </script> T
You'd better to consult the security experts on more complex cases.
How to interpolate structured texts into HTML without XSS
There's no silver bullet to parse structured texts in secure ways. You'd better to consult the security experts to do so.
Some CPAN module might help you. See String::Filter for example.
How to manage localization in templates
You can register any functions including
_()
, so no specific techniques are required.For example:
use I18N::Handle; # I18N::Handle installs the locale function "_" to the global namespace. # (remember the symbol *_ is global) I18N::Handle->new( ... )->speak('zh_tw'); my $tx = Text::Xslate->new( function => { _ => \&_, }, );
Then in your templates:
<: _('Hello %1', $john ) :>
See also: I18N::Handle, App::I18N.
How to load templates before
fork()
ing?It is a good idea to load templates in preforking-model applications. Here is an example to load all the templates which is in a given path:
use File::Find; my $path = ...; my $tx = Text::Xslate->new( path => [$path], cache_dir => $path, ); # pre-load files find sub { if(/\.tx$/) { my $file = $File::Find::name; $file =~ s/\Q$path\E .//xsm; # fix path names $tx->load_file($file); } }, $path; # fork and render ...
SEE ALSO
Module Install Instructions
To install Text::Xslate, copy and paste the appropriate command in to your terminal.
cpanm Text::Xslate
perl -MCPAN -e shell install Text::Xslate
For more information on module installation, please visit the detailed CPAN module installation guide.