RejectedSoftware Forums

Sign up

Dynamic templates...again

Hi,
I'm trying to figure out how to use "dynamic" template names. "Dynamic" = "not known at compile time". Let's say, i have a database of documents, each have "title", "content" and "template" fields, where "template" is an actual Diet template filename (e.g. "article.dt"). I want to read template filename along with other data and feed it to render function.
I've tried the most straightforward way:

...
string tpl = readFromDB(docId);
res.render!(tpl, someParams);
...

However, I'm getting an error: "variable tpl cannot be read at compile time".
While I understand the reasons of this approach not to work, I can't find an elegant way of solving this. Is there any way to "prerender" a bunch of templates, to explicitly tell compiler what possible templates I'm going to use? Quick look at the docs gives me compileDietFile function, but I'm not sure I understand how it works.

Re: Dynamic templates...again

...disregard this. I'm just using mustached and it suits well for my needs.

Re: Dynamic templates...again

On Fri, 28 Aug 2015 14:45:12 GMT, tired_eyes wrote:

Hi,
I'm trying to figure out how to use "dynamic" template names. "Dynamic" = "not known at compile time". Let's say, i have a database of documents, each have "title", "content" and "template" fields, where "template" is an actual Diet template filename (e.g. "article.dt"). I want to read template filename along with other data and feed it to render function.
I've tried the most straightforward way:

...
string tpl = readFromDB(docId);
res.render!(tpl, someParams);
...

However, I'm getting an error: "variable tpl cannot be read at compile time".
While I understand the reasons of this approach not to work, I can't find an elegant way of solving this. Is there any way to "prerender" a bunch of templates, to explicitly tell compiler what possible templates I'm going to use? Quick look at the docs gives me compileDietFile function, but I'm not sure I understand how it works.

The solution here is to use dynamic dispatch (for which all existing template names must be known):

import std.typetuple;
alias template_names = TypeTuple!("templ1.dt", "templ2.dt");

string tpl = readFromDB(docId);
switch (tpl) {
    default: throw new Exception("Unknown template name for record");
    foreach (templ; template_names) {
        case templ:
            res.render!(templ, somParams);
            return;
    }
}

The foreach within the switch is just a neat trick to avoid writing redundant code for each template name. Beware of the use of return instead of break - the latter would just break out of the foreach loop instead of the switch block.