Средства разработки  web  приложений (Web frameworks) Малышкин Фёдор 2 ноября 2007
Содержание <ul><li>Введение </li></ul><ul><li>Основа архитектуры «тонких» клиентов </li></ul><ul><li>Средства разработки в...
Введение <ul><li>Данная презентация познакомит Вас с существующими библиотеками разработки веб-приложений на языке  Java. ...
Основа архитектуры «тонких» клиентов <ul><li>В качестве основы для всех клиентов, связанных с пользовательским вводом (не ...
Основа архитектуры «тонких» клиентов
JSP  (Краткая характеристика) <ul><li>Положительные стороны: </li></ul><ul><ul><li>? </li></ul></ul><ul><li>Отрицательные ...
JSP ( Жизненный цикл )
Struts  (Краткая характеристика) <ul><li>Положительные стороны: </li></ul><ul><ul><li>Много проектов реализованных с помощ...
Spring ( Краткая характеристика ) <ul><li>Положительные стороны: </li></ul><ul><ul><li>Переопределение правил связки данны...
Spring  (Жизненный цикл  GET)
Spring  (Жизненный цикл  POST)
«Контроллер»  Spring <ul><li>public class UserController implements Controller { </li></ul><ul><li>private final Log log =...
«Контроллер»  Spring <ul><li>public class UserController implements Controller { </li></ul><ul><li>private final Log log =...
Конфигурирование  Spring <ul><li><bean id=&quot;userController&quot; class=&quot;org.appfuse.web.UserController&quot;> </l...
Конфигурирование  Spring <ul><li><bean id=&quot;userController&quot; class=&quot;org.appfuse.web.UserController&quot;> </l...
Конфигурирование  Spring <ul><li><bean id=&quot;userController&quot; class=&quot;org.appfuse.web.UserController&quot;> </l...
JSP  представление  Spring <ul><li><form:form commandName=&quot;user&quot; method=&quot;post&quot;> </li></ul><ul><li><for...
JSP  представление  Spring <ul><li><form:form commandName=&quot;user&quot; method=&quot;post&quot;> </li></ul><ul><li><for...
Velocity  представление  Spring <ul><li><form method=&quot;post&quot; action=&quot;#springUrl('/editUser.html')&quot;> </l...
Spring Web Flow <ul><li>Инфраструктура позволяющая определять последовательность переходов между страницами </li></ul><ul>...
Spring Web Flow <ul><li><webflow id=&quot;userFlow&quot; start-state=&quot;setupForm&quot;> </li></ul><ul><li><action-stat...
Tapestry ( Краткая характеристика ) <ul><li>Положительные стороны: </li></ul><ul><ul><li>Очень эффективна после изучения <...
Tapestry ( Жизненный цикл )
Класс  Tapestry <ul><li>public abstract class UserForm extends BasePage { </li></ul><ul><li>public abstract UserManager ge...
Конфигурирование  Tapestry <ul><li><application name=&quot;tapestry&quot;> </li></ul><ul><li><page name=&quot;Home&quot; s...
Конфигурирование  Tapestry <ul><li><page-specification class=&quot;org.appfuse.web.UserForm&quot;> </li></ul><ul><li><bean...
HTML  представление  Tapestry <ul><li><form jwcid=&quot;@Form&quot; delegate=&quot;ognl:beans.delegate&quot; name=&quot;us...
HTML  представление  Tapestry <ul><li><form jwcid=&quot;@Form&quot; delegate=&quot;ognl:beans.delegate&quot; name=&quot;us...
HTML  представление  Tapestry <ul><li><form jwcid=&quot;@Form&quot; delegate=&quot;ognl:beans.delegate&quot; name=&quot;us...
Улучшения в следующей версии  Tapestry <ul><li>Богатая поддержка аннотаций </li></ul><ul><li>Высокий уровень конфигурирова...
JSF ( Краткая характеристика ) <ul><li>Положительные стороны: </li></ul><ul><ul><li>J2EE  Стандарт </li></ul></ul><ul><ul>...
JSF ( Жизненный цикл )
Бин страницы  JSF  <ul><li>public class UserForm { </li></ul><ul><li>private String id; </li></ul><ul><li>public User user...
Конфигурация  JSF  <ul><li><application> </li></ul><ul><li><variable-resolver> </li></ul><ul><li>org.springframework.web.j...
Конфигурация  JSF  <ul><li><application> </li></ul><ul><li><variable-resolver> </li></ul><ul><li>org.springframework.web.j...
Конфигурация  JSF  <ul><li><managed-bean> </li></ul><ul><li><managed-bean-name>userForm</managed-bean-name> </li></ul><ul>...
JSP  представление  JSF  <ul><li><f:view> </li></ul><ul><li><f:loadBundle var=&quot;messages&quot; basename=&quot;messages...
JSP  представление  JSF  <ul><li><f:view> </li></ul><ul><li><f:loadBundle var=&quot;messages&quot; basename=&quot;messages...
JSP  представление  JSF  <ul><li><f:view> </li></ul><ul><li><f:loadBundle var=&quot;messages&quot; basename=&quot;messages...
Улучшения в следующей версии  JSF  (1.2) <ul><li>Унифицированный  EL –  лучшая поддержка  JSTL </li></ul><ul><li>Фокусиров...
Сравнение .  Критерии <ul><li>Сортируемые / Листаемые списки  – насколько просто создать список данных с листаемыми страни...
Сравнение .  Критерии <ul><li>Интернационализация </li></ul><ul><li>Модификация «на лету»  - принятие исправлений без необ...
Сортируемые / Листаемые списки <ul><li>JSP –  никакой поддержки </li></ul><ul><li>Spring & Struts  могут использовать библ...
Возможность создания закладок <ul><li>JSP, String & Strut  имеют  полный  контроль над строкой запроса </li></ul><ul><li>T...
Валидация <ul><li>JSP –  «собственные» решения, либо перенос проверки в модель данных </li></ul><ul><li>String & Struts  и...
Тестируемость <ul><li>Struts –  необходимо использование  StrutsTestCase </li></ul><ul><li>JSP, Spring –  легко тестируетс...
Интернационализация <ul><li>JSTL <fmt:message>  позволяет делать это легко почти в любой реализации </li></ul><ul><li>JSP,...
Модификация «на лету» <ul><li>JSP –  самый гибкий в данном случае (конечно при корректном   использовании).  JSP  файлы пе...
Поддержка разработчиками <ul><li>JSP & JSF –  стандарт, большое сообщество разработчиков и множество документации </li></u...
Производительность  /  Масштабируемость <ul><li>JSP –  хорошие показатели, в связи с отсутствием каких-либо промежуточных ...
«Компонетность» <ul><li>JSP  – тэг-файлы и тэги. </li></ul><ul><li>Tapestry –  очень ориентированная на создание и использ...
Возможности языка выражений <ul><li>JSP, JSF, Spring, Struts –  богатые возможности  EL  говорят сами за себя. </li></ul><...
Финал <ul><li>Выбирайте с умом… </li></ul>
Upcoming SlideShare
Loading in …5
×

Средства разработки web приложений (Web frameworks)

4,312 views

Published on

Средства разработки web приложений
(Web frameworks)

Published in: Technology
0 Comments
1 Like
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total views
4,312
On SlideShare
0
From Embeds
0
Number of Embeds
31
Actions
Shares
0
Downloads
49
Comments
0
Likes
1
Embeds 0
No embeds

No notes for slide

Средства разработки web приложений (Web frameworks)

  1. 1. Средства разработки web приложений (Web frameworks) Малышкин Фёдор 2 ноября 2007
  2. 2. Содержание <ul><li>Введение </li></ul><ul><li>Основа архитектуры «тонких» клиентов </li></ul><ul><li>Средства разработки веб-приложений: </li></ul><ul><ul><li>JSP </li></ul></ul><ul><ul><li>Struts </li></ul></ul><ul><ul><li>Spring </li></ul></ul><ul><ul><li>Tapestry </li></ul></ul><ul><ul><li>JSF </li></ul></ul><ul><li>Сравнение </li></ul>
  3. 3. Введение <ul><li>Данная презентация познакомит Вас с существующими библиотеками разработки веб-приложений на языке Java. </li></ul><ul><li>Будут описаны основополагающие моменты, лежащие в их основе, приведены примеры их использования, описаны их преимущества и недостатки. </li></ul><ul><li>Так же будут описаны классические модели реализации «тонких» клиентов, коим веб-приложение и является. </li></ul>
  4. 4. Основа архитектуры «тонких» клиентов <ul><li>В качестве основы для всех клиентов, связанных с пользовательским вводом (не обязательно «тонких»), используется MVC (Model-View-Controller). </li></ul><ul><li>Эта архитектура разделяет приложение на: </li></ul><ul><ul><li>Модель данных ( Model ) , занимающуюся хранением данных, обработкой данных (бизнес - логикой), а так же всем остальными «не визуальными» вещами. </li></ul></ul><ul><ul><li>Представление ( View ), занимающуюся отображением и представлением данных </li></ul></ul><ul><ul><li>Контроллер ( Controller ), занимающийся коммуникацией между данными и представлением. </li></ul></ul><ul><li>В веб-приложениях данная модель называется « Model-2 » (что бы отделить от настольной реализации MVC ) и указать, на то что она является приемником « Model-1 » . </li></ul>
  5. 5. Основа архитектуры «тонких» клиентов
  6. 6. JSP (Краткая характеристика) <ul><li>Положительные стороны: </li></ul><ul><ul><li>? </li></ul></ul><ul><li>Отрицательные стороны: </li></ul><ul><ul><li>? </li></ul></ul>
  7. 7. JSP ( Жизненный цикл )
  8. 8. Struts (Краткая характеристика) <ul><li>Положительные стороны: </li></ul><ul><ul><li>Много проектов реализованных с помощью данной библиотеки, подтверждает её стабильность и надёжность </li></ul></ul><ul><ul><li>Огромное количество примеров и документации </li></ul></ul><ul><ul><li>HTML библиотека тэгов одна из лучших </li></ul></ul><ul><li>Отрицательные стороны: </li></ul><ul><ul><li>Программирование «контроллера» - ActionForms – задача не из лёгких </li></ul></ul><ul><ul><li>Невозможно автономное тестирование </li></ul></ul><ul><ul><li>Ходят слухи, что проект «мёртв» </li></ul></ul>
  9. 9. Spring ( Краткая характеристика ) <ul><li>Положительные стороны: </li></ul><ul><ul><li>Переопределение правил связки данных на форме и в приложении, правил навигации и проверки введённых значений </li></ul></ul><ul><ul><li>Прозрачная интеграция с многочисленными средствами представления данных: JSP/JSTL, Tiles, Velocity, FreeMaker, Excel, XSL, PDF. </li></ul></ul><ul><ul><li>Удобная среда для автономного тестирования </li></ul></ul><ul><li>Отрицательные стороны: </li></ul><ul><ul><li>Много XML (в области конфигурирования) </li></ul></ul><ul><ul><li>Требует большого количества кода в JSP </li></ul></ul><ul><ul><li>«Слишком» гибок </li></ul></ul>
  10. 10. Spring (Жизненный цикл GET)
  11. 11. Spring (Жизненный цикл POST)
  12. 12. «Контроллер» Spring <ul><li>public class UserController implements Controller { </li></ul><ul><li>private final Log log = LogFactory.getLog(UserController.class); </li></ul><ul><li>private UserManager mgr = null; </li></ul><ul><li>public void setUserManager(UserManager userManager) { </li></ul><ul><li>this.mgr = userManager; </li></ul><ul><li>} </li></ul><ul><li>public ModelAndView handleRequest(HttpServletRequest request, HttpServletResponse response) throws Exception { </li></ul><ul><li>if (log.isDebugEnabled()) { </li></ul><ul><li>log.debug(&quot;entering 'handleRequest' method...&quot;); </li></ul><ul><li>} </li></ul><ul><li>return new ModelAndView(&quot;userList&quot;, &quot;users&quot;, mgr.getUsers()); </li></ul><ul><li>} </li></ul><ul><li>} </li></ul>
  13. 13. «Контроллер» Spring <ul><li>public class UserController implements Controller { </li></ul><ul><li>private final Log log = LogFactory.getLog(UserController.class); </li></ul><ul><li>private UserManager mgr = null; </li></ul><ul><li>public void setUserManager(UserManager userManager) { </li></ul><ul><li>this.mgr = userManager; </li></ul><ul><li>} </li></ul><ul><li>public ModelAndView handleRequest(HttpServletRequest request, HttpServletResponse response) throws Exception { </li></ul><ul><li>if (log.isDebugEnabled()) { </li></ul><ul><li>log.debug(&quot;entering 'handleRequest' method...&quot;); </li></ul><ul><li>} </li></ul><ul><li>return new ModelAndView(&quot;userList&quot;, &quot;users&quot;, mgr.getUsers()); </li></ul><ul><li>} </li></ul><ul><li>} </li></ul>
  14. 14. Конфигурирование Spring <ul><li><bean id=&quot;userController&quot; class=&quot;org.appfuse.web.UserController&quot;> </li></ul><ul><li><property name=&quot;userManager&quot; ref=&quot;userManager&quot;/> </li></ul><ul><li></bean> </li></ul>
  15. 15. Конфигурирование Spring <ul><li><bean id=&quot;userController&quot; class=&quot;org.appfuse.web.UserController&quot;> </li></ul><ul><li><property name=&quot;userManager&quot; ref=&quot;userManager&quot;/> </li></ul><ul><li></bean> </li></ul><ul><li><bean id=&quot;viewResolver&quot; </li></ul><ul><li>class=&quot;org.springframework.web.servlet.view.InternalResourceViewResolver&quot;> </li></ul><ul><li><property name=&quot;viewClass&quot; value=&quot;org.springframework.web.servlet.view.JstlView&quot;/> </li></ul><ul><li><property name=&quot;prefix&quot; value=&quot;/&quot;/> </li></ul><ul><li><property name=&quot;suffix&quot; value=&quot;.jsp&quot;/> </li></ul><ul><li></bean> </li></ul>
  16. 16. Конфигурирование Spring <ul><li><bean id=&quot;userController&quot; class=&quot;org.appfuse.web.UserController&quot;> </li></ul><ul><li><property name=&quot;userManager&quot; ref=&quot;userManager&quot;/> </li></ul><ul><li></bean> </li></ul><ul><li><bean id=&quot;viewResolver&quot; </li></ul><ul><li>class=&quot;org.springframework.web.servlet.view.InternalResourceViewResolver&quot;> </li></ul><ul><li><property name=&quot;viewClass&quot; value=&quot;org.springframework.web.servlet.view.JstlView&quot;/> </li></ul><ul><li><property name=&quot;prefix&quot; value=&quot;/&quot;/> </li></ul><ul><li><property name=&quot;suffix&quot; value=&quot;.jsp&quot;/> </li></ul><ul><li></bean> </li></ul><ul><li><bean id=&quot;urlMapping&quot; </li></ul><ul><li>class=&quot;org.springframework.web.servlet.handler.SimpleUrlHandlerMapping&quot;> </li></ul><ul><li><property name=&quot;mappings&quot;> </li></ul><ul><li><value> </li></ul><ul><li>/users.html=userController </li></ul><ul><li></value> </li></ul><ul><li></property> </li></ul><ul><li></bean> </li></ul>
  17. 17. JSP представление Spring <ul><li><form:form commandName=&quot;user&quot; method=&quot;post&quot;> </li></ul><ul><li><form:errors path=&quot;*&quot; cssClass=&quot;error&quot;/> </li></ul><ul><li><form:hidden path=&quot;id&quot; /> </li></ul><ul><li><table class=&quot;detail&quot;> </li></ul><ul><li><tr> </li></ul><ul><li><th><label for=&quot;firstName&quot;> </li></ul><ul><li><fmt:message key=&quot;user.firstName&quot;/>:</label></th> </li></ul><ul><li><td> </li></ul><ul><li><form:input path=&quot;firstName&quot; id=&quot;firstName&quot;/> </li></ul><ul><li><form:errors path=&quot;firstName&quot; cssClass=&quot;fieldError&quot;/> </li></ul><ul><li></td> </li></ul><ul><li></tr> </li></ul><ul><li><tr> </li></ul><ul><li><th><label for=&quot;lastName&quot; class=&quot;required&quot;> </li></ul><ul><li>* <fmt:message key=&quot;user.lastName&quot;/>:</label></th> </li></ul><ul><li><td> </li></ul><ul><li><form:input path=&quot;lastName&quot; id=&quot;firstName&quot;/> </li></ul><ul><li><form:errors path=&quot;lastName&quot; cssClass=&quot;fieldError&quot;/> </li></ul><ul><li></td> </li></ul><ul><li></tr> </li></ul>
  18. 18. JSP представление Spring <ul><li><form:form commandName=&quot;user&quot; method=&quot;post&quot;> </li></ul><ul><li><form:errors path=&quot;*&quot; cssClass=&quot;error&quot;/> </li></ul><ul><li><form:hidden path=&quot;id&quot; /> </li></ul><ul><li><table class=&quot;detail&quot;> </li></ul><ul><li><tr> </li></ul><ul><li><th><label for=&quot;firstName&quot;> </li></ul><ul><li><fmt:message key=&quot;user.firstName&quot;/>:</label></th> </li></ul><ul><li><td> </li></ul><ul><li><form:input path=&quot;firstName&quot; id=&quot;firstName&quot;/> </li></ul><ul><li><form:errors path=&quot;firstName&quot; cssClass=&quot;fieldError&quot;/> </li></ul><ul><li></td> </li></ul><ul><li></tr> </li></ul><ul><li><tr> </li></ul><ul><li><th><label for=&quot;lastName&quot; class=&quot;required&quot;> </li></ul><ul><li>* <fmt:message key=&quot;user.lastName&quot;/>:</label></th> </li></ul><ul><li><td> </li></ul><ul><li><form:input path=&quot;lastName&quot; id=&quot;firstName&quot;/> </li></ul><ul><li><form:errors path=&quot;lastName&quot; cssClass=&quot;fieldError&quot;/> </li></ul><ul><li></td> </li></ul><ul><li></tr> </li></ul>
  19. 19. Velocity представление Spring <ul><li><form method=&quot;post&quot; action=&quot;#springUrl('/editUser.html')&quot;> </li></ul><ul><li>#springFormHiddenInput(&quot;user.id&quot; '') </li></ul><ul><li><table> </li></ul><ul><li><tr> </li></ul><ul><li><th><label for=&quot;firstName&quot;>#springMessage(&quot;user.firstName&quot;):</label></th> </li></ul><ul><li><td> </li></ul><ul><li>#springFormInput(&quot;user.firstName&quot; 'id=&quot;firstName&quot;') </li></ul><ul><li>#springShowErrors(&quot;<br/>&quot; &quot;fieldError&quot;) </li></ul><ul><li></td> </li></ul><ul><li></tr> </li></ul><ul><li><tr> </li></ul><ul><li><th><label for=&quot;lastName&quot;>#springMessage(&quot;user.lastName&quot;):</label></th> </li></ul><ul><li><td> </li></ul><ul><li>#springFormInput(&quot;user.lastName&quot; 'id=&quot;lastName&quot;') </li></ul><ul><li>#springShowErrors(&quot;<br/>&quot; &quot;fieldError&quot;) </li></ul><ul><li></td> </li></ul><ul><li></tr> </li></ul>
  20. 20. Spring Web Flow <ul><li>Инфраструктура позволяющая определять последовательность переходов между страницами </li></ul><ul><li>Определяется программно или через XML </li></ul><ul><li>Правила навигации активируются на основании строковых значений, возвращённых вызванными методами (подобно JSF ) </li></ul>
  21. 21. Spring Web Flow <ul><li><webflow id=&quot;userFlow&quot; start-state=&quot;setupForm&quot;> </li></ul><ul><li><action-state id=&quot;setupForm&quot;> </li></ul><ul><li><action bean=&quot;userFormAction&quot;/> </li></ul><ul><li><transition on=&quot;success&quot; to=&quot;display.nameForm&quot;/> </li></ul><ul><li></action-state> </li></ul><ul><li><view-state id=&quot;display.nameForm&quot; view=&quot;flow/name&quot;> </li></ul><ul><li><transition on=&quot;submit&quot; to=&quot;display.addressForm&quot;> </li></ul><ul><li><action bean=&quot;userFormAction&quot; method=&quot;bindAndValidate&quot;/> </li></ul><ul><li></transition> </li></ul><ul><li><transition on=&quot;cancel&quot; to=&quot;finish&quot;/> </li></ul><ul><li></view-state> </li></ul><ul><li><view-state id=&quot;display.addressForm&quot; view=&quot;flow/address&quot;> </li></ul><ul><li><transition on=&quot;previous&quot; to=&quot;display.nameForm&quot;> </li></ul><ul><li><action bean=&quot;userFormAction&quot; method=&quot;bindAndValidate&quot;/> </li></ul><ul><li></transition> </li></ul><ul><li><transition on=&quot;submit&quot; to=&quot;display.otherForm&quot;> </li></ul><ul><li><action bean=&quot;userFormAction&quot; method=&quot;bindAndValidate&quot;/> </li></ul><ul><li></transition> </li></ul><ul><li><transition on=&quot;cancel&quot; to=&quot;finish&quot;/> </li></ul><ul><li></view-state> </li></ul>
  22. 22. Tapestry ( Краткая характеристика ) <ul><li>Положительные стороны: </li></ul><ul><ul><li>Очень эффективна после изучения </li></ul></ul><ul><ul><li>Шаблоны являются HTML , что очень хорошо для дизайнеров </li></ul></ul><ul><ul><li>Хорошее сообщество пользователей </li></ul></ul><ul><li>Отрицательные стороны: </li></ul><ul><ul><li>Документация достаточно сложна для восприятия </li></ul></ul><ul><ul><li>Крутая кривая обучения </li></ul></ul><ul><ul><li>Мало примеров </li></ul></ul><ul><ul><li>Долгие циклы релизов – ведущие релизы 1-2 раза в год </li></ul></ul>
  23. 23. Tapestry ( Жизненный цикл )
  24. 24. Класс Tapestry <ul><li>public abstract class UserForm extends BasePage { </li></ul><ul><li>public abstract UserManager getUserManager(); </li></ul><ul><li>public abstract void setUser(User user); </li></ul><ul><li>public abstract User getUser(); </li></ul><ul><li>public void save(IRequestCycle cycle) { </li></ul><ul><li>if (log.isDebugEnabled()) { </li></ul><ul><li>log.debug(&quot;entered 'save' method&quot;); </li></ul><ul><li>} </li></ul><ul><li>getUserManager().saveUser(getUser()); </li></ul><ul><li>UserList nextPage = (UserList) cycle.getPage(&quot;users&quot;); </li></ul><ul><li>nextPage.setMessage(getMessages().format(&quot;user.saved&quot;, getUser().getFullName())); </li></ul><ul><li>throw new PageRedirectException(nextPage); </li></ul><ul><li>} </li></ul>
  25. 25. Конфигурирование Tapestry <ul><li><application name=&quot;tapestry&quot;> </li></ul><ul><li><page name=&quot;Home&quot; specification-path=&quot;/pages/home.page&quot;/> </li></ul><ul><li><page name=&quot;users&quot; specification-path=&quot;/pages/users.page&quot;/> </li></ul><ul><li><page name=&quot;userForm&quot; specification-path=&quot;/pages/userForm.page&quot;/> </li></ul><ul><li><library id= “ contrib ” specification p ath=&quot;/org/apache/tapestry/contrib/Contrib.library&quot;/> </li></ul><ul><li></application> </li></ul>
  26. 26. Конфигурирование Tapestry <ul><li><page-specification class=&quot;org.appfuse.web.UserForm&quot;> </li></ul><ul><li><bean name=&quot;delegate“ class=&quot;org.apache.tapestry.valid.ValidationDelegate&quot;/> </li></ul><ul><li><component id=&quot;form&quot; type=&quot;Form&quot;> </li></ul><ul><li><binding name=&quot;delegate&quot; value=&quot;ognl:beans.delegate&quot;/> </li></ul><ul><li><binding name=&quot;clientValidationEnabled&quot; value=&quot;true&quot;/> </li></ul><ul><li></component> </li></ul><ul><li><property name=&quot;user&quot;/> </li></ul><ul><li><inject property=&quot;userManager&quot; object=&quot;spring:userManager&quot;/> </li></ul><ul><li><component id=&quot;lastNameField&quot; type=&quot;TextField&quot;> </li></ul><ul><li><binding name=&quot;value&quot; value=&quot;user.lastName&quot;/> </li></ul><ul><li><binding name=&quot;validators&quot; value=&quot;validators:required&quot;/> </li></ul><ul><li><binding name=&quot;displayName&quot; value=&quot;message:lastName&quot;/> </li></ul><ul><li></component> </li></ul><ul><li></page-specification> </li></ul>
  27. 27. HTML представление Tapestry <ul><li><form jwcid=&quot;@Form&quot; delegate=&quot;ognl:beans.delegate&quot; name=&quot;userForm&quot;> </li></ul><ul><li><input type=&quot;hidden&quot; jwcid=&quot;@Hidden&quot; value=&quot;ognl:user.id&quot;/> </li></ul><ul><li><table class=&quot;detail&quot;> </li></ul><ul><li><tr> </li></ul><ul><li><th> </li></ul><ul><li><label for=&quot;firstName&quot;><span key=&quot;firstName&quot;>First Name</span></label>: </li></ul><ul><li></th> </li></ul><ul><li><td><input jwcid=&quot;@TextField&quot; type=&quot;text&quot; value=&quot;ognl:user.firstName&quot; id=&quot;firstName&quot;/></td> </li></ul><ul><li></tr> </li></ul><ul><li><tr> </li></ul><ul><li><th> </li></ul><ul><li><label jwcid=&quot;@FieldLabel&quot; field=&quot;ognl:components.lastNameField&quot;>Last Name</label>: </li></ul><ul><li></th> </li></ul><ul><li><td><input jwcid=&quot;lastNameField&quot; type=&quot;text&quot; id=&quot;lastName&quot;/></td> </li></ul><ul><li></tr> </li></ul><ul><li><tr> </li></ul><ul><li><th> </li></ul><ul><li><label for=&quot;birthday&quot;><span key=&quot;birthday&quot;>Birthday</span></label>: </li></ul><ul><li></th> </li></ul><ul><li><td> </li></ul><ul><li><input jwcid=&quot;@DatePicker&quot; format=&quot;message:date.format&quot; type=&quot;text ” </li></ul><ul><li>size=&quot;11&quot; value=&quot;ognl:user.birthday&quot; id=&quot;birthday&quot;/> </li></ul><ul><li></td> </li></ul><ul><li></tr> </li></ul>
  28. 28. HTML представление Tapestry <ul><li><form jwcid=&quot;@Form&quot; delegate=&quot;ognl:beans.delegate&quot; name=&quot;userForm&quot;> </li></ul><ul><li><input type=&quot;hidden&quot; jwcid=&quot;@Hidden&quot; value=&quot;ognl:user.id&quot;/> </li></ul><ul><li><table class=&quot;detail&quot;> </li></ul><ul><li><tr> </li></ul><ul><li><th> </li></ul><ul><li><label for=&quot;firstName&quot;><span key=&quot;firstName&quot;>First Name</span></label>: </li></ul><ul><li></th> </li></ul><ul><li><td> <input jwcid=&quot;@TextField&quot; type=&quot;text&quot; value=&quot;ognl:user.firstName&quot; id=&quot;firstName&quot;/> </td> </li></ul><ul><li></tr> </li></ul><ul><li><tr> </li></ul><ul><li><th> </li></ul><ul><li><label jwcid=&quot;@FieldLabel&quot; field=&quot;ognl:components.lastNameField&quot;>Last Name</label> : </li></ul><ul><li></th> </li></ul><ul><li><td> <input jwcid=&quot;lastNameField&quot; type=&quot;text&quot; id=&quot;lastName&quot;/> </td> </li></ul><ul><li></tr> </li></ul><ul><li><tr> </li></ul><ul><li><th> </li></ul><ul><li><label for=&quot;birthday&quot;><span key=&quot;birthday&quot;>Birthday</span></label>: </li></ul><ul><li></th> </li></ul><ul><li><td> </li></ul><ul><li><input jwcid=&quot;@DatePicker&quot; format=&quot;message:date.format&quot; type=&quot;text ” </li></ul><ul><li>size=&quot;11&quot; value=&quot;ognl:user.birthday&quot; id=&quot;birthday&quot;/> </li></ul><ul><li></td> </li></ul><ul><li></tr > </li></ul>
  29. 29. HTML представление Tapestry <ul><li><form jwcid=&quot;@Form&quot; delegate=&quot;ognl:beans.delegate&quot; name=&quot;userForm&quot;> </li></ul><ul><li><input type=&quot;hidden&quot; jwcid=&quot;@Hidden&quot; value=&quot;ognl:user.id&quot;/> </li></ul><ul><li><table class=&quot;detail&quot;> </li></ul><ul><li><tr> </li></ul><ul><li><th> </li></ul><ul><li><label for=&quot;firstName&quot;><span key=&quot;firstName&quot;>First Name</span></label>: </li></ul><ul><li></th> </li></ul><ul><li><td><input jwcid=&quot;@TextField&quot; type=&quot;text&quot; value=&quot;ognl:user.firstName&quot; id=&quot;firstName&quot;/></td> </li></ul><ul><li></tr> </li></ul><ul><li><tr> </li></ul><ul><li><th> </li></ul><ul><li><label jwcid=&quot;@FieldLabel&quot; field=&quot;ognl:components.lastNameField&quot;>Last Name</label>: </li></ul><ul><li></th> </li></ul><ul><li><td><input jwcid=&quot;lastNameField&quot; type=&quot;text&quot; id=&quot;lastName&quot;/></td> </li></ul><ul><li></tr> </li></ul><ul><li><tr> </li></ul><ul><li><th> </li></ul><ul><li><label for=&quot;birthday&quot;><span key=&quot;birthday&quot;>Birthday</span></label>: </li></ul><ul><li></th> </li></ul><ul><li><td> </li></ul><ul><li><input jwcid=&quot;@DatePicker&quot; format=&quot;message:date.format&quot; type=&quot;text ” </li></ul><ul><li>size=&quot;11&quot; value=&quot;ognl:user.birthday&quot; id=&quot;birthday&quot;/> </li></ul><ul><li></td> </li></ul><ul><li></tr > </li></ul>
  30. 30. Улучшения в следующей версии Tapestry <ul><li>Богатая поддержка аннотаций </li></ul><ul><li>Высокий уровень конфигурирования – базирование на IoC контейнере Hivemind </li></ul><ul><li>Требует меньше кода – более простая реализация классов реализующих логику страниц </li></ul><ul><li>Поддержка URL дружественных к пользователю </li></ul><ul><li>Компоненты Tacos AJAX </li></ul>
  31. 31. JSF ( Краткая характеристика ) <ul><li>Положительные стороны: </li></ul><ul><ul><li>J2EE Стандарт </li></ul></ul><ul><ul><li>Быстрая и простая разработка </li></ul></ul><ul><ul><li>Богата библиотека навигации (аналог Spring Web Flow ) </li></ul></ul><ul><li>Отрицательные стороны: </li></ul><ul><ul><li>Мешанина из JSP тэгов </li></ul></ul><ul><ul><li>Плохая поддержка «легковесных» вызовов ( REST ) </li></ul></ul><ul><ul><li>Нет единого источника реализации </li></ul></ul>
  32. 32. JSF ( Жизненный цикл )
  33. 33. Бин страницы JSF <ul><li>public class UserForm { </li></ul><ul><li>private String id; </li></ul><ul><li>public User user = new User(); </li></ul><ul><li>public UserManager mgr; </li></ul><ul><li>public void setId(String id) { </li></ul><ul><li>this.id = id; </li></ul><ul><li>} </li></ul><ul><li>public void setUser(User user) { </li></ul><ul><li>this.user = user; </li></ul><ul><li>} </li></ul><ul><li>public void setUserManager(UserManager userManager) { </li></ul><ul><li>this.mgr = userManager; </li></ul><ul><li>} </li></ul><ul><li>public String edit() { </li></ul><ul><li>if (id != null) { </li></ul><ul><li>// assuming edit </li></ul><ul><li>setUser(mgr.getUser(id)); </li></ul><ul><li>} </li></ul><ul><li>return &quot;success&quot;; </li></ul><ul><li>} </li></ul>
  34. 34. Конфигурация JSF <ul><li><application> </li></ul><ul><li><variable-resolver> </li></ul><ul><li>org.springframework.web.jsf.DelegatingVariableResolver </li></ul><ul><li></variable-resolver> </li></ul><ul><li><locale-config> </li></ul><ul><li><default-locale>en</default-locale> </li></ul><ul><li><supported-locale>en</supported-locale> </li></ul><ul><li><supported-locale>es</supported-locale> </li></ul><ul><li></locale-config> </li></ul><ul><li><message-bundle>messages</message-bundle> </li></ul><ul><li></application> </li></ul><ul><li><navigation-rule> </li></ul><ul><li><from-view-id>/userForm.jsp</from-view-id> </li></ul><ul><li><navigation-case> </li></ul><ul><li><from-outcome>cancel</from-outcome> </li></ul><ul><li><to-view-id>/userList.jsp</to-view-id> </li></ul><ul><li></navigation-case> </li></ul><ul><li><navigation-case> </li></ul><ul><li><from-outcome>success</from-outcome> </li></ul><ul><li><to-view-id>/userList.jsp</to-view-id> </li></ul><ul><li><redirect/> </li></ul><ul><li></navigation-case> </li></ul><ul><li></navigation-rule> </li></ul>
  35. 35. Конфигурация JSF <ul><li><application> </li></ul><ul><li><variable-resolver> </li></ul><ul><li>org.springframework.web.jsf.DelegatingVariableResolver </li></ul><ul><li></variable-resolver> </li></ul><ul><li><locale-config> </li></ul><ul><li><default-locale>en</default-locale> </li></ul><ul><li><supported-locale>en</supported-locale> </li></ul><ul><li><supported-locale>es</supported-locale> </li></ul><ul><li></locale-config> </li></ul><ul><li><message-bundle>messages</message-bundle> </li></ul><ul><li></application> </li></ul><ul><li><navigation-rule> </li></ul><ul><li><from-view-id>/userForm.jsp</from-view-id> </li></ul><ul><li><navigation-case> </li></ul><ul><li><from-outcome>cancel</from-outcome> </li></ul><ul><li><to-view-id>/userList.jsp</to-view-id> </li></ul><ul><li></navigation-case> </li></ul><ul><li><navigation-case> </li></ul><ul><li><from-outcome>success</from-outcome> </li></ul><ul><li><to-view-id>/userList.jsp</to-view-id> </li></ul><ul><li><redirect/> </li></ul><ul><li></navigation-case> </li></ul><ul><li></navigation-rule> </li></ul>
  36. 36. Конфигурация JSF <ul><li><managed-bean> </li></ul><ul><li><managed-bean-name>userForm</managed-bean-name> </li></ul><ul><li><managed-bean-class>org.appfuse.web.UserForm</managed-bean-class> </li></ul><ul><li><managed-bean-scope>request</managed-bean-scope> </li></ul><ul><li><managed-property> </li></ul><ul><li><property-name>id</property-name> </li></ul><ul><li><value>#{param.id}</value> </li></ul><ul><li></managed-property> </li></ul><ul><li><managed-property> </li></ul><ul><li><property-name>userManager</property-name> </li></ul><ul><li><value>#{userManager}</value> </li></ul><ul><li></managed-property> </li></ul><ul><li></managed-bean> </li></ul>
  37. 37. JSP представление JSF <ul><li><f:view> </li></ul><ul><li><f:loadBundle var=&quot;messages&quot; basename=&quot;messages&quot;/> </li></ul><ul><li><h:form id=&quot;userForm&quot;> </li></ul><ul><li><h:inputHidden value=&quot;#{userForm.user.id}&quot;> </li></ul><ul><li><f:convertNumber/> </li></ul><ul><li></h:inputHidden> </li></ul><ul><li><h:panelGrid columns=&quot;3&quot; styleClass=&quot;detail&quot; columnClasses=&quot;label&quot;> </li></ul><ul><li><h:outputLabel for=&quot;firstName&quot; value=&quot;#{messages['user.firstName']}&quot;/> </li></ul><ul><li><h:inputText value=&quot;#{userForm.user.firstName}&quot; id=&quot;firstName&quot;/> </li></ul><ul><li><h:message for=&quot;firstName&quot; styleClass=&quot;errorMessage&quot;/> </li></ul><ul><li><h:outputLabel for=&quot;lastName&quot; value=&quot;#{messages['user.lastName']}&quot;/> </li></ul><ul><li><h:inputText value=&quot;#{userForm.user.lastName}&quot; id=&quot;lastName&quot; required=&quot;true&quot;/> </li></ul><ul><li><h:message for=&quot;lastName&quot; styleClass=&quot;errorMessage&quot;/> </li></ul><ul><li><h:outputLabel for=&quot;birthday&quot; value=&quot;#{messages['user.birthday']}&quot;/> </li></ul><ul><li><t:inputCalendar monthYearRowClass=&quot;yearMonthHeader&quot; </li></ul><ul><li>weekRowClass=&quot;weekHeader&quot; id=&quot;birthday&quot; </li></ul><ul><li>currentDayCellClass=&quot;currentDayCell&quot; value=&quot;#{userForm.user.birthday}&quot; </li></ul><ul><li>renderAsPopup=&quot;true&quot; addResources=&quot;false&quot;/> </li></ul><ul><li><h:message for=&quot;birthday&quot; styleClass=&quot;errorMessage&quot;/> </li></ul>
  38. 38. JSP представление JSF <ul><li><f:view> </li></ul><ul><li><f:loadBundle var=&quot;messages&quot; basename=&quot;messages&quot;/> </li></ul><ul><li><h:form id=&quot;userForm&quot;> </li></ul><ul><li><h:inputHidden value=&quot;#{userForm.user.id}&quot;> </li></ul><ul><li><f:convertNumber/> </li></ul><ul><li></h:inputHidden> </li></ul><ul><li><h:panelGrid columns=&quot;3&quot; styleClass=&quot;detail&quot; columnClasses=&quot;label&quot;> </li></ul><ul><li><h:outputLabel for=&quot;firstName&quot; value=&quot;#{messages['user.firstName']}&quot;/> </li></ul><ul><li><h:inputText value=&quot;#{userForm.user.firstName}&quot; id=&quot;firstName&quot;/> </li></ul><ul><li><h:message for=&quot;firstName&quot; styleClass=&quot;errorMessage&quot;/> </li></ul><ul><li><h:outputLabel for=&quot;lastName&quot; value=&quot;#{messages['user.lastName']}&quot;/> </li></ul><ul><li><h:inputText value=&quot;#{userForm.user.lastName}&quot; id=&quot;lastName&quot; required=&quot;true&quot; /> </li></ul><ul><li><h:message for=&quot;lastName&quot; styleClass=&quot;errorMessage&quot;/> </li></ul><ul><li><h:outputLabel for=&quot;birthday&quot; value=&quot;#{messages['user.birthday']}&quot;/> </li></ul><ul><li><t:inputCalendar monthYearRowClass=&quot;yearMonthHeader&quot; </li></ul><ul><li>weekRowClass=&quot;weekHeader&quot; id=&quot;birthday&quot; </li></ul><ul><li>currentDayCellClass=&quot;currentDayCell&quot; value=&quot;#{userForm.user.birthday}&quot; </li></ul><ul><li>renderAsPopup=&quot;true&quot; addResources=&quot;false&quot;/> </li></ul><ul><li><h:message for=&quot;birthday&quot; styleClass=&quot;errorMessage&quot;/> </li></ul>
  39. 39. JSP представление JSF <ul><li><f:view> </li></ul><ul><li><f:loadBundle var=&quot;messages&quot; basename=&quot;messages&quot;/> </li></ul><ul><li><h:form id=&quot;userForm&quot;> </li></ul><ul><li><h:inputHidden value=&quot;#{userForm.user.id}&quot;> </li></ul><ul><li><f:convertNumber/> </li></ul><ul><li></h:inputHidden> </li></ul><ul><li><h:panelGrid columns=&quot;3&quot; styleClass=&quot;detail&quot; columnClasses=&quot;label&quot;> </li></ul><ul><li><h:outputLabel for=&quot;firstName&quot; value=&quot;#{messages['user.firstName']}&quot;/> </li></ul><ul><li><h:inputText value=&quot;#{userForm.user.firstName}&quot; id=&quot;firstName&quot;/> </li></ul><ul><li><h:message for=&quot;firstName&quot; styleClass=&quot;errorMessage&quot;/> </li></ul><ul><li><h:outputLabel for=&quot;lastName&quot; value=&quot;#{messages['user.lastName']}&quot;/> </li></ul><ul><li><h:inputText value=&quot;#{userForm.user.lastName}&quot; id=&quot;lastName&quot; required=&quot;true&quot; /> </li></ul><ul><li><h:message for=&quot;lastName&quot; styleClass=&quot;errorMessage&quot;/> </li></ul><ul><li><h:outputLabel for=&quot;birthday&quot; value=&quot;#{messages['user.birthday']}&quot;/> </li></ul><ul><li><t:inputCalendar monthYearRowClass=&quot;yearMonthHeader&quot; </li></ul><ul><li>weekRowClass=&quot;weekHeader&quot; id=&quot;birthday&quot; </li></ul><ul><li>currentDayCellClass=&quot;currentDayCell&quot; value=&quot;#{userForm.user.birthday}&quot; </li></ul><ul><li>renderAsPopup=&quot;true&quot; addResources=&quot;false&quot;/> </li></ul><ul><li><h:message for=&quot;birthday&quot; styleClass=&quot;errorMessage&quot;/> </li></ul>
  40. 40. Улучшения в следующей версии JSF (1.2) <ul><li>Унифицированный EL – лучшая поддержка JSTL </li></ul><ul><li>Фокусировка на лёгком использовании </li></ul><ul><li>Расширенная поддержка AJAX </li></ul><ul><li>Дополнительные реализации: ADF Faces, Facelets </li></ul>
  41. 41. Сравнение . Критерии <ul><li>Сортируемые / Листаемые списки – насколько просто создать список данных с листаемыми страницами и возможностями сортировки. </li></ul><ul><li>Возможность создания закладок – может ли пользователь создавать закладки на страницы для последующего обращения к ним? </li></ul><ul><li>Валидация - проверка введённых значений. </li></ul><ul><li>Тестируемость – возможности для автономного тестирования классов, составляющих клиента, вне контейнера. </li></ul>
  42. 42. Сравнение . Критерии <ul><li>Интернационализация </li></ul><ul><li>Модификация «на лету» - принятие исправлений без необходимости перекомпиляции или перезапуска контейнера </li></ul><ul><li>Поддержка разработчиками </li></ul><ul><li>Производительность / Масштабируемость </li></ul><ul><li>«Компонетность» - возможность создания повторно-используемых, параметризуемых модулей </li></ul><ul><li>Возможности языка выражений </li></ul>
  43. 43. Сортируемые / Листаемые списки <ul><li>JSP – никакой поддержки </li></ul><ul><li>Spring & Struts могут использовать библиотеки тэгов, типа “DisplayTag” </li></ul><ul><li>Tapestry имеет contrib:Table компонент </li></ul><ul><li>JSF имеет h:dataTable компонент без возможностей сортировки – необходимо писать свою собственную логику для реализации данного функционала </li></ul>
  44. 44. Возможность создания закладок <ul><li>JSP, String & Strut имеют полный контроль над строкой запроса </li></ul><ul><li>Tapestry имеет слегка корявую поддержку создания закладок, но всё же все возможности реализованы </li></ul><ul><li>JSF делает POST для всего – закладки даже не рассматриваются (но при желании и это можно обойти) </li></ul>
  45. 45. Валидация <ul><li>JSP – «собственные» решения, либо перенос проверки в модель данных </li></ul><ul><li>String & Struts используют проект Apache – Commons Validator – надёжное и зрелое решение </li></ul><ul><li>Tapestry – хорошая архитектура валидации – хорошие сообщения (даже без необходимости корректировки под свои нужды) </li></ul><ul><li>JSF – «некрасивые» сообщения об ошибках по-умолчанию (но легко исправляется) </li></ul>
  46. 46. Тестируемость <ul><li>Struts – необходимо использование StrutsTestCase </li></ul><ul><li>JSP, Spring – легко тестируется с использованием средств генерации «заглушек» ( mock ) (EasyMock, jMock, Spring Mock…) </li></ul><ul><li>Tapestry – неочевидное тестирование, т.к. классы абстрактные – класс Creator помогает </li></ul><ul><li>JSF – самое простая архитектура для тестирования – классы – просто бины </li></ul>
  47. 47. Интернационализация <ul><li>JSTL <fmt:message> позволяет делать это легко почти в любой реализации </li></ul><ul><li>JSP, Struts, Spring, JSF – используют один ResourceBundle на язык </li></ul><ul><li>Tapestry – предпочитает отдельные файлы для страниц / компонентов </li></ul><ul><li>JSF требует, что данные с локализацией были объявлены на каждой странице </li></ul>
  48. 48. Модификация «на лету» <ul><li>JSP – самый гибкий в данном случае (конечно при корректном использовании). JSP файлы перекомпиливаются при каждом изменении, а вот классы нет. </li></ul><ul><li>Tapestry, Spring & Struts – всё (страницы, компоненты, библиотеки и конфигурационные файлы) (кроме классов) перечитывается при изменении. </li></ul><ul><li>JSF – не перечитываются конфигурационные файлы. </li></ul>
  49. 49. Поддержка разработчиками <ul><li>JSP & JSF – стандарт, большое сообщество разработчиков и множество документации </li></ul><ul><li>Spring – большое количество примеров и документации, хорошая поддержка разработчиками библиотеки </li></ul><ul><li>Tapestry – мало хорошей, понятной документации. Мало примеров. </li></ul><ul><li>Struts – отсутствие поддержки со стороны разработчиков, но при этом много документации и примеров использования в больших проектах </li></ul>
  50. 50. Производительность / Масштабируемость <ul><li>JSP – хорошие показатели, в связи с отсутствием каких-либо промежуточных уровней </li></ul><ul><li>Tapestry – после версии 4.0 (где было удалено широкое использование интроспекции) скорость стала сравнима с JSP </li></ul><ul><li>JSF – не самые лучшие показатели… </li></ul><ul><li>Spring & Struts – адекватные показатели. </li></ul>
  51. 51. «Компонетность» <ul><li>JSP – тэг-файлы и тэги. </li></ul><ul><li>Tapestry – очень ориентированная на создание и использование компонетов, хорошая интеграция с JavaScript. </li></ul><ul><li>JSF – хорошие возможности по созданию компонентов, но создавать не так легко как в Tapestry. </li></ul><ul><li>Spring & Struts – лишь то же, что даёт JSP. </li></ul>
  52. 52. Возможности языка выражений <ul><li>JSP, JSF, Spring, Struts – богатые возможности EL говорят сами за себя. </li></ul><ul><li>Tapestry – вместо EL используется OGNL , который предоставляет ещё большие возможности. </li></ul>
  53. 53. Финал <ul><li>Выбирайте с умом… </li></ul>

×