| <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" |
| "http://www.w3.org/TR/html4/loose.dtd"> |
| <html> |
| <head> |
| <meta http-equiv="content-type" content="text/html; charset=UTF-8"> |
| <meta name="description" content="Demonstrates how the IDE can generate robust and easily maintainable code when generating JSF pages from entity classes."> |
| |
| <meta name="keywords" content="NetBeans, IDE, integrated development environment, |
| Java, Java EE, open source, web technology, CRUD, JSF, tutorial, database"> |
| |
| <link rel="stylesheet" type="text/css" href="../../../netbeans.css"> |
| <link rel="stylesheet" type="text/css" href="../../../lytebox.css" media="screen"> |
| <script type="text/javascript" src="../../../images_www/js/lytebox-compressed.js"></script> |
| |
| <script src="../../../images_www/js/listCollapse.js" type="text/javascript"></script> |
| |
| <title>Создание приложения CRUD JavaServer Faces 2.x на основе базы данных - учебный курс по IDE NetBeans</title> |
| </head> |
| |
| <body> |
| |
| <!-- Copyright (c) 2009, 2010, 2011, Oracle and/or its affiliates. All rights reserved. --> |
| |
| <h1>Создание приложения JavaServer Faces 2.x CRUD на основе базы данных</h1> |
| |
| <p>В этом учебном курсе описывается использование NetBeans IDE для создания веб-приложения, взаимодействующего с серверной базой данных. Приложение предоставляет возможность просмотра и изменения данных, содержащихся в базе данных, другими словами – функциональные возможности <em>CRUD</em> (Create, Read, Update, Delete – создание, чтение, обновление, удаление). Разрабатываемое приложение основывается на следующих технологиях.</p> |
| |
| <ul> |
| <li><strong>JavaServer Faces (JSF) 2.x</strong> для веб-страниц внешнего интерфейса, обработки проверки и управления циклом "запрос-ответ".</li> |
| |
| <li><strong>Интерфейс API сохранения состояния Java (Java Persistence API, JPA) 2.0</strong> с использованием EclipseLink для создания классов сущностей из базы данных и управления транзакциями. (EclipseLink является образцовой реализацией JPA и поставщиком сохранения состояния для сервера GlassFish по умолчанию).</li> |
| |
| <li><strong>Enterprise JavaBeans (EJB) 3.1</strong> – предоставление компонентов EJB без сохранения состояния, которые имеют доступ к классам сущностей и содержат бизнес-логику для приложения.</li> |
| </ul> |
| |
| <p>В среде IDE предоставляются два мастера для создания всех строк кода приложения. Первый – <a href="#generateEntity">мастер создания классов сущностей из базы данных</a>, позволяющий создавать классы сущностей из предоставленной базы данных. После создания классов сущностей используйте <a href="#jsfPagesEntityClasses">мастер создания страниц JSF из классов сущностей</a> для создания управляемых компонентов JSF и компонентов EJB для классов сущностей, а также набор страниц Facelets для обработки представления данных классов сущностей. Последний раздел руководства <a href="#explore">Анализ приложения</a> является дополнительным. В него включено множество упражнений, помогающих лучше понять приложение и ознакомиться со средой IDE.</p> |
| |
| <img alt="Содержимое на этой странице применимо к IDE NetBeans 7.2, 7.3, 7.4 и 8.0" class="stamp" src="../../../images_www/articles/73/netbeans-stamp-80-74-73.png" title="Содержимое этой страницы применимо к IDE NetBeans 7.2, 7.3, 7.4 и 8.0"> |
| |
| |
| <h4>Содержание</h4> |
| |
| <ul class="toc"> |
| <li><a href="#createDB">Создание базы данных</a></li> |
| <li><a href="#examineDB">Изучение структуры базы данных</a></li> |
| <li><a href="#createProject">Создание проекта веб-приложения</a></li> |
| <li><a href="#generateEntity">Создание классов сущностей из базы данных</a></li> |
| <li><a href="#jsfPagesEntityClasses">Создание страниц JSF из классов сущностей</a></li> |
| <li><a href="#explore">Анализ приложения</a> |
| |
| <ul> |
| <li><a href="#completedProject">Изучение выполненного проекта</a></li> |
| <li><a href="#populateDB">Заполнение базы данных с помощью сценария SQL</a></li> |
| <li><a href="#editorSupport">Изучение поддержки редактора на страницах Facelets</a></li> |
| <li><a href="#dbIntegrity">Изучение целостности базы данных с проверкой поля</a></li> |
| <li><a href="#editEntity">Правка классов сущностей</a></li> |
| </ul></li> |
| |
| <li><a href="#troubleshooting">Устранение проблем</a></li> |
| <li><a href="#seeAlso">Дополнительные сведения</a></li> |
| </ul> |
| |
| <p id="requiredSoftware">Для работы с этим учебным курсом требуется программное обеспечение и материалы, перечисленные ниже.</p> |
| |
| <table> |
| <tbody> |
| <tr> |
| <th class="tblheader" scope="col">Программное обеспечение или материал</th> |
| <th class="tblheader" scope="col">Требуемая версия</th> |
| </tr> |
| <tr> |
| <td class="tbltd1"><a href="https://netbeans.org/downloads/index.html">IDE NetBeans</a></td> |
| <td class="tbltd1">7.2, 7.3, 7.4, 8.0, пакет Java EE</td> |
| </tr> |
| <tr> |
| <td class="tbltd1"><a href="http://www.oracle.com/technetwork/java/javase/downloads/index.html">Комплект для разработчика на языке Java (JDK)</a></td> |
| <td class="tbltd1">7 или 8</td> |
| </tr> |
| <tr> |
| <td class="tbltd1"><a href="http://glassfish.dev.java.net/">GlassFish Server Open Source Edition 3.1.2.2</a></td> |
| <td class="tbltd1">3.x, 4.x </td> |
| </tr> |
| <tr> |
| <td class="tbltd1"><a href="https://netbeans.org/projects/samples/downloads/download/Samples%252FJavaEE%252Fmysql-consult.zip">mysql-consult.zip</a> (MySQL) <br><em class="margin-around" style="margin-left:6em">или</em><br> <a href="https://netbeans.org/projects/samples/downloads/download/Samples%252FJavaEE%252Fjavadb-consult.zip">javadb-consult.zip</a> (JavaDB)</td> |
| <td class="tbltd1">неприменимо</td> |
| </tr> |
| </tbody> |
| </table> |
| |
| <p class="notes"><strong>Примечания</strong></p> |
| |
| <div class="indent"> |
| <ul> |
| <li>В комплект Java EE в среде IDE NetBeans также входит сервер GlassFish - сервер, совместимый с Java EE 6, который требуется для этого учебного курса.</li> |
| |
| <li>Для проекта решения в этом учебном курсе загрузите <a href="https://netbeans.org/projects/samples/downloads/download/Samples%252FJavaEE%252FConsultingAgencyJSF20.zip">ConsultingAgencyJSF20.zip</a></li> |
| </ul> |
| </div> |
| |
| <br> |
| <h2 id="createDB">Создание базы данных</h2> |
| |
| <p>В целях этого руководства используется база данных консультационного агентства с именем <code>consult</code>. Эта база данных не входит в устанавливаемую среду IDE, поэтому перед изучением этого руководства необходимо создать базу данных.</p> |
| |
| <p>База данных <code>consult</code> разработана для демонстрации области поддержки среды IDE для обработки различных структур баз данных. Таким образом, эта база данных не предназначена для использования в качестве рекомендуемого примера разработки базы данных или в качестве практической рекомендации. Тем не менее, в нее включено множество возможностей, которые потенциально требуются при разработке базы данных. Например, база данных <code>consult</code> содержит все возможные типы отношений, составные первичные ключи и многие другие типы данных. Подробный обзор структуры базы данных приведен в таблице ниже.</p> |
| |
| <p><strong class="notes">Примечания:</strong></p> |
| |
| <ul> |
| <li>В данном учебном курсе используется сервер базы данных MySQL, однако для работы с этим учебным руководством можно также использовать сервер базы данных JavaDB. Чтобы создать базу данных в JavaDB, загрузите и извлеките архив <a href="https://netbeans.org/projects/samples/downloads/download/Samples%252FJavaEE%252Fjavadb-consult.zip">javadb-consult.zip</a>. Архив содержит сценарии SQL для создания, удаления и заполнения базы данных <code>consult</code>.</li> |
| |
| <li>Для получения дополнительной информации о настройке среды IDE для работы с MySQL см. учебный курс <a href="../ide/mysql.html">Подключение к базе данных MySQL</a>.</li> |
| |
| <li>Дополнительные сведения о настройке среды IDE для работы с JavaDB приведены в учебном курсе <a href="../ide/java-db.html">Работа с базой данных Java DB (Derby)</a>.</li> |
| </ul> |
| |
| <div class="feedback-box float-left" style="width: 678px; margin: 0 0 10px 10px"> |
| <p><strong class="alert">Сочетание MySQL с GlassFish:</strong></p> |
| |
| <p>При использовании сервера баз данных MySQL и вместе с ним GlassFish версии 3 или Open Source Edition версии 3.0.1 необходимо убедиться, что база данных защищена паролем. (Дополнительную информацию можно получить в описании <a href="https://java.net/jira/browse/GLASSFISH-12221" target="_blank">Issue 12221</a> (проблема 12221) сервера GlassFish.) При использовании учетной записи MySQL <code>root</code> по умолчанию с пустым паролем с помощью командной строки можно установить другой пароль. <br><br> К примеру, чтобы установить пароль к <code><em>nbuser</em></code>, необходимо в командную строку ввести следующие команды.</p> |
| |
| <pre class="examplecode" style="width: 658px;"> |
| shell> mysql -u root |
| mysql> UPDATE mysql.user SET Password = PASSWORD('<em>nbuser</em>') WHERE User = 'root'; |
| mysql> FLUSH PRIVILEGES;</pre> |
| |
| <p>Если в ответ получена ошибка "<code>mysql: command not found</code>" (mysql: не найдена команда), это означает, что команда <code>mysql</code> не была добавлена в переменную среды <code>PATH</code>. Вместо этого команду можно вызвать, выбрав полный путь к установочному каталогу MySQL <code>bin</code>. Например, если команда <code>mysql</code> находится на компьютере по пути <code>/usr/local/mysql/bin</code>, выберите следующее:</p> |
| |
| <pre class="examplecode" style="width: 658px;">shell> /usr/local/mysql/bin/mysql -u root</pre> |
| |
| <p>Дополнительные сведения приведены в официальном справочном руководстве по MySQL:</p> |
| |
| <ul> |
| <li><a href="http://dev.mysql.com/doc/refman/5.1/en/default-privileges.html" target="_blank">Обеспечение защиты начальных счетов MySQL </a></li> |
| |
| <li><a href="http://dev.mysql.com/doc/refman/5.1/en/invoking-programs.html" target="_blank">4.2.1. Invoking MySQL Programs ("Вызов программ MySQL")</a></li> |
| |
| <li><a href="http://dev.mysql.com/doc/refman/5.1/en/setting-environment-variables.html" target="_blank">4.2.4. Setting Environment Variables ("Настройка переменных среды")</a></li> |
| </ul> |
| |
| </div> |
| <br style="clear: both;"/> |
| |
| <br> |
| <p>Для создания базы данных и подключения к ней из среды IDE выполните следующие действия.</p> |
| |
| <ol style="margin-top:0"> |
| <li>Загрузите <a href="https://netbeans.org/projects/samples/downloads/download/Samples%252FJavaEE%252Fmysql-consult.zip">mysql-consult.zip</a> и извлеките архив в локальную систему. В результате извлечения архива появятся сценарии SQL для создания и заполнения базы данных. Архив также содержит сценарии для перетаскивания таблиц.</li> |
| |
| <li>В окне 'Службы' разверните узел Databases, щелкните правой кнопкой мыши узел MySQL и выберите 'Запустить сервер'.</li> |
| |
| <li>Щелкните правой кнопкой мыши узел "MySQL Server" и выберите "Create Database".</li> |
| |
| <li>В диалоговом окне "Создание базы данных MySQL" введите <strong>consult</strong> в поле "Имя базы данных". Нажмите кнопку "ОК". Под узлом "Базы данных" появится новый узел (<code>jdbc:mysql://localhost:3306/consult [корень в схеме по умолчанию]</code>).</li> |
| |
| <li>Правой кнопкой мыши щелкните новый узел и выберите "Подключить".</li> |
| |
| <li>В основном меню выберите "Файл > Открыть файл" и перейдите к извлеченному файлу <code>mysql_create_.sql</code>. Нажмите кнопку Open ("Открыть"). Файл автоматически откроется в редакторе SQL. <br> <img alt="Снимок редактора SQL" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/run-sql-script.png" title="Откройте файлы SQL в редакторе IDE"></li> |
| |
| <li>Убедитесь, что база данных <code>consult</code> выбрана в раскрывающемся списке "Соединение" на панели инструментов редактора SQL, затем нажмите кнопку 'Выполнить SQL' ( <img alt="Кнопка "Выполнить SQL"" src="../../../images_www/articles/72/web/jsf20-crud/run-sql-btn.png"> ). |
| |
| <p>После нажатия кнопки "Запустить SQL" в окне вывода появятся следующие выходные данные.</p> |
| |
| <img alt="Cнимок окна вывода" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/run-sql-output.png" title="Окно вывода, в котором указываются сведения о выполнении SQL"></li> |
| </ol> |
| |
| |
| <br> |
| <h2 id="examineDB">Изучение структуры базы данных</h2> |
| |
| <p>Чтобы убедиться в том, что таблицы созданы правильно, разверните узел "Таблицы" под узлом подключения к базе данных. В развернутом узле таблицы можно посмотреть столбцы, индексы и внешние ключи. Для просмотра дополнительных сведений о столбце щелкните правой кнопкой мыши и выберите 'Свойства'.</p> |
| |
| <div class="indent"> |
| <img alt="Снимок окна 'Службы'" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/services-window-tables.png" title="В окне 'Службы' отображаются подключения к базам данных, таблицы, столбцы таблиц, индексы и внешние ключи"> |
| </div> |
| |
| <p class="notes"><strong>Примечание.</strong> Если таблицы не отображаются в узле 'Таблицы', щелкните правой кнопкой мыши узел 'Таблицы' и выберите 'Обновить'.</p> |
| |
| <p>Анализ структуры базы данных <code>consult</code> позволяет установить, что база данных содержит таблицы с множеством отношений и различными типами полей. При создании классов сущностей в базе данных в среде IDE автоматически создается соответствующий код для различных типов полей.</p> |
| |
| <img alt="Диаграмма связей сущностей базы данных consult" class="margin-around b-all" id="er-diagram" src="../../../images_www/articles/72/web/jsf20-crud/diagram_consult.png" title="Диаграмма связей сущностей базы данных consult"> |
| |
| <p>В следующей таблице представлено описание таблиц, обнаруженных в базе данных <code>consult</code>.</p> |
| |
| <table class="indent" style="width: 744px"> |
| <tr> |
| <th class="tblheader" scope="col">Таблица базы данных</th> |
| <th class="tblheader" scope="col">Описание</th> |
| <th class="tblheader" scope="col">Функции разработки</th> |
| </tr> |
| <tr> |
| <td class="tbltd1">CLIENT</td> |
| <td class="tbltd0">Клиент консультационного агентства</td> |
| <td class="tbltd0">Несгенерированный составной первичный ключ (поля которого не являются частью внешнего ключа)</td> |
| |
| </tr> |
| <tr> |
| <td class="tbltd1">CONSULTANT</td> |
| <td class="tbltd0">Сотрудник консультационного агентства, которого могут нанять клиенты на контрактной основе.</td> |
| <td class="tbltd0">Включает в себя поле резюме типа LONG VARCHAR.</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">CONSULTANT_STATUS</td> |
| <td class="tbltd0">Состояние консультанта в консультационном агентстве (пример возможных состояний: "Активно" и "Неактивно").</td> |
| <td class="tbltd0">Несгенерированный первичный ключ типа CHAR.</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">RECRUITER</td> |
| <td class="tbltd0">Сотрудник консультационного агентства, ответственный за установление связи между клиентами и консультантами.</td> |
| <td class="tbltd0"> </td> |
| </tr> |
| <tr> |
| <td class="tbltd1">PROJECT</td> |
| <td class="tbltd0">Проект, под который клиент укомплектовывает штат консультантами консультационного агентства.</td> |
| <td class="tbltd0">Несгенерированный составной первичный ключ, который содержит два поля, составляющие внешний ключ для таблицы CLIENT.</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">BILLABLE</td> |
| <td class="tbltd0">Количество часов, отработанных консультантом над проектом, которые консультационное агентство выставляет в счете на оплату соответствующему клиенту.</td> |
| <td class="tbltd0">Включает в себя поле артефакта типа CLOB.</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">ADDRESS</td> |
| <td class="tbltd0">Адрес для выставления счета клиенту.</td> |
| <td class="tbltd0"> </td> |
| </tr> |
| <tr> |
| <td class="tbltd1">PROJECT_CONSULTANT</td> |
| <td class="tbltd0">Таблица перекрестных ссылок, определяющая текущие присвоения консультантов проектам.</td> |
| <td class="tbltd0">Перекрестные ссылки PROJECT и CONSULTANT, при этом последней соответствует составной первичный ключ.</td> |
| </tr> |
| </table> |
| |
| <br> |
| <p>База данных <code>consult</code> имеет множество отношений. При создании классов сущностей из базы данных в среде IDE автоматически создаются свойства соответствующего типа Java на основе типа SQL столбцов. Следующая таблица описывает отношения сущностей для базы данных <code>consult</code> (обратные отношения не отображаются).</p> |
| |
| <table id="relationships" class="indent" style="width: 744px"> |
| <tr> |
| <th class="tblheader" scope="col">Сущность</th> |
| <th class="tblheader" scope="col">Связанная сущность</th> |
| <th class="tblheader" scope="col">Информация об отношениях</th> |
| <th class="tblheader" scope="col">Описание</th> |
| </tr> |
| <tr> |
| <td class="tbltd1">CLIENT</td> |
| <td class="tbltd0">RECRUITER</td> |
| <td class="tbltd0">нулевое, "один к одному", с правкой вручную; нулевое, "один ко многим", если без правки.</td> |
| <td class="tbltd0">CLIENT соответствует несколько RECRUITER, а RECRUITER соответствует нуль или один CLIENT (если без правки вручную).</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">CLIENT</td> |
| <td class="tbltd0">ADDRESS</td> |
| <td class="tbltd0">ненулевое, "один к одному".</td> |
| <td class="tbltd0">CLIENT соответствует один ADDRESS, а ADDRESS соответствует нуль или один CLIENT.</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">CLIENT</td> |
| <td class="tbltd0">PROJECT</td> |
| <td class="tbltd0">ненулевое, "один ко многим"; в сущности "Проект" значение поля клиента является частью первичного ключа проекта.</td> |
| <td class="tbltd0">CLIENT соответствует несколько PROJECT, а PROJECT соответствует один CLIENT.</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">CONSULTANT</td> |
| <td class="tbltd0">PROJECT</td> |
| <td class="tbltd0">"многие ко многим".</td> |
| <td class="tbltd0">CONSULTANT соответствует несколько PROJECT, а PROJECT соответствует несколько CONSULTANT.</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">CONSULTANT</td> |
| <td class="tbltd0">BILLABLE</td> |
| <td class="tbltd0">ненулевое, "один ко многим".</td> |
| <td class="tbltd0">CONSULTANT соответствует несколько BILLABLE, а BILLABLE соответствует один CONSULTANT.</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">CONSULTANT_STATUS</td> |
| <td class="tbltd0">CONSULTANT</td> |
| <td class="tbltd0">ненулевое, "один ко многим".</td> |
| <td class="tbltd0">CONSULTANT_STATUS соответствует несколько CONSULTANT, а CONSULTANT соответствует один CONSULTANT_STATUS.</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">CONSULTANT</td> |
| <td class="tbltd0">RECRUITER</td> |
| <td class="tbltd0">нулевое, "один ко многим".</td> |
| <td class="tbltd0">CONSULTANT соответствует нуль или одного RECRUITER, а RECRUITER соответствует несколько CONSULTANT.</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">BILLABLE</td> |
| <td class="tbltd0">PROJECT</td> |
| <td class="tbltd0">ненулевое, "один ко многим".</td> |
| <td class="tbltd0">BILLABLE соответствует один PROJECT, а PROJECT соответствует несколько BILLABLE.</td> |
| </tr> |
| </table> |
| |
| <p>Теперь, после создания базы данных, можно создать веб-приложение и использовать мастер создания классов сущностей из базы данных для создания классов сущностей на основе таблиц баз данных.</p> |
| |
| |
| <h2 id="createProject">Создание проекта веб-приложения</h2> |
| |
| <p>В этом упражнении будет создан веб-проект и добавлена платформа JavaServer Faces к проекту. При создании проекта выбираем JavaServer Faces на панели "Платформы" мастера создания проекта.</p> |
| |
| <ol> |
| <li>Выберите "Файл > Новый проект" (CTRL+SHIFT+N; &#8984+SHIFT+N в Mac ОС) в главном меню.</li> |
| |
| <li>Выберите "Веб-приложение" в категории "Java Web". Нажмите кнопку "Далее".</li> |
| |
| <li>Введите <code>ConsultingAgency</code> в качестве имени проекта и укажите местоположение проекта. Нажмите кнопку "Далее".</li> |
| |
| <li>Укажите GlassFish в качестве сервера и Java 6 Web или Java EE 7 Web в качестве версии Java EE. Нажмите кнопку "Далее".</li> |
| |
| <li>На панели "Платформы" выберите параметр JavaServer Faces. Нажмите кнопку "Завершить".</li> |
| |
| </ol> |
| <p>При нажатии кнопки "Готово" в среде IDE будет создан проект веб-приложения и открыт <code>index.xhtml</code> в редакторе.</p> |
| |
| |
| <h2 id="generateEntity">Создание классов сущностей из базы данных</h2> |
| |
| <p>После подключения к базе данных в среде IDE можно использовать мастер создания классов сущностей из базы данных для быстрого создания классов сущностей на основе таблиц в базе данных. В среде IDE можно создавать классы сущностей для каждой выбранной таблицы, а также создавать любые классы сущностей для соответствующих таблиц.</p> |
| |
| <ol> |
| <li>В окне 'Проекты' щелкните правой кнопкой мыши узел проекта <code>ConsultingAgency</code> и выберите 'Создать' > 'Классы сущностей' в базе данных. Если данная команда отсутствует, выберите пункт "Прочие". После этого в мастере создания файла выберите категорию "Сохранение состояния", а затем - пункт "Классы сущностей из базы данных".</li> |
| |
| <li>Для открытия диалогового окна "Создание источника данных" в раскрывающемся списке "Источник данных" выберите "Новый источник данных".</li> |
| |
| <li>В поле "Имя JNDI" введите <code>jdbc/consult</code> и выберите подключение <code>jdbc:mysql://localhost:3306/consult</code> в списке "Подключение к базе данных". <br> <img alt="Диалоговое окно 'Создать источник данных'" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/create-datasource.png" title="Укажите имя JNDI и соединение с базой данных для создания источника данных"></li> |
| |
| <li>Нажмите кнопку "ОК" для закрытия диалогового окна и возврата в мастер. Таблицы базы данных <code>consult</code> выводятся в окне списка "Доступные таблицы".</li> |
| |
| <li>Для выбора всех таблиц, имеющихся в базе данных, нажмите кнопку "Добавить все". Нажмите кнопку "Далее". <br> <img alt="Новые сущности из мастера баз данных" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/new-entities-wizard.png"></li> |
| |
| <li>Введите <code>jpa.entities</code> в качестве имени пакета. </li> |
| |
| <li>Убедитесь, что установлены оба флажка — и создания именованных запросов, и создания блоков сохранения состояния. Нажмите кнопку "Завершить".</li> |
| </ol> |
| |
| <p>При нажатии кнопки "Готово" среда IDE создает классы сущностей в пакете проекта <code>jpa.entities</code>.</p> |
| |
| <p>При использовании мастера создания классов сущностей из базы данных в среде IDE проверяются отношения между таблицами базы данных. В окне 'Проекты' при развертывании узла проекта <code>jpa.entities</code> можно увидеть, что в IDE создан класс сущности для всех таблиц, кроме таблицы <code>PROJECT_CONSULTANT</code>. В среде IDE класс сущностей для таблицы <code>PROJECT_CONSULTANT</code> не создан, так как она является таблицей перекрестных ссылок.</p> |
| |
| <div class="indent"> |
| <img alt="снимок окна 'Проекты'" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/projects-window-entities.png" title="снимок окна 'Проекты', в котором отображаются созданные классы сущностей"> |
| </div> |
| |
| <p>В среде IDE также создано два дополнительных класса для таблиц с составными первичными ключами: <code>CLIENT</code> и <code>PROJECT</code>. К именам классов первичных ключей для этих таблиц (<code>ClientPK.java</code> и <code>ProjectPK.java</code>) добавлено <code>PK</code>.</p> |
| |
| <p>При просмотре созданного кода для классов сущностей можно отметить, что мастером добавлены аннотации <code>@GeneratedValue</code> к автоматически созданным полям ID и аннотации <code>@Basic(optional = "false")</code> к полям в классах сущностей. На основе аннотаций <code>@Basic(optional = "false")</code> мастер создания страниц JSF из классов сущностей способен создавать код с блоками проверок для предотвращения нарушений в ненулевых столбцах для этих полей.</p> |
| |
| |
| <br> |
| <h2 id="jsfPagesEntityClasses">Создание страниц JSF из классов сущностей</h2> |
| |
| <p>Теперь, после создания классов сущностей, можно создать веб-интерфейс для отображения и изменения данных. Для создания страниц JavaServer Faces используется страницы JSF мастера создания классов сущностей. Код, созданный мастером, основан на аннотациях сохранения состояния, содержащихся в классах сущностей.</p> |
| |
| <p>Для каждого класса сущностей мастер создает следующие файлы.</p> |
| |
| <ul> |
| <li>сеансный компонент без сохранения состояния, расширяющий <tt>AbstractFacade.java</tt></li> |
| |
| <li>управляемый компонент JSF в контексте сеанса;</li> |
| |
| <li>каталог, содержащий четыре файла Facelets возможностей CRUD (<code>Create.xhtml</code>, <code>Edit.xhtml</code>, <code>List.xhtml</code> и <code>View.xhtml</code>);</li> |
| </ul> |
| <p>Мастер также создает следующие файлы.</p> |
| <ul> |
| <li>класс <tt>AbstractFacade.java</tt>, содержащий бизнес-логику для создания, извлечения, изменения и удаления экземпляров сущностей</li> |
| <li>служебные классы, используемые управляемыми компонентами JSF (<code>JsfUtil</code>, <code>PaginationHelper</code>);</li> |
| |
| <li>набор свойств для локализованных сообщений и соответствующая запись в файле настройки Faces проекта (создается файл <code>faces-config.xml</code>, если он на данный момент отсутствует);</li> |
| |
| <li>вспомогательные веб-файлы, включая стандартную таблицу стилей для отображения компонентов и файл шаблона Facelets.</li> |
| </ul> |
| |
| <p>Чтобы создать страницу JSF, выполните следующие действия:</p> |
| |
| <ol> |
| <li>В окне 'Проекты' щелкните правой кнопкой мыши узел проекта и выберите 'Создать' > 'Страницы JSF' в 'Классы сущностей', чтобы открыть мастер. Если данная команда отсутствует, выберите пункт "Прочие". После этого в мастере создания файла выберите категорию "JavaServer Faces", затем "Страницы JSF из классов сущностей".) |
| |
| <p> |
| В окне "Доступные классы сущностей" выводится список из семи классов сущностей, имеющихся в этом проекте. В окне не выводятся встраиваемые классы (<code>ClientPK.java</code> и <code>ProjectPK.java</code>).</p></li> |
| |
| <li>Нажмите кнопку "Добавить все" для переноса всех классов в окно "Выбранные классы сущностей". <br> <img alt="Мастер создания страниц JSF из классов сущностей" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/newjsf-wizard.png" title="В мастере создания страниц JSF из классов сущностей отображаются все классы сущностей, содержащиеся в проекте"> <br> Нажмите кнопку "Далее".</li> |
| |
| <li>На третьем экране мастера "Создание страниц JSF и классов" в поле "Пакет сеансного компонента JPA" введите <code>jpa.session</code>.</li> |
| |
| <li>В поле "Пакет классов JSF" введите <code>jsf</code>.</li> |
| |
| <li>В поле "Имя набора локализаций" введите "<code>/resources/Bundle</code>". Будет создан пакет с именем <code>resources</code>, в который входит файл <code>Bundle.properties</code>. (Если поле оставить пустым, набор свойств будет создан в пакете проекта по умолчанию.) <br> <img alt="Мастер создания страниц JSF из классов сущностей. Шаг 3" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/newjsf-wizard2.png" title="Укажите имена пакетов и папок для созданных файлов"> |
| |
| <p class="tips">Для оптимизации правил проекта в среде IDE настройте файлы, созданные в мастере. Для изменения шаблонов, используемых в мастере, щелкните ссылку "Настройка шаблона". <br> <img alt="Раскрывающийся список 'Настройка шаблонов'" class="margin-around" src="../../../images_www/articles/72/web/jsf20-crud/customize-template.png" title="Настройка шаблонов для файлов, созданных мастером"> <br> В целом, для вызова и изменения всех шаблонов, поддерживаемых в среде IDE, используйте диспетчер шаблонов ("Сервис" > "Шаблоны").</p></li> |
| |
| <li>Нажмите кнопку "Завершить". В среде IDE создаются сеансные компоненты без сохранения состояния в пакете <code>jpa.session</code> и управляемые компоненты JSF в контексте сеанса в пакете <code>jsf</code>. Каждый сеансный компонент без сохранения состояния обрабатывает операции для соответствующего класса сущностей, включая создание, правку и удаление экземпляров класса сущностей, с помощью интерфейса Java Persistence API. Каждый управляемый компонент JSF реализует интерфейс <code>javax.faces.convert.Converter</code> и играет роль экземпляров преобразования соответствующего класса сущностей в объекты <code>String</code> и наоборот.</li> |
| </ol> |
| |
| <p>При развертывании узла "Веб-страницы" можно отметить, что в среде IDE была создана папка для каждого класса сущностей. Каждая папка содержит файлы <code>Create.xhtml</code>, <code>Edit.xhtml</code>, <code>List.xhtml</code> и <code>View.xhtml</code>. В среде IDE также изменен файл <code>index.xhtml</code> посредством вставки ссылок на каждую из страниц <code>List.xhtml</code>.</p> |
| |
| <div class="indent"> |
| <img alt="снимок каталога веб-страниц в окне 'Проекты'" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/projects-jsfpages.png" title="Страницы Facelets для всех классов сущностей создаются мастером"> |
| </div> |
| |
| <p>Каждый управляемый компонент JSF относится к четырем соответствующим файлам Facelets и содержит код, вызывающий методы в соответствующем сеансном компоненте.</p> |
| |
| <p>Разверните узел папки <code>resources</code> для поиска таблицы стилей по умолчанию <code>jsfcrud.css</code>, созданной в мастере. При открытии страницы приветствия приложения (<code>index.xhtml</code>) или файла шаблона Facelets (<code>template.xhtml</code>) в редакторе отобразится ссылка на таблицу стилей.</p> |
| |
| <div class="indent"> |
| <pre class="examplecode"><h:outputStylesheet name="css/jsfcrud.css"/></pre> |
| </div> |
| |
| <p>Файл шаблона Facelets используется в каждом из четырех файлов Facelets для каждого класса сущностей.</p> |
| |
| <p>При развертывании узла "Пакеты с исходными файлами" отображаются сеансные компоненты, управляемые компоненты JSF, служебные классы и набор свойств, созданные мастером.</p> |
| |
| <div class="indent"> |
| <img alt="снимок каталога 'Исходные пакеты' в окне 'Проекты'" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/projects-generated-classes70.png" title="снимок каталога 'Исходные пакеты' в окне 'Проекты', в котором отображаются созданные мастером классы сущностей"> |
| </div> |
| |
| <p>Также мастером был создан файл настройки Faces (<code>faces-config.xml</code>) для регистрации местоположения набора свойств. При развертывании узла "Файлы настройки" и открытии <code>faces-config.xml</code> в редакторе XML отобразится следующая запись.</p> |
| |
| <div class="indent"> |
| <pre class="examplecode"><application> |
| <resource-bundle> |
| <base-name>/resources/Bundle</base-name> |
| <var>bundle</var> |
| </resource-bundle> |
| </application></pre> |
| </div> |
| |
| <p>Кроме того, при развертывании нового пакета <code>resources</code> отображается файл <code>Bundle.properties</code>, содержащий сообщения для языка клиента по умолчанию. Сообщения произведены из свойств класса сущностей.</p> |
| |
| <p class="tips">Для добавления нового комплекта свойств щелкните правой кнопкой файл <code>Bundle.properties</code> и выберите 'Настройка'. В диалоговом окне "Средство настройки" можно добавить к приложению новые локали.</p> |
| |
| |
| <br> |
| <h2 id="explore">Анализ приложения</h2> |
| |
| <p>Теперь, при наличии в проекте классов сущностей, сеансных компонентов EJB для управления классами сущностей и внешнего интерфейса на основе JSF для отображения и изменения базы данных, попробуйте выполнить проект и посмотрите результаты.</p> |
| |
| <p>Ниже приведены несколько коротких дополнительных упражнений, которые помогут лучше узнать приложение, а также возможности и функции среды IDE.</p> |
| |
| <ul> |
| <li><a href="#completedProject">Изучение выполненного проекта</a></li> |
| <li><a href="#populateDB">Заполнение базы данных с помощью сценария SQL</a></li> |
| <li><a href="#editorSupport">Изучение поддержки редактора на страницах Facelets</a></li> |
| <li><a href="#dbIntegrity">Изучение целостности базы данных с проверкой поля</a></li> |
| <li><a href="#editEntity">Правка классов сущностей</a></li> |
| </ul> |
| |
| <div class="indent"> |
| <h3 id="completedProject">Изучение выполненного проекта</h3> |
| |
| <ol> |
| <li>Для запуска проекта щелкните правой кнопкой мыши узел проекта в окне 'Проекты' и выберите 'Запустить' или нажмите кнопку 'Запустить проект' ( <img alt="Кнопка 'Выполнить проект'" src="../../../images_www/articles/72/web/jsf20-crud/run-project-btn.png"> ) на главной панели инструментов. |
| |
| <p> |
| При отображении страницы приветствия приложения выводится список ссылок, позволяющих просмотреть записи, которые включены в каждую таблицу базы данных. |
| </p> |
| <img alt="Страница приветствия ConsultingAgency в браузере" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/welcome-page-links.png" title="Ссылки для отображения содержимого баз данных для всех таблиц"> |
| |
| <p> |
| После завершения выполнения всех шагов мастера создания страниц JSF из классов сущностей ссылки добавлены на страницу приветствия (<code>index.xhtml</code>). Они представлены в качестве точек входа на страницы Facelets, обеспечивающие функциональность CRUD в базе данных "Консультационное агентство".</p> |
| |
| <pre class="examplecode"> |
| <h:body> |
| Hello from Facelets |
| <h:form> |
| <h:commandLink action="/address/List" value="Show All Address Items"/> |
| </h:form> |
| <h:form> |
| <h:commandLink action="/billable/List" value="Show All Billable Items"/> |
| </h:form> |
| <h:form> |
| <h:commandLink action="/client/List" value="Show All Client Items"/> |
| </h:form> |
| <h:form> |
| <h:commandLink action="/consultant/List" value="Show All Consultant Items"/> |
| </h:form> |
| <h:form> |
| <h:commandLink action="/consultantStatus/List" value="Show All ConsultantStatus Items"/> |
| </h:form> |
| <h:form> |
| <h:commandLink action="/project/List" value="Show All Project Items"/> |
| </h:form> |
| <h:form> |
| <h:commandLink action="/recruiter/List" value="Show All Recruiter Items"/> |
| </h:form> |
| </h:body></pre></li> |
| |
| <li>Щелкните ссылку "<code>Показать все элементы консультантов</code>". При анализе приведенного выше кода можно отметить, что целевая страница – <code>/consultant/List.xhtml</code>. (В JSF 2.x расширение файла является предполагаемым из-за неявного перехода.) <br> <img alt="Страница 'Consultants'" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/empty-consultants-list.png" title="Таблица 'Consultants' в настоящее вермя пуста"> <br> Текущая база данных не содержит данные примера. Данные можно добавить вручную посредством нажатия ссылки "<code>Create New Consultant</code>" и использования предоставленной веб-формы. При этом инициируется отображение страницы <code>/consultant/Create.xhtml</code>. Для заполнения таблиц данными примера также можно выполнить сценарий SQL в среде IDE. В следующих подразделах рассматриваются оба эти варианта.</li> |
| </ol> |
| |
| <p>Для возврата к списку ссылок на странице приветствия щелкните индексную ссылку. По ссылкам открывается представление данных, хранящихся в каждой таблице базы данных, и инициируется файл <code>List.xhtml</code> для каждой отображаемой папки сущностей. Как будет показано ниже, после внесения данных в таблицу появятся другие ссылки для каждой записи, с помощью которых можно просматривать (<code>View.xhtml</code>), править (<code>Edit.xhmtl</code>) и удалять данные отдельной записи таблицы.</p> |
| |
| <p class="notes"><strong>Примечание.</strong> Если при развертывании приложения произойдет ошибка, см. раздел <a href="#troubleshooting">устранение неполадок</a>. (См. также статью об устранении неполадок в разделе <a href="mysql-webapp.html#troubleshoot">Создание простого веб-приложения с помощью базы данных MySQL</a>.)</p> |
| |
| |
| <h3 id="populateDB">Заполнение базы данных с помощью сценария SQL</h3> |
| |
| <p>Запустите предоставленный сценарий, создающий данные примера для таблиц базы данных. Сценарий (<code>mysql_insert_data_consult.sql</code>) включен в файл ZIP "База данных консультационного агентства", который можно загрузить из <a href="#requiredSoftware">таблицы требуемого программного обеспечения</a>.</p> |
| |
| <p>В зависимости от сервера базы данных, с которым вы работаете (MySQL или JavaDB), можно выполнить запуск предоставленного сценария, создающего данные примера для таблиц базы данных. Для MySQL таким сценарием является <code>mysql_insert_data_consult.sql</code>. Для JavaDB таким сценарием является <code>javadb_insert_data_consult.sql</code>. Оба сценария включены в соответствующие архивы, которые можно загрузить из <a href="#requiredSoftware">таблицы требуемого программного обеспечения</a>.</p> |
| |
| <ol> |
| <li>Выберите в основном меню "Файл" > "Открыть файл", затем перейдите к папке сценария на компьютере. Нажмите кнопку Open ("Открыть"). Файл автоматически открывается в редакторе SQL среды IDE.</li> |
| |
| <li>Убедитесь, что база данных <code>consult</code> выбрана в раскрывающемся списке "Соединение" на панели инструментов редактора SQL. <br> <img alt="снимок редактора SQL и сценария вставки данных" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/run-sql-insert.png" title="Откройте сценарий в редакторе SQL в IDE"> |
| |
| <p> |
| Щелкните правой кнопкой мыши в редакторе и выберите 'Запустить оператор' или нажмите кнопку 'Запустить SQL' ( <img alt="Кнопка "Выполнить SQL"" src="../../../images_www/articles/72/web/jsf20-crud/run-sql-btn.png"> ). Результаты выполнения сценария отображаются в окне вывода.</p></li> |
| |
| <li>Перезапустите сервер приложений GlassFish. Это необходимо для перезагрузки и кэширования новых данных при помощи сервера, содержащихся в базе данных <code>consult</code>. Чтобы это сделать, перейдите на вкладку 'Сервер GlassFish' в окне вывода (на вкладке 'Сервер GlassFish' отображается журнал сервера). Затем нажмите кнопку 'Перезапустить сервер' в левом поле ( <img alt="Кнопка 'Перезапустить сервер'" src="../../../images_www/articles/72/web/jsf20-crud/glassfish-restart.png"> ). Сервер остановится, затем перезапустится.</li> |
| |
| <li>Выполните проект еще раз и щелкните ссылку "<code>Показать все элементы консультантов</code>". Теперь можно заметить, что список больше не пуст. <br> <a href="../../../images_www/articles/72/web/jsf20-crud/consultants-list.png" id="consultantsList" rel="lytebox" title="На странице Facelets отображаются записи, содержащиеся в таблице 'Consultants'"> <img alt="На странице 'Consultants' отображаются записи таблицы" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/consultants-list-small.png"></a> |
| |
| <div class="feedback-box float-left" style="width: 683px;"> |
| |
| <h3>Поддержка баз данных NetBeans</h3> |
| |
| <p>Можно использовать средство просмотра для таблиц базы данных в среде IDE, чтобы отображать и изменять данные таблиц, управляемые непосредственно в базе данных. Например, щелкните правой кнопкой мыши таблицу <code>consultant</code> в окне 'Службы' и выберите 'Просмотреть данные'.</p> |
| |
| <img alt="Окно 'Службы' - щелкните правой кнопкой мыши меню таблицы баз данных" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/view-data.png" title="В контекстном меню таблиц баз данных выберите 'Просмотреть данные'"> |
| |
| <p>Запрос SQL, который используется для выполнения действий, отображается в верхней части редактора, а графическое представление таблицы помещено ниже.</p> |
| |
| <a href="../../../images_www/articles/72/web/jsf20-crud/view-data-table.png" rel="lytebox" title="Используйте графическое представление таблиц базы данных для просмотра и изменения данных таблицы"> <img alt="В редакторе SQL отображаются данные базы данных" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/view-data-table-small.png"></a> |
| |
| <p>Дважды щелкните ячейки таблицы для выполнения внутристрочных изменений данных. Щелкните значок 'Фиксировать записи' ( <img alt="значок 'Фиксировать записи'" src="../../../images_www/articles/72/web/jsf20-crud/commit-records-icon.png"> ) для фиксации изменений базы данных.</p> |
| |
| <p> |
| Графическое представление обеспечивает большую функциональность. Дополнительные сведения см. в разделе <a href="../../docs/ide/database-improvements-screencast.html">Поддержка баз данных в IDE NetBeans</a>.</p> |
| </div> |
| <br style="clear: both;"/></li> |
| </ol> |
| |
| |
| <h3 id="editorSupport">Изучение поддержки редактора на страницах Facelets</h3> |
| |
| <ol> |
| <li>Откройте страницу <code>/consultant/List.xhtml</code> в редакторе. В строке 8 указывается, что визуализация страницы зависит от файла <code>template.xhtml</code> Facelets. |
| |
| <pre class="examplecode"><ui:composition template="/template.xhtml"></pre> |
| |
| <p class="tips">Чтобы отобразить номера строк, щелкните правой кнопкой мыши на левой границе редактора и выберите 'Показать номера строк'.</p></li> |
| |
| <li>С помощью диалогового окна "Переход к файлу" в среде IDE откройте файл <code>template.xhtml</code>. Нажмите сочетание клавиш ALT+SCHIFT+O (CTRL+SHIFT+O в Mac), затем введите <code>template</code>. <br> <img alt="Диалоговое окно 'Перейти к файлу'" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/go-to-file.png" title="С помощью диалогового окна &quot;Переход к файлу&quot; быстро откройте файлы проекта"> |
| |
| <p>Нажмите кнопку "ОК" (или нажмите ENTER).</p></li> |
| |
| <li>В шаблоне применяются теги <code><ui:insert></code> для вставки содержимого из других файлов в заголовок и тело. Установите курсор на тег <code><ui:insert></code>, затем нажмите сочетание клавиш CTRL+ПРОБЕЛ для вызова всплывающего окна документации. <br> <img alt="Всплывающее окно документации отображается в редакторе" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/doc-popup.png" title="Нажмите сочетание клавиш CTRL+ПРОБЕЛ для вызова всплывающего окна документации в тегах Facelets"> |
| |
| <p>Для вызова всплывающего окна документации можно нажать сочетание клавиш CTRL+ПРОБЕЛ, установив курсор на тегах JSF и соответствующих атрибутах. Отображаемая документация взята из описаний, предоставленных в официальной <a href="http://javaserverfaces.java.net/nonav/docs/2.1/vdldocs/facelets/index.html">Документации о библиотеке тегов JSF</a>.</p></li> |
| |
| <li>Вернитесь к файлу <code>List.xhtml</code> (нажмите CTRL+TAB). Теги <code><ui:define></code> используются для определения содержимого, которое применяется в заголовке и теле шаблона. Этот шаблон используется для всех четырех файлов Facelets (<code>Create.xhtml</code>, <code>Edit.xhtml</code>, <code>List.xhtml</code> и <code>View.xhtml</code>), созданных для каждого класса сущностей.</li> |
| |
| <li>Установите курсор на одном из выражений на языке выражений, используемых для локализованных сообщений, содержащихся в файле <code>Bundle.properties</code>. Для просмотра локализованного сообщения нажмите сочетание клавиш CTRL+ПРОБЕЛ. <br> <a href="../../../images_www/articles/72/web/jsf20-crud/localized-messages.png" rel="lytebox" title="Просмотрите локализованные сообщения с помощью поддержки автозавершения кода редактора"> <img alt="Всплывающее окно автозавершения кода сообщений от набора свойств" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/localized-messages-small.png"></a> |
| |
| <p>На приведенном выше изображении можно заметить, что выражение на языке выражений разрешено в списке "<code>List</code>", который применяется для заголовка шаблона и проверяется из отображаемой в браузере страницы.</p></li> |
| |
| <li>Выполните прокрутку до конца файла и найдите код для ссылки <code>Create New Consultant</code> (строка 92). Это выглядит следующим образом: |
| |
| <pre class="examplecode"> |
| <h:commandLink action="#{consultantController.prepareCreate}" value="#{bundle.ListConsultantCreateLink}"/></pre></li> |
| |
| <li>Для вызова всплывающего окна документации нажмите сочетание клавиш CTRL+ПРОБЕЛ на атрибуте <code>action</code> для <code>commandLink</code>. <br><br> Атрибут <code>action</code> указывает на метод, обрабатывающий запрос при щелчке ссылки в браузере. Предоставлена следующая документация: <br><br> |
| <div class="indent" style="width:680px"> |
| <em>Компонент MethodExpression определяет вызываемую операцию приложения при его активации пользователем. Выражение должно определять общедоступный метод, который не принимает параметры и возвращает объект (метод toString() которого вызывается для получения логического результата), передаваемый в NavigationHandler для этого приложения.</em></div> |
| |
| <br> Другими словами, значение <code>action</code> обычно относится к методу в управляемом компоненте JSF, который имеет значение <code>String</code>. Затем строка используется в <code>NavigationHandler</code> JSF для передачи запроса в соответствующее представление. Проверка этого осуществляется при выполнении следующих действий.</li> |
| |
| <li>Установите курсор на <code>consultantController</code> и нажмите сочетание клавиш CTRL+ПРОБЕЛ. Функция автозавершения кода в редакторе указывает на то, что <code>consultantController</code> является управляемым компонентом JSF. <br> <img alt="Автозавершение кода вызвано в редакторе" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/code-completion-managed-bean.png" title="Автозавершение кода обеспечено для управляемых компонентов JSF"></li> |
| |
| <li>Переместите курсор на <code>prepareCreate</code> и нажмите сочетание клавиш CTRL+ПРОБЕЛ. При вызове функции автозавершения кода выводится список методов, содержащихся в управляемом компоненте <code>ConsultantController</code>. <br> <img alt="Автозавершение кода вызвано в редакторе" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/code-completion-properties.png" title="Автозавершение кода обеспечено для методов классов"></li> |
| |
| <li>Нажмите CTRL (&#8984 в Mac), затем наведите указатель мыши на <code>prepareCreate</code>. Будет создана ссылка, с помощью которой можно перейти непосредственно к методу <code>prepareCreate()</code> в управляемом компоненте <code>ConsultantController</code>. <br> <img alt="Ссылка отображается в редакторе" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/editor-navigation.png" title="Используйте навигацию в редакторе для быстрого перехода по исходному коду"></li> |
| |
| <li>Щелкните ссылку и просмотрите метод <code>prepareCreate()</code> (отображаемый ниже). |
| |
| <pre class="examplecode"> |
| public String prepareCreate() { |
| current = new Consultant(); |
| selectedItemIndex = -1; |
| return "Create"; |
| }</pre> |
| |
| Метод возвращает <code>Create</code>. Метод <code>NavigationHandler</code> собирает информацию в фоновом режиме и применяет строку <code>Create</code> в пути для открытия представления, отправленного в ответ на запрос: <code>/consultant/<strong>Create</strong>.xhtml</code>. (В JSF 2.x расширение файла является предполагаемым из-за неявного перехода.)</li> |
| </ol> |
| |
| |
| <h3 id="dbIntegrity">Изучение целостности базы данных с проверкой поля</h3> |
| |
| <ol> |
| <li>На <a href="#consultantsList">странице "Consultants List"</a> в браузере щелкните ссылку "<code>Create New Consultant</code>". Как показано в предыдущем подразделе, это инициирует визуализацию страницы <code>/consultant/Create.xhtml</code>.</li> |
| |
| <li>Введите в форму следующие подробные сведения. На данный момент оставьте оба поля <code>RecruiterId</code> и <code>StatusId</code> пустыми. <br><br> |
| <table> |
| <tbody> |
| <tr> |
| <th class="tblheader" scope="col">Поле</th> |
| <th class="tblheader" scope="col">Значение</th> |
| </tr> |
| <tr> |
| <td class="tbltd1">Id консультанта</td> |
| <td class="tbltd1">2</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">Эл. почта</td> |
| <td class="tbltd1">jack.smart@jsfcrudconsultants.com</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">Пароль</td> |
| <td class="tbltd1">jack.smart</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">Почасовая ставка</td> |
| <td class="tbltd1">75</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">Оплачиваемая почасовая ставка</td> |
| <td class="tbltd1">110</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">Дата принятия на работу</td> |
| <td class="tbltd1">07/22/2008</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">Резюме</td> |
| <td class="tbltd1">У меня большой опыт работы консультантом. Примите меня на эту должность, и вы не разочаруетесь!</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">RecruiterId</td> |
| <td class="tbltd1">---</td> |
| </tr> |
| <tr> |
| <td class="tbltd1">StatusId</td> |
| <td class="tbltd1">---</td> |
| </tr> |
| </tbody> |
| </table></li> |
| |
| <li>Нажмите кнопку "Сохранить". При подобном заполнении поле <code>StatusId</code> будет отмечено ошибкой проверки. <br> <img alt="Создайте страницу 'New Consultant', содержащую образец данных" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/create-new-consultant.png" title="Введите в форму образец данных"> <br> Почему это произошло? Повторно проверьте <a href="#er-diagram">диаграмму "сущность/отношение" для базы данных консультационного агентства</a>. Как указано выше в <a href="#relationships">таблице связей</a>, в таблицах <code>CONSULTANT</code> и <code>CONSULTANT_STATUS</code> совместно используется ненулевое отношение "один ко многим". Поэтому каждая запись в таблице <code>CONSULTANT</code> должна содержать ссылку на запись в таблице <code>CONSULTANT_STATUS</code>. Это отмечено во внешнем ключе <code>consultant_fk_consultant_status</code>, который имеет ссылки на две таблицы. |
| |
| <p class="tips">Внешние ключи, хранящиеся в таблицах, можно просмотреть посредством развертывания узла "Внешние ключи" таблицы в окне "Службы" (CTRL+5; &#8984+5 на компьютере Mac).</p> |
| |
| <img alt="В окне 'Службы' - внешние ключи для таблицы 'consultant'" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/consultant-fk.png" title="Проверьте атрибуты внешних ключей в окне 'Службы'"></li> |
| |
| <li>Для устранения ошибки проверки выберите <code>entity.ConsultantStatus[statusId=A]</code> в раскрывающемся списке <code>StatusId</code>. <br><br> <strong class="notes">Примечание. </strong>Поле <code>RecruiterId</code> можно оставить пустым. Как указано на <a href="#er-diagram">диаграмме "сущность/отношение" для базы данных</a>, между таблицами <code>CONSULTANT</code> и <code>RECRUITER</code> существует нулевое отношение "один ко многим", что означает, что создавать отношение между записями в таблице <code>CONSULTANT</code> с записью <code>RECRUITER</code> не требуется.</li> |
| |
| <li>Нажмите кнопку "Сохранить". На экран выводится сообщение об успешном сохранении записи consultant. При щелчке ссылки <code>Show All Consultant Items</code> в таблице появится новая запись.</li> |
| </ol> |
| |
| <p>Как правило, на созданных страницах Facelets отображаются ошибки вводимой пользователем информации:</p> |
| |
| <ul> |
| <li>пустые поля для ненулевых ячеек таблицы;</li> |
| <li>изменения данных, которые нельзя изменять (например, первичные ключи);</li> |
| <li>вставка данных неверного типа;</li> |
| <li>изменения данных, когда представление пользователя больше не синхронизируется с базой данных.</li> |
| </ul> |
| |
| |
| <h3 id="editEntity">Правка классов сущностей</h3> |
| |
| <p>В предыдущем подразделе был показан не совсем интуитивно понятный параметр <code>entity.ConsultantStatus[statusId=A]</code> в раскрывающемся списке <code>StatusId</code>. Необходимо учитывать, что текст, отображаемый для каждой позиции в этом раскрывающемся списке, является строковым представлением каждой обнаруженной сущности <code>ConsultantStatus</code> (т.е., вызывается метод <code>toString()</code> класса сущностей).</p> |
| |
| <p>В этом подразделе описаны способы использования автозавершения кода в редакторе, документация и поддержка функции переходов, чтобы сделать такой вывод. Кроме того, подготовка наиболее интуитивно понятного сообщения для раскрывающегося списка.</p> |
| |
| <ol> |
| <li id="markup">Откройте в редакторе файл <code>/consultant/Create.xhtml</code>. Это форма "Create New Consultant", отображаемая в браузере. Выполните прокрутку вниз до кода раскрывающегося списка <code>StatusId</code> (выделено ниже <strong>жирным шрифтом</strong>). |
| |
| <pre class="examplecode"> |
| <h:outputLabel value="#{bundle.CreateConsultantLabel_resume}" for="resume" /> |
| <h:inputTextarea rows="4" cols="30" id="resume" value="#{consultantController.selected.resume}" title="#{bundle.CreateConsultantTitle_resume}" /> |
| <strong><h:outputLabel value="#{bundle.CreateConsultantLabel_statusId}" for="statusId" /> |
| <h:selectOneMenu id="statusId" value="#{consultantController.selected.statusId}" title="#{bundle.CreateConsultantTitle_statusId}" required="true" requiredMessage="#{bundle.CreateConsultantRequiredMessage_statusId}"> |
| <f:selectItems value="#{consultantStatusController.itemsAvailableSelectOne}"/> |
| </h:selectOneMenu></strong> |
| <h:outputLabel value="#{bundle.CreateConsultantLabel_recruiterId}" for="recruiterId" /> |
| <h:selectOneMenu id="recruiterId" value="#{consultantController.selected.recruiterId}" title="#{bundle.CreateConsultantTitle_recruiterId}" > |
| <f:selectItems value="#{recruiterController.itemsAvailableSelectOne}"/> |
| </h:selectOneMenu> |
| </h:panelGrid></pre></li> |
| |
| <li>Проверьте атрибут <code>value</code>, применяемый к тегу <code><f:selectItems></code>. Атрибут <code>value</code> определяет текст, отображаемый для каждой позиции в раскрывающемся списке. <br><br> Нажмите сочетание клавиш CTRL+ПРОБЕЛ, установив курсор на <code>itemsAvailableSelectOne</code>. Автозавершение кода в редакторе указывает, что метод <code>getItemsAvailableSelectOne()</code> для <code>ConsultantStatusController</code> возвращает массив объектов <code>SelectItem</code>. <br> <img alt="Автозавершение кода вызвано в редакторе" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/code-completion-returned-object.png" title="Автозавершение кода отображает возвращаемые классы для методов"></li> |
| |
| <li>Нажмите CTRL (&#8984 в Mac), затем наведите указатель мыши на <code>itemsAvailableSelectOne</code>. Создается ссылка, позволяющая переходить непосредственно к методу <code>getItemsAvailableSelectOne()</code> в исходном коде сущностей <code>ConsultantStatus</code>. Щелкните эту ссылку.</li> |
| |
| <li>Установите курсор на значении возврата <code>SelectItem[]</code> в сигнатуре метода и нажмите сочетание клавиш CTRL+ПРОБЕЛ для вызова всплывающего окна документации. <br> <img alt="Всплывающее окно документации вызвано в классе Java" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/documentation-select-item.png" title="Для вызова поддержки документации нажмите сочетание клавиш CTRL+ПРОБЕЛ."> |
| |
| <p class="tips">Щелкните значок веб-браузера ( <img alt="Значок веб-браузера " src="../../../images_www/articles/72/web/jsf20-crud/web-browser-icon.png"> ) в окне документации, чтобы открыть Javadoc во внешнем веб-браузере.</p> |
| |
| Итак, класс <code>SelectItem</code> относится к инфраструктуре JSF. Компонент <code>UISelectOne</code>, как упоминалось в документации, представлен тегом <code><h:selectOneMenu></code> из разметки, проверенной выше в <a href="#markup">Шаге 1</a>.</li> |
| |
| <li>Нажмите CTRL (&#8984 в Mac), затем наведите указатель мыши на <code>findAll()</code>. Появится всплывающее окно, отображающее сигнатуру метода. <br> <img alt="Всплывающее окно сигнатуры метода" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/method-signature.png" title="Просмотрите всплывающее окно сигнатур методов в редакторе"> <br> Здесь можно отметить, что <code>ejbFacade.findAll()</code> возвращает <code>List</code> объектов <code>ConsultantStatus</code>.</li> |
| |
| <li>Перейдите к <code>JsfUtil.getSelectItems</code>. Наведите указатель мыши на <code>getSelectItems</code> и нажмите CTRL (&#8984 на компьютере Mac), затем щелкните появившуюся ссылку. <br><br> <strong class="notes">Примечание. </strong>Помните, что <code>JsfUtil</code> является одним из классов служебных программ, созданных при завершении <a href="#jsfPagesEntityClasses">страниц JSF из мастера классов логических объектов</a>. <br><br> Этот метод организует цикл по списку сущностей (т.е., по списку <code>List</code> объектов <code>ConsultantStatus</code>) и создает <code>SelectItem</code> для каждой позиции. Как показано ниже (<strong>выделено жирным шрифтом</strong>), каждая позиция <code>SelectItem</code> создана с помощью объекта сущностей и <em>метки</em> объекта. |
| |
| <pre class="examplecode"> |
| public static SelectItem[] getSelectItems(List<?> entities, boolean selectOne) { |
| int size = selectOne ? entities.size() + 1 : entities.size(); |
| SelectItem[] items = new SelectItem[size]; |
| int i = 0; |
| if (selectOne) { |
| items[0] = new SelectItem("", "---"); |
| i++; |
| } |
| <strong>for (Object x : entities) { |
| items[i++] = new SelectItem(x, x.toString()); |
| }</strong> |
| return items; |
| }</pre> |
| <p>Эта метка создана с помощью метода <code>toString()</code> сущностей и является представлением объекта, отображаемым в этом ответе. (См. определение документации Javadoc для конструктора <code>SelectItem(значение java.lang.Object, метка java.lang.String)</code>.)</p> |
| |
| <p> |
| После проверки того, что методом <code>toString()</code> сущности является метод, отображаемый в браузере при просмотре позиций в раскрывающемся списке, измените метод <code>ConsultantStatus</code> <code>toString()</code>.</p> |
| </li> |
| |
| <li>Откройте класс сущностей <code>ConsultantStatus</code> в редакторе. Измените метод <code>toString</code> для возврата <code>statusId</code> и <code>description</code>. Это свойства записей, соответствующие двум столбцам таблицы <code>CONSULTANT_STATUS</code>. |
| |
| <pre class="examplecode">public String toString() { |
| return <strong>statusId + ", " + description;</strong> |
| }</pre></li> |
| |
| <li>Выполните проект еще раз. При отображении в браузере страницы приветствия щелкните ссылку <code>Show All Consultant Items</code>, затем нажмите <code>Create New Consultant</code>. |
| |
| <p> |
| Просмотрите раскрывающийся список <code>StatusId</code>. Теперь на экран будет выведен идентификатор состояния и описание записи, содержащейся в таблице <code>CONSULTANT_STATUS</code> базы данных.</p> |
| |
| <img alt="В браузере отображается раскрывающийся список StatusId" class="margin-around b-all" src="../../../images_www/articles/72/web/jsf20-crud/drop-down.png" title="В раскрывающемся списке StatusId отображаются элементы в соответствии с методом toString() сущности ConsultantStatus"> |
| </li> |
| </ol> |
| </div> |
| |
| |
| |
| <h2 id="troubleshooting">Устранение проблем</h2> |
| <p>В зависимости от конфигурации при развертывании приложения на сервере может произойти ошибка. В этом случае в окне "Результаты" отображается следующее сообщение. |
| </p> |
| |
| <pre class="examplecode">GlassFish Server 4 is running. |
| In-place deployment at /MyDocuments/ConsultingAgency/build/web |
| GlassFish Server 4, deploy, null, false |
| /MyDocuments/ConsultingAgency/nbproject/build-impl.xml:1045: The module has not been deployed. |
| See the server log for details.</pre> |
| <p>Основная причина таких ошибок - проблемы при создании ресурсов JDBC на сервере. В этом случае на вкладке "Журнал сервера" в окне "Результаты" может отобразиться следующее или аналогичное сообщение. |
| </p> |
| |
| <pre class="examplecode">Severe: Exception while preparing the app : Invalid resource : jdbc/consult__pm |
| com.sun.appserv.connectors.internal.api.ConnectorRuntimeException: Invalid resource : jdbc/consult__pm</pre> |
| |
| <p class=tips>Если вкладка "Журнал сервера" отсутствует, ее можно добавить. Для этого щелкните правой кнопкой мыши узел GlassFish Server в окне "Службы" и выберите "Просмотр журнала доменного сервера".</p> |
| |
| <p>Для этого приложения требуются два ресурса JDBC:</p> |
| <ul> |
| <li>Ресурс JDBC или источник данных. Поиск ресурса JDBC в приложении осуществляется посредством поиска JNDI. Если посмотреть на элемент постоянного соединения (<code>persistence.xml</code>), можно увидеть, что имя JNDI для источника данных JTA этого приложения - <code>jdbc/consult</code>. |
| <p>Ресурс JDBC определяет текущий пул соединений, используемый приложением.</p></li> |
| <li>Пул соединений JDBC. Пул соединений определяет параметры подключения к базе данных, в том числе местоположение, имя пользователя и пароль. Для данного приложения используется пул соединений <code>consultPool</code>.</li> |
| </ul> |
| <p>Ресурс JDBC и пул соединений указываются в файле <code>glassfish-resources.xml</code>. Чтобы открыть файл <code>glassfish-resources.xml</code> в редакторе, разверните узел "Ресурсы сервера" в окне "Проекты" и дважды щелкните этот файл. Файл имеет примерно следующий вид.</p> |
| |
| <pre class="examplecode"> |
| <?xml version="1.0" encoding="UTF-8"?> |
| <!DOCTYPE resources PUBLIC "-//GlassFish.org//DTD GlassFish Application Server 3.1 Resource Definitions//EN" "http://glassfish.org/dtds/glassfish-resources_1_5.dtd"> |
| <resources> |
| <jdbc-connection-pool allow-non-component-callers="false" associate-with-thread="false" connection-creation-retry-attempts="0" connection-creation-retry-interval-in-seconds="10" connection-leak-reclaim="false" connection-leak-timeout-in-seconds="0" connection-validation-method="auto-commit" datasource-classname="com.mysql.jdbc.jdbc2.optional.MysqlDataSource" fail-all-connections="false" idle-timeout-in-seconds="300" is-connection-validation-required="false" is-isolation-level-guaranteed="true" lazy-connection-association="false" lazy-connection-enlistment="false" match-connections="false" max-connection-usage-count="0" max-pool-size="32" max-wait-time-in-millis="60000" name="consultPool" non-transactional-connections="false" ping="false" pool-resize-quantity="2" pooling="true" res-type="javax.sql.DataSource" statement-cache-size="0" statement-leak-reclaim="false" statement-leak-timeout-in-seconds="0" statement-timeout-in-seconds="-1" steady-pool-size="8" validate-atmost-once-period-in-seconds="0" wrap-jdbc-objects="false"> |
| <property name="serverName" value="localhost"/> |
| <property name="portNumber" value="3306"/> |
| <property name="databaseName" value="consult"/> |
| <property name="User" value="root"/> |
| <property name="Password" value="nb"/> |
| <property name="URL" value="jdbc:mysql://localhost:3306/consult?zeroDateTimeBehavior=convertToNull"/> |
| <property name="driverClass" value="com.mysql.jdbc.Driver"/> |
| /<jdbc-connection-pool> |
| <jdbc-resource enabled="true" jndi-name="jdbc/consult" object-type="user" pool-name="consultPool"/> |
| /<resources></pre> |
| |
| <p>Как видите, указанный в файле <code>glassfish-resources.xml</code> ресурс JDBC <code>jdbc/consult</code> определяет <code>consultPool</code> как имя пула соединений. Также здесь видны свойства <code>consultPool</code>. Для данного приложения в файле <code>glassfish-resources.xml</code> указан только один источник данных и только один пул соединений. Иногда возникает необходимость указать дополнительные ресурсы, например, временное хранилище данных, используемое только для разработки или тестирования.</p> |
| |
| <p>Если ресурс JDBC и пул соединений не созданы на сервере автоматически при запуске приложения, их можно создать вручную в консоли администрирования GlassFish.</p> |
| |
| <ol> |
| <li>Если файл <code>glassfish-resources.xml</code> еще не открыт, откройте его в редакторе. |
| <p>Для создания ресурса JDBC и пула соединений потребуются значения свойств, указанные в файле <code>glassfish-resources.xml</code>.</p></li> |
| <li>Щелкните правой кнопкой мыши узел GlassFish Server в окне "Службы" и выберите пункт меню "Открыть консоль администрирования домена". Консоль GlassFish откроется в браузере.</li> |
| <li>На панели "Общие задачи" в консоли GlassFish разверните узел <strong>JDBC</strong>, а также узлы <strong>Ресурсы JDBC</strong> и <strong>Пулы соединений JDBC</strong>. <br> <a href="../../../images_www/articles/80/web/jsf20-crud/gf-admin-console-lg.png"> <img alt="Вид консоли администрирования GlassFish в браузере" class="margin-around b-all" src="../../../images_www/articles/80/web/jsf20-crud/gf-admin-console-sm.png" title="Нажмите, чтобы просмотреть изображение консоли администрирования GlassFish в полном размере"></a> |
| <p>В консоли отображаются текущие ресурсы JDBC, зарегистрированные на сервере. Если в списке под узлом JDBC на панели навигации "Общие задачи" отсутствуют ресурсы <code>jdbc/consult</code> и <code>consultPool</code>, их необходимо создать. Некоторые ресурсы JDBC , созданные по умолчанию при установке сервера, отображаются в виде дочерних узлов. </p></li> |
| <li>Выберите узел <strong>Пулы соединений JDBC</strong>, затем в разделе "Новый пул соединений JDBC" нажмите "Создать". <br> <img alt="Вид раздела "Новый пул соединений JDBC" в браузере" class="margin-around b-all" src="../../../images_www/articles/80/web/jsf20-crud/gf-new-jdbc-pool1.png" title="Раздел "Новый пул соединений JDBC" в консоли администрирования GlassFish"></li> |
| <li>Укажите <strong>consultPool</strong> в качестве имени пула, выберите <strong>javax.sql.ConnectionPoolDataSource</strong> в списке "Тип ресурса", затем выберите <strong>MySql</strong> в списке "Поставщик драйверов базы данных". Нажмите кнопку "Далее".</li> |
| <li>На экране 2 укажите значения свойств <strong>URL</strong>, <strong>имя пользователя</strong> и <strong>пароль</strong>, найденные в файле. Нажмите "Готово". <br> <img alt="Вид второй панели в разделе "Новый пул соединений JDBC" в браузере" class="margin-around b-all" src="../../../images_www/articles/80/web/jsf20-crud/gf-new-jdbc-pool2.png" title="Панель "Новый пул соединений JDBC" в консоли администрирования GlassFish"> |
| <p class="tips">Значения свойств можно найти в файле <code>glassfish-resources.xml</code>.</p> |
| <p>При нажатии на кнопку "Готово" на сервере создается новый пул соединений, и под узлом "Пулы соединений JDBC" в консоли появляется соответствующий узел.</p></li> |
| <li>Выберите узел <strong>Ресурсы JDBC</strong> на панели навигации "Общие задачи" и нажмите "Создать".</li> |
| <li>Укажите <strong>jdbc/consult</strong> в качестве имени JNDI и выберите <strong>consultPool</strong> в списке "Имя пула". Нажмите OK. <br> <img alt="Вид раздела "Новый ресурс JDBC" в браузере" class="margin-around b-all" src="../../../images_www/articles/80/web/jsf20-crud/gf-new-jdbc-resource.png" title="Раздел "Новый ресурс JDBC" в консоли администрирования GlassFish"> |
| <p>При нажатии на кнопку "Готово" на сервере создается новый ресурс JDBC, и под узлом "Ресурсы JDBC" в консоли появляется соответствующий узел.</p> |
| <p>В окне "Службы" в IDE раскройте узел "Ресурсы", находящийся под узлом GlassFish Server, и убедитесь, что в IDE добавлены новые ресурсы. Возможно, для отображения изменений потребуется обновить представление (щелкните правой кнопкой мыши узел "Ресурсы" и выберите "Обновить").</p> |
| <img alt="снимок окна "Службы" в IDE" class="margin-around b-all" src="../../../images_www/articles/80/web/jsf20-crud/gf-services-jdbc-resources.png" title="Ресурсы JDBC в окне "Службы" в IDE"></li> |
| </ol> |
| <p>Другие советы по устранению проблем с MySQL и IDE см. в следующих документах:</p> |
| <ul> |
| <li>Учебный курс <a href="../ide/mysql.html">Подключение к базе данных MySQL</a>.</li> |
| <li>Статья об устранении неполадок в разделе <a href="mysql-webapp.html#troubleshoot">Создание простого веб-приложения с помощью базы данных MySQL</a></li> |
| </ul> |
| |
| |
| <div class="feedback-box"> |
| <a href="/about/contact_form.html?to=3&subject=Feedback:%20Creating%20a%20JSF%202.0%20CRUD%20Application">Отправить отзыв по этому учебному курсу</a> |
| </div> |
| |
| <br style="clear:both;" /> |
| |
| |
| <h2 id="seealso">Дополнительные сведения</h2> |
| |
| <p>Подробнее о JSF 2.x см. в следующих ресурсах.</p> |
| |
| <div class="indent"> |
| <h3>Статьи и учебные курсы по NetBeans</h3> |
| |
| <ul> |
| <li><a href="jsf20-intro.html">Введение в JavaServer Faces 2.x в IDE NetBeans</a></li> |
| <li><a href="jsf20-support.html">Поддержка JSF 2.x в IDE NetBeans</a></li> |
| <li><a href="../../samples/scrum-toys.html">Scrum Toys – полный пример приложения JSF 2.0</a></li> |
| <li><a href="../javaee/javaee-gettingstarted.html">Начало работы с приложениями Java EE</a></li> |
| <li><a href="../../trails/java-ee.html">Учебная карта по Java EE и Java Web</a></li> |
| </ul> |
| |
| <h3>Внешние ресурсы</h3> |
| |
| <ul> |
| <li><a href="http://www.oracle.com/technetwork/java/javaee/javaserverfaces-139869.html">Технология JavaServer Faces</a> (официальная домашняя страница)</li> |
| <li><a href="http://jcp.org/aboutJava/communityprocess/final/jsr314/index.html">Спецификация JSR 314 для JavaServer Faces 2.0</a></li> |
| <li>Глава <a href="http://docs.oracle.com/javaee/7/tutorial/doc/jsf-intro.htm">Технология JavaServer Faces</a> в учебном курсе по Java EE 7</li> |
| <li><a href="http://javaserverfaces.dev.java.net/">GlassFish Project Mojarra</a> (официальный пример реализации JSF 2.х)</li> |
| <li><a href="http://forums.oracle.com/forums/forum.jspa?forumID=982">Интернет-форум OTN: JavaServer Faces</a></li> |
| <li><a href="http://www.jsfcentral.com/">JSF Central</a></li> |
| </ul> |
| |
| <h3>Блоги</h3> |
| |
| <ul> |
| <li><a href="http://www.java.net/blogs/edburns/">Эд Бернс (Ed Burns)</a></li> |
| <li><a href="http://www.java.net/blogs/driscoll/">Джим Дрисколл (Jim Driscoll)</a></li> |
| </ul> |
| </div> |
| |
| </body> |
| </html> |