无法在Freemarker模板中读取对象值

3

我不能在Freemarker模板中读取scala/java对象的值。

我尝试了以下代码:

    case class ScheduleEmail(workOrderNo:String,
                             name:String,
                             woType:String,
                             numberOfAssets:String,
                              artisan:String,
                             dueDate:Date,priority:String)

    object ScheduleMailSending extends  App{
      val scheduleEmail1= List(ScheduleEmail("1", "Oil Change1", "WO", "3", "XYZ", Date.valueOf("2015-01-01"), "High"))
      val configaration = new Configuration
      configaration.setClassForTemplateLoading(this.getClass, "/")
      configaration.setObjectWrapper(new DefaultObjectWrapper())
      val data: util.HashMap[String, Object] = new util.HashMap[String, Object]
      val templet = configaration.getTemplate("schedule.ftl")
      data.put("mails",scheduleEmail1.asJava)
      val writer =new StringWriter()
     templet.process(data,writer)
      println("writer"+writer)
    }

我的模板是-
<#list mails as std>

    WorkOrderNo:${std.workOrderNo}
    woType:${std.woType}

</#l

我正在与这个错误进行斗争-

SEVERE: Error executing FreeMarker template
FreeMarker template error:
For "${...}" content: Expected a string or something automatically convertible to string (number, date or boolean), but this evaluated to a sequence+method (wrapper: f.e.b.SimpleMethodModel):
==> std.workOrderNo  [in template "schedule.ftl" at line 2, column 15]

The failing instruction (FTL stack trace):
----------
==> ${std.workOrderNo}  [in template "schedule.ftl" at line 2, column 13]
----------

Java stack trace (for programmers):

有人能帮助我解决这个问题吗?


我们可以在Twirl引擎中进行类似的模板化吗? - Kishorekumar Yakkala
1个回答

6

Scala在生成workOrderNo(以及BeanInfo)时不会产生getter方法,因此它不是一个JavaBean属性。但它确实生成了一个String workOrderNo()方法(虽然我对Scala已经生疏了,但错误消息也表明了这一点)。所以在模板中,您必须编写std.workOrderNo()。或者,您可以自定义ObjectWrapper以识别String workOrderNo()作为属性,通过setMethodAppearanceFineTuner(MethodAppearanceFineTuner)进行。如果您将使用Scala进行大量工作,则应该这样做。


在Freemarker 2.3.31中,即使进行了自定义,使用Scala时ObjectWrapper仍然无法正常工作。代码:val owb = new DefaultObjectWrapperBuilder(Configuration.VERSION_2_3_31) owb.setMethodAppearanceFineTuner(new MethodAppearanceFineTuner() { override def process(in: BeansWrapper.MethodAppearanceDecisionInput, out: BeansWrapper.MethodAppearanceDecision): Unit = { out.setReplaceExistingProperty(false); out.setMethodShadowsProperty(false) } }) freemarkerConfig.setObjectWrapper(owb.build) - Pravin Pundge
1
@PravinPundge,你需要在那里使用MethodAppearanceDecision.setExposeAsProperty(PropertyDescriptor)。另请参阅freemarker.ext.beans.MethodAppearanceFineTuner.process的Javadoc。 - ddekany

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接