Note that there's quick draft of TemplateResolver committed in the "3" branch: https://github.com/apache/incubator-freemarker/blob/3/src/main/java/org/apache/freemarker/core/templateresolver/TemplateResolver.java
It's not integrated with the other parts of FM (it's assumed everywhere that we have a DefaultTemplateResolver, not a generic TemplateResolver), nor does it deal with the configuration aspects discussed today. But it shows an idea for the main functionality. Tuesday, February 7, 2017, 11:59:08 AM, Daniel Dekany wrote: > Tuesday, February 7, 2017, 7:40:18 AM, David E Jones wrote: > >> On Tue, 2017-01-24 at 23:47 +0100, Daniel Dekany wrote: >>> >>> Should the TemplateResolver-s (the work name for the new interface) >>> still get the template name already resolved to absolute and >>> normalized? So when cfg.getTemplate is called, then it invokes >>> cfg.templateNameFormat.normalizeAbsoluteName(String) to normalize the >>> path, and only then it calls the TemplateResolver. Also #import and >>> such currently calls templateNameFormat.toAbsoluteName(String, >>> String), and that would happen earlier than TemplateResolver is >>> involved. >>> >>> And how would it look... perhaps like this: >>> >>> public interface TemplateResolver { >>> >>> Template getTemplate(String templatePath, Local lookupLocale, Object >>> customLookupCondition) >>> throws IOException; >>> >>> } >>> >>> You may notice that it misses the `encoding` and `parsed` parameter of >>> cfg.getTemplate. That's because I belive that in FM3 we should not >>> allow specifying those as getTemplate parameters anymore, but that >>> will be another thread when we get there. >> >> IMO it should pass through the exact text from the include/etc in >> the template. It might be worth constraining to a valid URI syntax >> but other than that a TemplateResolver would be much more flexible if no >> normalization/etc is done. > > In FM2 there's a class like this: > > public abstract class TemplateNameFormat { > ... > abstract String toAbsoluteName(String baseName, String > targetName) throws MalformedTemplateNameException; > abstract String normalizeAbsoluteName(String name) throws > MalformedTemplateNameException; > } > > My idea was that if we allow users to provide a custom implementation, > then if the standard rules don't fit your custom TemplateResolver, you > just create a custom TemplateNameFormat too. But now that I think > about it more, pushing the TemplateNameFormat functionality on the > TemplateResolver implementation does indeed look like a better > approach, because then it can't happen that a configuration > accidentally contains a TemplateResolver with a TemplateNameFormat > that doesn't work well with it. But then the above two methods should > be part of the TemplateResolver interface (because, for example, when > you #import something, FM has to find out if the same FTL was already > imported in the current Environment, so it needs to normalize the > #import argument without loading anything). WDYT? > >> Passing in the Locale rather than trying to call it multiple times >> with different locale extensions is a good idea too as different >> underlying content or file stores may have their own approach for >> this. > > That's even a problem with the TemplateLoader interface proposed to > FM3. Like in the recent database template loader thread, the author > wanted to use a separate column to indicate the locale of the template > (and the same could happen with custom lookup conditions too), so you > don't want to encode that information into the template name in the > case of that particular TemplateLoader. It's something we may try to > address in a second iteration of the FM3 TemplateLoader interface. > >> For example a JCR back end has quite a bit for meta data and >> content variations. >> >> In general more parameters and less built into the path/name is a good thing >> IMO. > > BTW, I still want to see if in FM3 the standard TemplateResolver (the > one that's basically FM2's TemplateCache, relies on TemplateLoader and > TemplateLookupStrategy and TemplateNameFormat) could cover more use > cases without becoming overly intricate. Also, even if you decide to > use a custom TemplateResolver, perhaps you still want to call some of > the stock TemplateLoader-s from it (while you replace the caching > logic, etc., or load from non-TemplateLoader sources too in case of > more sophisticated storages). I suspect you have experience with these > things, so it would be good if you can look at the FM3 TemplateLoader > thread. > >> -David > -- Thanks, Daniel Dekany