Mihai Bazon wrote:
 > So again, I must ask.. why can't we just have this basic functionality
 > in the core,

We can.  But it'll be in TT3, not TT2, as part of a total overhaul of the
way the template paths work.  Here's a brief outline.

For starters, relative paths will resolve relative to the current template
path:

    [% INCLUDE ./header %]       # header in the same directory
    [% INCLUDE ../header %]      # header in the parent directory
    [% INCLUDE ../../header %]   # and so on

Absolute paths will resolve relative to the INCLUDE_PATH (which will be called
template_path in TT3). So the "root" template directory is effectively a
virtual directory mapped to the real directories (or other provider sources)
in the template_path.

    [% INCLUDE /header %]        # header in one of the template_path dirs

The template_path directories set a hard limit, so that you can only access
files "below" them.  No sneaky ..ing up above the root like this:

    [% INCLUDE /../../../../../etc/passwd %]   # close, but no cigar

If you want the TT2 behaviour of ABSOLUTE_PATHS (which lets you load any file
in the filesystem), then you just need to add '/' to your template_path. This
will be the default if you don't explicitly set a template_path, so that
things like this Just Work[tm]:

     use Template;
     print Template->process('/absolute/path/to/template', { pi => 3.14 });

As well as relative and absolute paths (that work properly) there's walkup
paths and walkdown paths.  These walk from the current directory up, or from
the template_path directories down, respectively, until the template is found:

    [% INCLUDE .../header %]     # walk up directories to root
    [% INCLUDE /.../header %]    # walk down directories from root

So from the /foo/bar/baz template (relative to template_path), .../header will
give you the first of /foo/bar/header, /foo/header or /header that it finds,
and /.../header will give you the first of /header, /foo/header or
/foo/bar/header.

If you don't specify any absolute (/) or relative (./ or ../) prefix on the
path then you'll get the default behaviour which you can set to be any of the
above. The _default_ default behaviour will be to do what TT2 does and assume
an implicit '/' on the front. So:

    [% INCLUDE header %]   ===   [% INCLUDE /header %]

But you could set it to do an implicit relative/walkup/walkdown if you prefer.

    [% INCLUDE header %]   ===   [% INCLUDE ./header %]    # default: relative
    [% INCLUDE header %]   ===   [% INCLUDE .../header %]  # default: walkup
    [% INCLUDE header %]   ===   [% INCLUDE /.../header %] # default: walkdown

(NOTE: the situation is slightly complicated by BLOCK definitions but I'll
save that for another day).

So to recap, there will be ways to explicitly use templates in local
directories (or those relative to the local directory), and you'll also
be able to tweak the configuration so that this happens automatically,
if that's what you want.

On top of all that, TT3 will provide a generic namespace mechanism that allows
you to define your own strategies for fetching things, be they templates,
files, images, database records, or whatever.

The implicit namespace for the INCLUDE and related directives will be
'template:'.  So these are equivalent:

     [% INCLUDE header %]   ===  [% INCLUDE template:header %]
     [% INCLUDE /header %]  ===  [% INCLUDE template:/header %]
     [% INCLUDE ./header %] ===  [% INCLUDE template:./header %]

The 'template:' namespace, whether it's there explicitly or defined
implicitly by context (i.e. coming after the INCLUDE keyword), tells
TT to look for the template in one of the template_path directories
(there's a bit more to it than that, but I'll spare you the details).

You'll also be able to define your own namespaces and corresponding search
paths and search strategies. For example, you could define the "system:"
namespace to map to a template provider that looks in one particular location
for templates. Meanwhile the "user:" namespace might map to a provider that
looks in a local directory first, then a user-specific directory, before
falling back on the system templates directory. Or whatever.

The end result is that all that messy path searching logic can be hidden
away behind a simple prefix:

    [% INCLUDE header %]              # implicit template: namespace
    [% INCLUDE template:header %]     # explicit template: namespace
    [% INCLUDE system:header %]       # custom template search path #1
    [% INCLUDE user:header %]         # custom template search path #2

There's a basic implementation of that hidden away in TT2.  It's not
documented (very well, if at all), because it's still officially experimental.
But in TT3 it will be experimentally official.

There's a whole lot more interesting stuff that falls out of this addition
to TT, but I'll save that for another day.

Cheers
A



_______________________________________________
templates mailing list
[email protected]
http://mail.template-toolkit.org/mailman/listinfo/templates

Reply via email to