Struts2 + Freemarker + DisplayTag: как заставить это работать - PullRequest
0 голосов
/ 14 июля 2010

В настоящее время я обновляю наше приложение с Webwork до Struts2. Сегодня я столкнулся со странной ошибкой: displayTag перестал работать после обновления.

Это отрывок из моего файла FTL:

<#assign display=JspTaglibs["http://displaytag.sf.net"]>

<@s.set name="entries" value="historyEntries" scope="page"/>

<@display.table class="data" name="pageScope.entries" sort="list" 
      pagesize=30 id="entry" defaultsort=5 defaultorder="descending">
  <@display.column property="folderName" title="Folder" sortable=true/>
</@display.table>

Я получаю ошибку:

freemarker.template.TemplateModelException:   
javax.servlet.jsp.JspException: Exception:   
[.LookupUtil] Error looking up property "folderName" 
in object type "freemarker.template.SimpleSequence". 
Cause: Unknown property 'folderName'

Стандартные метки стоек работают правильно, в мою конфигурацию добавлено JspSupportServlet. Есть идеи, почему это не работает?

Ответы [ 2 ]

0 голосов
/ 07 мая 2016

Вы также можете подтвердить, что ваше развертывание копирует все зависимости в WEB-INF / lib.TaglibFactory выполняет поиск всех TLD в / META-INF / внутри jar.

Взгляните на https://stackoverflow.com/a/37092269/1113510

0 голосов
/ 15 июля 2010

Я нашел способ решить эту проблему (не уверен, что это единственный способ, или если он лучший, но у меня все получилось).

Корень проблемы заключался в том, что freemarker.template.SimpleSequence не осуществляет стандартную реализацию API коллекций, а не коллекцию, перечисление и т. Д.

Для решения этой проблемы я создал пользовательский FreemarkerManager и предоставил пользовательский BeansWrapper:

@Override
protected BeansWrapper getObjectWrapper() {
    BeansWrapper wrapper = super.getObjectWrapper();
    class CustomBeansWrapper extends BeansWrapper {
        private BeansWrapper internalWrapper;

        public Xp2BeansWrapper(BeansWrapper wrapper) {
            this.internalWrapper = wrapper;
        }

        //delegate methods


        public TemplateModel wrap(Object object) throws TemplateModelException {
            TemplateModel model = internalWrapper.wrap(object);
            if (model instanceof SimpleSequence) {
                class SimpleSequenceWithIterator extends SimpleSequence {
                    private SimpleSequence internalSequence;
                    public SimpleSequenceWithIterator(SimpleSequence sequence) {
                        this.internalSequence = sequence;
                    }

                    //delegate methods

                    //IteratorUtils from Apache Commons is used internally 
                    //by DisplayTag library, it can use public iterator() method
                    public Iterator iterator() throws TemplateModelException {
                        return toList().iterator();
                    }

                }
                return new SimpleSequenceWithIterator((SimpleSequence) model);
            }
            return model;
        }


    }
    return new CustomBeansWrapper(wrapper);

}

Теперь мне просто нужно изменить одну настройку в struts.properties:

struts.freemarker.manager.classname=xyz.CustomFreemarkerManager
...