Миграция с JSF 1.2 на JSF 2.0

Я работаю с довольно большим приложением, написанным в JSF 1.2. JSF 1.2 составляет около 6 лет. Мне нужно перейти на JSF 2.0. Как это будет болезненно? Я заметил, что некоторые атрибуты в пользовательских тегах были изменены и т.д.

Ответы

Ответ 1

Болезненность

Болезненность обновления JSF 1.2 до 2.0 зависит от технологии просмотра, которую вы в настоящее время используете и которую хотите использовать.

  • JSP 2.x - JSP 2.x = Почти без усилий.
  • Facelets 1.x to Facelets 2.0 = Маленькие усилия.
  • JSP 2.x to Facelets 2.0 = Много усилий. Двойное это, если у вас также есть пользовательские компоненты.

Основные изменения

Независимо от переключателя технологии просмотра, необходимо выполнить следующие шаги:

  • Удалите JSF 1.2 JAR из /WEB-INF/lib (если есть).
  • Drop JSF 2.0 JAR в /WEB-INF/lib (если JSF 1.2 был предоставлен сервлетконтейнером, вам может потребоваться изменить политику загрузки классов для загрузки библиотек webapp перед библиотеками сервлетконтейнеров, см. также JSF2 проблемы с загрузкой на серверах приложений).
  • Обновить объявление корня faces-config.xml для соответствия спецификации JSF 2.0.

    <faces-config
        xmlns="http://java.sun.com/xml/ns/javaee"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-facesconfig_2_0.xsd"
        version="2.0">
    
  • Убедитесь, что корневое объявление web.xml уже соответствует хотя бы Servlet 2.5. JSF 2.0 не будет работать на 2,4 или ниже (хотя он взламывается).

    <web-app 
        xmlns="http://java.sun.com/xml/ns/javaee"
        xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
        xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
        id="YourWebappID"
        version="2.5">
    

JSP 2.x в JSP 2.x

Если вы используете JSP 2.x и хотите, чтобы сохранить, используя это, вам больше не нужно ничего менять.

Постепенное обновление

Если вы уже используете суффикс url-pattern для FacesServlet, например *.jsf, тогда хорошо знать, что FacesServlet сначала сканирует файл *.xhtml, а если его нет, затем сканируйте файл *.jsp. Это дает вам возможность постепенно конвертировать из JSP в Facelets за кулисами, не изменяя URL.

Но если вы используете префикс url-pattern, например /faces/*, и вы хотите постепенно обновлять его с JSP до Facelets, вам действительно нужно изменить его на *.jsf и, возможно, также все ссылки в существующем JSP страницы.

Вам нужно только помнить, что новый JSF 2.0, обеспечивающий неявную навигацию, не проверяет наличие файла, в любом случае он будет outcome.xhtml. Поэтому, если вы хотите перейти или перейти на *.jsp, вам все равно нужно включить его в viewid для JSF 1.x.


Facelets 1.x to Facelets 2.0

Если вы используете Facelets 1.x в качестве технологии просмотра и хотите использовать поставляемый JSF 2.0 Facelets 2.0, вам необходимо выполнить следующие дополнительные действия:

  • Удалить флажки 1.x JAR из /WEB-INF/lib.
  • Снимите флажки 1.x FaceletViewHandler с faces-config.xml.
  • Любая пользовательская реализация FaceletViewHandler должна быть обновлена, чтобы вместо ViewHandlerWrapper.
  • Не нужно, но только для очистки удалите любые связанные с Facelets 1.x значения <context-param> из web.xml, которые по умолчанию установлены в Facelets 2.0, например javax.faces.DEFAULT_SUFFIX со значением *.xhtml.
  • Обновить корневую декларацию существующего XML файла Facelet taglib для соответствия Facelets 2.0.

    <facelet-taglib 
        xmlns="http://java.sun.com/xml/ns/javaee"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-facelettaglibrary_2_0.xsd"
        version="2.0">
    

Это должно быть в основном.


JSP 2.x to Facelets 2.0

Если вы используете JSP 2.x в качестве технологии просмотра и хотите немедленно перейти на Facelets 2.0, то вам нужно сделать много изменений до сайт может жить. Вы в основном меняете технологию просмотра здесь.

Изменение главной страницы

На каждой главной странице вам необходимо изменить следующий базовый шаблон JSP.

<%@page contentType="text/html" pageEncoding="UTF-8"%>
<%@taglib prefix="f" uri="http://java.sun.com/jsf/core"%>
<%@taglib prefix="h" uri="http://java.sun.com/jsf/html"%>
<!DOCTYPE html>
<f:view>
    <html lang="en">
        <head>
            <title>JSP page</title>
        </head>
        <body>
            <h:outputText value="JSF components here." />
        </body>
    </html>
</f:view>

.. к следующему базовому шаблону Facelets:

<!DOCTYPE html>
<html lang="en"
    xmlns="http://www.w3.org/1999/xhtml"
    xmlns:f="http://java.sun.com/jsf/core"
    xmlns:h="http://java.sun.com/jsf/html"
    xmlns:ui="http://java.sun.com/jsf/facelets">
    <h:head>
        <title>XHTML page</title>
    </h:head>
    <h:body>
        <h:outputText value="JSF components here." />
    </h:body>  
</html>

Включить изменения страницы

Если ваши существующие JSP-страницы хорошо разработаны, вы не должны иметь строку кода сценария, и вы должны также иметь только <jsp:include> в качестве единственного JSP-специфического тега. Любую из них нужно изменить:

<jsp:include page="include.jsp" />

к

<ui:include src="include.xhtml" />

В базовый JSP включен шаблон страницы..

<%@page contentType="text/html" pageEncoding="UTF-8"%>
<%@taglib prefix="f" uri="http://java.sun.com/jsf/core"%>
<%@taglib prefix="h" uri="http://java.sun.com/jsf/html"%>
<f:subview id="include">
    <h:outputText value="JSF components here." />
</f:subview>

.. следует изменить на следующие основные шаблоны Facelets:

<ui:composition
    xmlns="http://www.w3.org/1999/xhtml"
    xmlns:f="http://java.sun.com/jsf/core"
    xmlns:h="http://java.sun.com/jsf/html"
    xmlns:ui="http://java.sun.com/jsf/facelets">
    <h:outputText value="JSF components here." />
</ui:composition>

Пользовательские изменения компонентов

Вам нужно изменить файлы TLD JSP на файлы TLD Facelets, как описано в этом Руководство по миграции Mojarra.


Aftermath

Независимо от подхода к миграции вы можете постепенно исключить faces-config.xml новыми аннотациями JSF 2.0. Любой <managed-bean> может быть аннотирован @ManagedBean:

@ManagedBean(name="managedBeanName")
@RequestScoped
public class SomeBean {}

Рядом с @RequestScoped есть также @ViewScoped, @SessionScoped и @ApplicationScopedдоступный. Если вы опускаете атрибут name @ManagedBean, то по умолчанию будет присвоено имя класса с 1-м char нижним регистром.

@ManagedBean
@RequestScoped
public class SomeBean {}

В этом конкретном примере это будет #{someBean}.

Любые <managed-property> могут быть аннотированы с помощью @ManagedProperty:

@ManagedProperty("#{otherBean}")
private OtherBean otherBean;

Любые <validator> могут быть аннотированы с помощью @FacesValidator:

@FacesValidator("someValidator")
public class SomeValidator implements Validator {}

Любые <converter> могут быть аннотированы с помощью @FacesConverter

@FacesConverter("someConverter")
public class SomeConverter implements Converter {}

Любой <renderer> может быть аннотирован с помощью @FacesRenderer

@FacesRenderer(componentFamily="someComponentFamily", rendererType="someRendererType")
public class SomeRenderer extends Renderer {}

Любой <navigation-case>, который использует имя файла на странице XHTML, так как оба <from-outcome> и <to-view-id> могут быть удалены, так как это будет неявно сделано. Это можно сделать постепенно, изменив все исходные значения в соответствии с именем файла целевого представления.

Наконец, любой сеансовый охват bean, который был помещен в сеанс с единственной причиной сохранения данных bean в последующих запросах в одной и той же вкладке/окне, может быть лучше отмечен @ViewScoped, так как bean не будет затронута, когда конечный пользователь откроет одну и ту же страницу в разных вкладках/окнах.


Библиотеки компонентов

Обратите внимание, что я не принимаю во внимание в этом ответе какие-либо сторонние библиотеки компонентов, такие как PrimeFaces/RichFaces/IceFaces, тогда было бы невозможно написать надежный ответ, поскольку он в основном сводится к "это зависит". В общем случае достаточно просто обновить библиотеку компонентов до версии, совместимой с JSF 2.0, в соответствии с их инструкциями. Лучше всего просто написать модульные тесты, запустить их до и после обновления и исправить любые проблемы по отдельности.

Вот, по крайней мере, некоторые полезные ссылки в отношении миграции библиотеки конкретных компонентов:

В PrimeFaces нет руководства по миграции для PrimeFaces 1.x до 2.x, поскольку PrimeFaces 1.x уже требует Facelets 1.x, поэтому вам нужно просто следить за шагами миграции Facelets 1.x до 2.x. Тем не менее, есть приложение PrimeFaces 2.x to 3.x, которое также может применяться при переходе с PrimeFaces 1.x на 3.x. В Tomahawk также нет руководства по миграции. В основном единственное, что вам нужно изменить, это JAR и, если необходимо, избавиться от всех ссылок <t:saveState> в области с привязкой к запросу bean, создав область просмотра bean.

Ответ 3

web.xml

 Add the jars
    1. jsf-api-2.0.jar 
    2. jsf-impl.2.0.2.jar

Шаг 1: Измените web.xml

<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
            xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
            xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
            id="WebApp_ID" version="2.5">


    <servlet>
            <servlet-name>facesServlet</servlet-name>
            <servlet-class>javax.faces.webapp.FacesServlet</servlet-class>
            <load-on-startup>1</load-on-startup>
        </servlet>

        <servlet-mapping>
            <servlet-name>facesServlet</servlet-name>
            <url-pattern>/faces/*</url-pattern>
        </servlet-mapping>
        <servlet-mapping>

            <servlet-name>facesServlet</servlet-name>
            <url-pattern>*.jsf</url-pattern>
        </servlet-mapping>

        <servlet-mapping>
            <servlet-name>facesServlet</servlet-name>
            <url-pattern>*.faces</url-pattern>
        </servlet-mapping>

        <servlet-mapping>
            <servlet-name>facesServlet</servlet-name>
        <url-pattern>*.xhtml</url-pattern>
        </servlet-mapping>

Шаг 2: webmvc-config.xml

<!-- Handles requests mapped to the Spring Web Flow system -->
    <bean id="flowController" class="org.springframework.webflow.mvc.servlet.FlowController">
        <property name="flowExecutor" ref="flowExecutor" />
        <property name="ajaxHandler">
            <bean class="org.springframework.faces.webflow.JsfAjaxHandler" />
        </property>
</bean>

Шаг 3: facess-config.xml

<faces-config xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-facesconfig_2_0.xsd" version="2.0">

Ответ 4

JSF 2.0 имеет много новых функций и компонентов, и я не чувствую, что миграция будет болезненной. Только область, которую вы найдете трудной, - это использование сторонних библиотек. Если ваше приложение сильно зависит от таких библиотек, как Richfaces, вы столкнетесь с проблемой. Не все компоненты из Richfaces 3 портированы в Richfaces 4.

Это также может помочь Перенос приложений JSF 1.2 в JSF 2.0

Также проверьте это Что нового в JSF 2?

Ответ 5

Если вы используете Apache Trinidad, вам также придется обновить его до версии 2.0, чтобы он поддерживал JSF 2.0. Там больше информации на Hacker Valhalla.