JSF SelectItems и экранирование (xss)

в моем примере есть selectOneMenu с атрибутом f: selectItems. Элементы select разрешены из моего bean следующим образом:

<h:selectOneMenu value="#{bean.value}">
    <f:selectItems value="#{bean.selectItems}" var="obj" itemValue="#{obj}" itemLabel="#{obj.name}"/>
</h:selectOneMenu>

Метод getSelectItems() в моем bean выглядит следующим образом:

    public List<MyObject> getSelectItems() {
        List<MyObject> list = new LinkedList<MyObject>();

        MyObject obj = new MyObject("Peter");
        list.add(obj);

        return list;
    }

Объекты, которые отображаются, являются простыми объектами с атрибутом "имя".

Ничего особенного до этого момента. Но теперь я меняю свой метод на это:

 public List<MyObject> getSelectItems() {
        List<MyObject> list = new LinkedList<MyObject>();

        MyObject obj = new MyObject("<script>alert('xss is bad');</script>");
        list.add(obj);

        return list;
    }

javascript не экранируется MenuRenderer-Class, и моя страница показывает мне сообщение-предупреждение.

Есть ли причина, по которой значение по умолчанию для escape-атрибута SelectItem является "false"? Как я могу исправить эту проблему? (Я использую Mojarra 2.1.7)

Ответы

Ответ 1

По умолчанию действительно не было false. Я сообщил об этом как issue 2747.

В то же время добавьте itemLabelEscaped="true", чтобы избежать его.

<f:selectItems ... itemLabelEscaped="true" />

Обратите внимание, что это необходимо только при использовании GenericObjectSelectItems, т.е. при поставке E[]/List<E>/Map<K, V> вместо List<SelectItem>/SelectItem[]. Также обратите внимание, что экранирование является абсолютно обязательным, если оно относится к управляемому пользователем вводу (что, к счастью, очень редко относится к значениям выпадающего списка).