今天在学习FreeMarker的import的时候突然间出现了一下面这样的错误:
Error reading imported file lib/my_test.ftl
The problematic instruction:
----------
==> import '/lib/my_test.ftl' as my [on line 135, column 1 in demo1.ftl]
----------
Java backtrace for programmers:
----------
freemarker.template.TemplateException: Error reading imported file lib/my_test.ftl
at freemarker.core.LibraryLoad.accept(LibraryLoad.java:122)
at freemarker.core.Environment.visit(Environment.java:210)
at freemarker.core.MixedContent.accept(MixedContent.java:92)
at freemarker.core.Environment.visit(Environment.java:210)
at freemarker.core.Environment.process(Environment.java:190)
at freemarker.template.Template.process(Template.java:237)
at com.zhl.freemar.test.TestValue.testFreeMarker(TestValue.java:59)
at com.zhl.freemar.test.TestValue.main(TestValue.java:64)
Caused by: java.io.FileNotFoundException: Template lib/my_test.ftl not found.
at freemarker.template.Configuration.getTemplate(Configuration.java:489)
at freemarker.core.Environment.getTemplateForInclusion(Environment.java:1465)
at freemarker.core.Environment.getTemplateForImporting(Environment.java:1519)
at freemarker.core.LibraryLoad.accept(LibraryLoad.java:112)
... 7 more
开始我很是不解,很像知道FreeMarker在加载导入模板的时候是怎样确定其路径的,根据报错信息翻看了下源码:
下面是LibraryLoad类的构造函数和accept方法的源码
LibraryLoad(Template template,
Expression templateName,
String namespace)
{
this.namespace = namespace;
String templatePath1 = template.getName();
int lastSlash = templatePath1.lastIndexOf('/');
templatePath = lastSlash == -1 ? "" : templatePath1.substring(0, lastSlash + 1);
this.templateName = templateName;
}
void accept(Environment env) throws TemplateException, IOException {
String templateNameString = templateName.getStringValue(env);
if( templateNameString == null ) {
String msg = "Error " + getStartLocation()
+ "The expression " + templateName + " is undefined.";
throw new InvalidReferenceException(msg, env);
}
Template importedTemplate;
try {
if(!env.isClassicCompatible()) {
if (templateNameString.indexOf("://") >0) {
;
}
else if(templateNameString.length() > 0 && templateNameString.charAt(0) == '/') {
int protIndex = templatePath.indexOf("://");
if (protIndex >0) {
templateNameString = templatePath.substring(0, protIndex + 2) + templateNameString;
} else {
templateNameString = templateNameString.substring(1);
}
}
else {
templateNameString = templatePath + templateNameString;
}
}
importedTemplate = env.getTemplateForImporting(templateNameString);
}
catch (ParseException pe) {
String msg = "Error parsing imported template "
+ templateNameString;
throw new TemplateException(msg, pe, env);
}
catch (IOException ioe) {
String msg = "Error reading imported file "
+ templateNameString;
throw new TemplateException(msg, ioe, env);
}
env.importLib(importedTemplate, namespace);
}
关于模板的加载一定要看几句代码:
LibraryLoad(Template template,
Expression templateName,
String namespace)
{
//获取<#import>所在模板的名称
String templatePath1 = template.getName();
int lastSlash = templatePath1.lastIndexOf('/');
//获取<#import>所在模板的名称的路径
templatePath = lastSlash == -1 ? "" : templatePath1.substring(0, lastSlash + 1);
//<#import >中的表达式,也就是另外一个模板的路径
this.templateName = templateName;
}
然后在看accept中的代码,主要是几个if条件的判断,它们分别代表集中不同了路径的加载方式:
1、
if (templateNameString.indexOf("://") >0) {
;
}
这一种是绝对路径的书写格式,不做任何处理,后面直接执行
env.getTemplateForImporting(templateNameString);
2、
if(templateNameString.length() > 0 && templateNameString.charAt(0) == '/') {
int protIndex = templatePath.indexOf("://");
if (protIndex >0) {
templateNameString = templatePath.substring(0, protIndex + 2) + templateNameString;
} else {
templateNameString = templateNameString.substring(1);
}
}
这一种是表达式以"/"开头的情况,表示是加载在该模板下的文件夹中的模板
如:a.ftl中:<#import "/c/b.ftl" as kk>b.ftl和a.ftl是同级的,都在c文件夹下
3、最后一个else表示通模板在该模板的下一级文件中:
templateNameString = templatePath + templateNameString;
如:a.ftl中:<#import "c/b.ftl" as kk>表示c文件夹和a.ftl同级,b.ftl在c文件夹中
分享到:
相关推荐
Freemarker是一款强大的模板引擎,常...通过详细研读这份教程,开发者不仅可以掌握Freemarker的基本使用,还能深入理解其高级特性和优化技巧,从而在实际工作中更高效地生成静态文件,提升Web应用的性能和用户体验。
通过阅读和理解FreeMarker 2.3.23的官方中文文档,开发者能够熟练掌握FreeMarker的使用技巧,从而在Web应用开发中更加高效地创建和管理动态内容。这份文档详尽地涵盖了FreeMarker的各个方面,无论是初学者还是经验...
FreeMarker中文手册中会详细解释这些概念和语法,并提供丰富的示例帮助理解和应用。通过深入阅读和实践,你可以掌握FreeMarker的使用,从而更高效地构建动态网页和邮件模板等。同时,理解FreeMarker如何与Spring、...
3. **指令**:如`<#include>`用于包含其他模板,`<#import>`引入宏库,`<#function>`定义函数等,它们扩展了FreeMarker的功能。 4. **数据模型**:FreeMarker通过一个称为“Environment”的上下文对象与Java代码...
这个“freemarker中文学习资料”压缩包提供了详尽的网页版API文档,对于想要深入理解和掌握Freemarker的开发者来说,是一份非常宝贵的资源。 1. **Freemarker基础概念** - **模板语言**:Freemarker使用一种简单的...
Freemarker是一个强大的模板引擎,常用于JavaEE应用中的视图层处理,尤其与Struts2等MVC框架配合使用,能实现灵活的动态页面...在学习过程中,可以逐步尝试不同的表达式、控制结构和内置功能,加深对Freemarker的理解。
通过阅读《freemarker 中文手册》(doc),你可以深入理解上述概念,并学习如何在实际项目中有效地使用Freemarker。手册会详细介绍每个功能的用法,包括示例和注意事项,是学习和查阅Freemarker的宝贵资源。
Freemarker是一个强大的模板引擎,常用于Web应用中的视图层渲染,比如JavaEE的Struts、Spring MVC等框架。它的主要任务是将数据模型与HTML或其他格式的模板结合,生成最终用户可见的动态内容。这个“freemarker 中文...
对于深入理解Freemarker的工作原理,阅读源码是有帮助的。Freemarker的解析、编译、执行过程涉及多个组件,如`Template`、`TemplateModel`、`TemplateParser`等,它们协同工作以生成最终输出。 总结,Freemarker...
通过阅读这份中文手册,开发者可以掌握FreeMarker的使用方法,理解其核心概念,并学会如何在实际项目中有效利用FreeMarker实现高效、安全的动态页面生成。在Web开发中,熟练运用FreeMarker可以极大地提升开发效率和...
"freemarker中文手册"为中文用户提供了方便,它翻译了官方文档的主要内容,使得国内开发者能够更轻松地学习和理解FreeMarker的各项功能。 **8. 学习资源** FreeMarker的官方文档和这两份手册是学习FreeMarker的基础...
Freemarker是一个强大的模板引擎,主要用于生成动态HTML、XML或其他文本格式的文件,广泛...在"freemarker2.3.28"这个压缩包中,可能包含了Freemarker的完整源代码、文档、示例和其他相关资源,便于深入理解和自定义。
2. **数据模型**:理解如何将Java对象映射到Freemarker的数据模型,包括如何设置和访问对象属性,以及使用List、Map等复杂数据结构。 3. **指令**:深入讲解Freemarker的各种指令,如`<#include>`用于导入其他模板...
这份“freemarker官方中文帮助文档”提供了详尽的指南,帮助用户深入理解和使用Freemarker。 在《FreeMarker Manual(zh_CN)》中,你可能会了解到以下关键知识点: 1. **基础概念**:Freemarker的核心概念包括...
在"FreeMarker手册.pdf"中,你将找到关于这些概念的详细解释、示例代码和最佳实践,对于深入理解和使用FreeMarker是非常有价值的资源。无论你是初学者还是经验丰富的开发者,这本手册都能为你提供必要的指导和支持。
- **4.6 在Servlet中使用FreeMarker**:提供了在Servlet环境中使用FreeMarker的具体步骤。 - **4.7 为FreeMarker配置安全策略**:介绍了如何增强FreeMarker的安全性。 - **4.8 遗留的XML包装实现**:讨论了旧版XML...
Freemarker是一个强大的、开源的模板引擎,常用于Java Web应用中的视图层技术,它允许开发者使用简单的标记语言(Markup Language)来控制显示逻辑,而无需深入理解HTML或者其他前端技术。这个“freemarker-2.3.23-...
通过阅读《FreeMarker 2.3.19手册—中文版》PDF,你可以深入理解这个模板引擎的工作原理,学会如何有效地利用它来创建动态页面,提高你的Web开发效率。这份文档详细且全面,是FreeMarker初学者和进阶者不可或缺的...
通过这个简单的示例,你应该能理解如何在Spring Boot中有效地使用Freemarker进行模板渲染。这只是一个基础的示例,实际上,Freemarker支持更复杂的逻辑和控制结构,能够满足你在实际开发中的各种需求。
这个中文手册和教程全面覆盖了Freemarker的各个方面,无论你是初学者还是经验丰富的开发者,都能从中找到所需的知识点,加深对Freemarker的理解,提升开发效率。通过阅读《Freemarker教程_中文版.docx》和...