Перенос старого JSP в Facelet (управляемый компонент не создан)
Я использую устаревший код JSP-скриплета и решил попробовать Facelets и перенести мое приложение. Мне уже не нравятся некоторые вещи (например, дополнительная работа по изменению некоторых тегов HTML5, которые дает мне дизайнер, закрытие их и т. Д.), Но преимущества, кажется, того стоят. Я нахожу некоторые проблемы в миграции, в основном я пытаюсь определить composite component
и пройти через List<T extends BasicData>
быть отображенным.
я использую Netbeans 8.0.2
, Apache Tomcat 8.0.3.0
(J2EE 7), JDK 1.8
, Я читаю Java Server Faces - Введение за примером, чтобы получить помощь и примеры.
1) Я не уверен, что включил правильные зависимости в Maven, или я включил дублированные функциональные возможности с библиотеками. Это минимальный набор? (учитывая, что я мог бы использовать JSTL)
<dependencies>
<dependency>
<groupId>javax</groupId>
<artifactId>javaee-web-api</artifactId>
<version>7.0</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>javax.faces</groupId>
<artifactId>javax.faces-api</artifactId>
<version>2.2</version>
<scope>provided</scope>
</dependency>
<dependency>
<!-- This is the Mojarra Implementation of JSF -->
<groupId>org.glassfish</groupId>
<artifactId>javax.faces</artifactId>
<version>2.2.8-02</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>com.sun.faces</groupId>
<artifactId>jsf-api</artifactId>
<version>2.1.0-b03</version>
</dependency>
<dependency>
<groupId>com.sun.faces</groupId>
<artifactId>jsf-impl</artifactId>
<version>2.1.0-b03</version>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
<version>2.5</version>
</dependency>
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>jsp-api</artifactId>
<version>2.1</version>
</dependency>
<dependency>
<groupId>com.sun.el</groupId>
<artifactId>el-ri</artifactId>
<version>1.0</version>
</dependency>
2) Начиная с JSF 2.0, мне не нужен следующий фрагмент в web.xml
, Однако, когда я опускаю его, я не получаю рендеринг JSF и получаю только необработанный XML. Что я делаю неправильно?
<context-param>
<param-name>javax.faces.PROJECT_STAGE</param-name>
<param-value>Development</param-value>
</context-param>
<servlet>
<servlet-name>Faces Servlet</servlet-name>
<servlet-class>javax.faces.webapp.FacesServlet</servlet-class>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>/faces/*</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>*.jsf</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>*.faces</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>Faces Servlet</servlet-name>
<url-pattern>*.xhtml</url-pattern>
</servlet-mapping>
3) Теперь главная проблема в том, что мой бин, кажется, не создается. Все хорошо, кроме того, что бин передается всегда null
, На самом деле я могу передать любой тип данных (например, String
вместо List
) и никогда не жалуется (поскольку все, что я передаю, всегда null
и Netbeans, по-видимому, не обнаруживает его во время компиляции).
index.xhtml
<ui:composition xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:ui="http://xmlns.jcp.org/jsf/facelets"
xmlns:util="http://java.sun.com/jsf/composite/util"
template="template.xhtml">
<ui:define name="content">
<util:visualisationList
elementList="#{visualisationListController.elements}"/>
</ui:define>
</ui:composition>
visualisationListController.java
@Named(value = "visualisationListController")
@Dependent
public class VisualisationListController <T extends BasicData> implements Serializable {
private List<T> elements;
/**
* Creates a new instance of visualisationList
*/
public VisualisationListController() {
// This is for testing, eventually I would like to get this information from a DB
System.out.println("constructor");
elements = new ArrayList<>();
ComplexData cd = new ComplexData(); // ComplexData EXTENDS BasicData
cd.setName("ELEMENT 1");
elements.add((T)cd);
cd = new ComplexData();
cd.setName("ELEMENT 2");
elements.add((T)cd);
}
public List<T> getElements() {
return elements;
}
public void setElements(List<T> elements) {
this.elements = elements;
}
}
visualisationList.xhtml (Это рендеринг, но список null
так что ничего не печатается)
<!DOCTYPE html>
<html lang="en"
xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:cc="http://xmlns.jcp.org/jsf/composite"
xmlns:c="http://java.sun.com/jsp/jstl/core">
<!-- INTERFACE -->
<cc:interface>
<cc:attribute name="elementList" type="java.util.List" required="true" shortDescription="The list of objects to be displayed"/>
</cc:interface>
<!-- IMPLEMENTATION -->
<cc:implementation>
<ul>
<c:forEach items="#{cc.attrs.elementList}" var="element">
<li>
#{element.name}
</li>
</c:forEach>
</ul>
</cc:implementation>
</html>
Я никогда не читаю мне нужна beans.xml
как предложено здесь, и этот пост также не дает мне подсказки. Предполагается, что боб автоматически создается. Чтобы провести дальнейшее тестирование, я попробовал первый простой пример из вышеупомянутой книги, и мой bean-компонент также не создается. Из текста книги я понимаю, что объект должен быть автоматически создан.
В случае возникновения ошибки на пути лечения или создания List
Я также попытался использовать менее сложные данные (просто String
), используйте @SessionScoped
и удалите c:forEach
и это тоже не работает.
РЕДАКТИРОВАТЬ
Проблема исправлена благодаря (еще раз) BalusC
указатель. Мне приходилось получать информацию из разных источников, поэтому для удобства я собрал шаги, которые я предпринял ниже. Однако мой вопрос все еще неясен (1): согласно информационной странице JSF, мне нужно включить только одну зависимость Maven. Но при этом я получаю следующее сообщение об ошибке:
An Error Occurred:
Could not get component metadata for visualisationList.xhtml. Did you forget to specify <composite:interface>?
viewId=/index.xhtml
location= ...
Я попытался несколько вещей, в том числе шаги здесь, безуспешно. Если я включаю определенные библиотеки, я получаю:
javax.servlet.ServletException
javax.faces.webapp.FacesServlet.service(FacesServlet.java:606)
org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)
root cause
java.lang.NullPointerException
java.util.concurrent.ConcurrentHashMap.putVal(ConcurrentHashMap.java:1011)
java.util.concurrent.ConcurrentHashMap.putIfAbsent(ConcurrentHashMap.java:1535)
Единственное, что сработало для меня, хотя я не уверен, почему, это включить зависимость:
<dependency>
<groupId>org.glassfish</groupId>
<artifactId>javax.faces</artifactId>
<version>2.2.8-02</version>
<scope>runtime</scope>
</dependency>
(Вместе с javaee-web-api 6.0 конечно)
Только тогда я получаю результат, которого ожидал с самого начала. Тем не менее, я не понимаю, почему эта зависимость должна быть включена, если TomEE предполагалось предоставить все это. Кроме того, я не уверен, что это означает, что я буду использовать v.2.2, когда прочитал, что EE 6 должен работать только до 2.1. Наконец, мне пришлось создать beans.xml
чтобы это работало, и я не уверен почему - это только для версии JSF <= 2.1?
ШАГИ, КОТОРЫЕ Я СДЕЛАЛ, ЧТОБЫ ИЗМЕНИТЬ TOMCAT ДЛЯ TOMEE НА NETBEANS
- Скачать TomEE. Установите и настройте его в разделе серверов Netbeans. ( Источник)
- Отредактируйте TomEE server.xml и измените все порты, чтобы избежать столкновения с моим старым Tomcat.
В server.xml удалите
xpoweredBy
а такжеserver
атрибуты от коннектора:( Источник)
Затем в
bin/catalina.bat
менять::noJuliConfig set "JAVA_OPTS=%JAVA_OPTS% %LOGGING_CONFIG%" ... :noJuliManager set "JAVA_OPTS=%JAVA_OPTS% %LOGGING_MANAGER%"
чтобы:
:noJuliConfig set JAVA_OPTS=%JAVA_OPTS% %LOGGING_CONFIG% ... :noJuliManager set JAVA_OPTS=%JAVA_OPTS% %LOGGING_MANAGER%
( Источник)
Затем щелкните правой кнопкой мыши на проекте - Свойства - Выполнить. Измените сервер на TomEE и версию Java EE на "Java EE 6 Web" (поскольку текущая версия TomEE поддерживает только JEE 1.6). Зависимости в
pom.xml
должны быть изменены соответственно на версию 6:<dependency> <groupId>javax</groupId> <artifactId>javaee-web-api</artifactId> <version>6.0</version> <!-- 7.0 (JSF 2.2) or 6.0 (JSF 2.0/2.1) --> <scope>provided</scope> </dependency> .... <artifactItem> <groupId>javax</groupId> <artifactId>javaee-endorsed-api</artifactId> <version>6.0</version> <type>jar</type> </artifactItem>
....
Теперь TomEE должен работать и запускать приложение из Netbeans.