Статьи

Создание веб-приложения на Java с использованием Hibernate с Spring

В этом посте будет показано, как создать приложение для зачисления студентов с помощью MYSQL DB с Hibernate ORM в среде Spring. Это простое приложение, которое предназначено для сбора входных данных от пользователя во время регистрации, сохранения данных в базе данных MYSQL и аутентификации при входе.

1. Создание проекта веб-приложения Java с использованием шаблона Maven

Для начала в IDE создайте проект Java Maven с шаблоном maven-archetype-webapp (отфильтруйте каталог на основе строки «webapp»), указав соответствующие значения для GroupId и Artifact Id для проекта. Пример структуры каталогов веб-приложения показан ниже со стандартным дескриптором развертывания web.xml и Maven pom.xml.

SpringLayout

2. Обновите pom.xml

Чтобы вышеуказанный проект Maven Java Web Application поддерживал Hibernate ORM в среде Spring, добавьте следующие зависимости в существующий файл pom.xml.

  • jstl, spring-webmvc и servlet-api (для поддержки Spring)
  • mysql-connector-java (для поддержки MYSQL)
  • spring-jdbc (для доступа к данным с помощью JDBC Spring)
  • Spring-Orm (для доступа к данным ORM с помощью Spring)
  • spring-data-jpa (для поддержки JPA)
  • hibernate-validator и hibernate-entitymanager (для поддержки Hibernate)
  • JTA (для поддержки транзакций)
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
<dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-webmvc</artifactId>
      <version>3.2.4.RELEASE</version>
    </dependency>
    <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>servlet-api</artifactId>
      <version>2.5</version>
      <scope>provided</scope>
    </dependency>
    <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>jstl</artifactId>
      <version>1.2</version>
    </dependency>
    <dependency>
      <groupId>mysql</groupId>
      <artifactId>mysql-connector-java</artifactId>
      <version>5.1.21</version>
    </dependency>
    <dependency>
      <groupId>org.hibernate</groupId>
      <artifactId>hibernate-validator</artifactId>
      <version>4.2.0.Final</version>
    </dependency>
    <dependency>
      <groupId>org.hibernate</groupId>
      <artifactId>hibernate-entitymanager</artifactId>
      <version>4.1.9.Final</version>
    </dependency>
    <dependency>
      <groupId>javax.transaction</groupId>
      <artifactId>jta</artifactId>
      <version>1.1</version>
    </dependency>
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-jdbc</artifactId>
      <version>3.2.0.RELEASE</version>
    </dependency>
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-orm</artifactId>
      <version>3.2.0.RELEASE</version>
    </dependency>
    <dependency>
      <groupId>org.springframework.data</groupId>
      <artifactId>spring-data-jpa</artifactId>
      <version>1.3.0.RELEASE</version>
      <exclusions>
          <exclusion>
              <groupId>org.springframework</groupId>
              <artifactId>spring-aop</artifactId>
          </exclusion>
      </exclusions>
    </dependency>

3. Изменить web.xml

Измените содержимое файла web.xml, включив в него следующее:

  • Сервлет и указать расположение файла конфигурации для того же. В этом примере файл конфигурации с именем springConfig.xml создается в папке WEB-INF / config в макете проекта.
  • Отображение сервлета для сопоставления сервлета, созданного на предыдущем шаге, который должен вызываться, когда клиент указывает URL-адрес, соответствующий шаблону URL-адреса.
  • ContextLoaderListener для интеграции Spring с веб-приложением и предоставления contextConfigLocation, где находятся файлы контекста для JPA.
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5"
 
<servlet>
  <servlet-name>studentHibernateServlet</servlet-name>
  <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
  <init-param>
      <param-name>contextConfigLocation</param-name>
      <param-value>/WEB-INF/config/servletConfig.xml</param-value>
  </init-param>
</servlet>
 
<servlet-mapping>
  <servlet-name>studentHibernateServlet</servlet-name>
  <url-pattern>*.html</url-pattern>
</servlet-mapping>
 
<context-param>
  <param-name>contextConfigLocation</param-name>
  <param-value>classpath:/jpaContext.xml</param-value>
</context-param>
 
<listener>
  <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
 
  <display-name>Archetype Created Web Application</display-name>
</web-app>

4. Создайте файл конфигурации Spring

Создайте файл конфигурации Spring Bean в папке WEB-INF / config. Если STS (Spring Tool Suite) является IDE, включите пространство имен context и mvc. ServletConfig.xml будет таким, как показано ниже

После включения необходимых пространств имен добавьте следующее (между тегами <beans> и </ beans>), чтобы указать, что приложение управляется аннотациями и является базовым пакетом для сканирования компонента контекста.

1
2
3
<mvc:annotation-driven />
 
<context:component-scan base-package="com.github.elizabetht" />

Включите bean-компонент InternalResourceViewResolver для Spring, чтобы найти файлы jsp

1
2
3
4
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
  <property name="prefix" value="/WEB-INF/jsp/" />
  <property name="suffix" value=".jsp" />
</bean>

Включите компонент для указания файла свойств (подробнее об этом позже), который будет использоваться для хранения пользовательских сообщений или свойств. Следующая конфигурация позволяет создать файл свойств с именем messages.properties в папке src / main / resources в проекте.

1
2
3
<bean id="messageSource" class="org.springframework.context.support.ResourceBundleMessageSource">
  <property name="basename" value="messages" />
</bean>

5. Создайте файл persistence.xml

Создайте файл с именем persistence.xml в папке src / main / resources / META-INF в проекте, чтобы определить единицу сохранения, требуемую JPA. Добавьте следующее в файл persistence.xml, чтобы определить единицу хранения с именем punit.

1
2
3
4
5
6
7
8
9
  version="2.0">
 
  <persistence-unit name="punit">
  </persistence-unit>
 
</persistence>

6. Создайте jpaContext.xml

Как определено в файле web.xml, создайте файл с именем jpaContext.xml в папке src / main / resources в проекте, чтобы определить конфигурации, связанные с JPA и Hibernate. Обратите внимание, что любой файл, созданный в папке src / main / resources в проекте maven, будет автоматически добавлен Maven в путь к классам. Если STS (Spring Tool Suite) является IDE, включите пространства имен context, jpa и tx. Файл jpaContext.xml будет таким, как показано ниже

После включения необходимых пространств имен добавьте следующее (между тегами <beans> и </ beans>), чтобы указать, что приложение управляется аннотациями и является базовым пакетом для сканирования репозиториев jpa.

1
2
3
<context:annotation-config />
 
<jpa:repositories base-package="com.github.elizabetht.repository" />

Затем включите bean-компонент PersistenceAnnotationBeanPostProcessor. Это необходимо для обработки модуля сохраняемости, аннотаций постоянства и для ввода ресурсов, связанных с JPA.

1
<bean class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor" />

Включите компонент для EntityManagerFactory, в котором перечислены различные свойства / ресурсы, связанные с JPA.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
      <property name="persistenceUnitName" value="punit" />
      <property name="dataSource" ref="dataSource" />
      <property name="jpaVendorAdapter">
          <bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
              <property name="showSql" value="true" />
          </bean>
      </property>
      <property name="jpaPropertyMap">
          <map>
              <entry key="hibernate.dialect" value="org.hibernate.dialect.MySQL5InnoDBDialect" />
              <entry key="hibernate.hbm2ddl.auto" value="validate" />
              <entry key="hibernate.format_sql" value="true" />
          </map>
      </property>
  </bean>

Включите bean-компонент для источника данных, где можно указать свойства базы данных MYSQL, такие как url, имя пользователя и пароль. Замените <include connection url> фактическим URL-адресом соединения для подключения к базе данных MYSQL. Аналогичным образом замените <include username> и <include password> действительными значениями имени пользователя и пароля.

1
2
3
4
5
6
<bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
      <property name="driverClassName" value="com.mysql.jdbc.Driver" />
      <property name="url" value="jdbc:mysql//<include connection url>:3306/studentEnrollment?autoReconnect=true&createDatabaseIfNotExist=true&" />
      <property name="username" value="<include username>" />
      <property name="password" value="<include password>" />
</bean>

Включите bean-компонент для менеджера транзакций для определения объема / управления транзакциями.

1
2
3
4
5
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
      <property name="entityManagerFactory" ref="entityManagerFactory" />
</bean>
 
<tx:annotation-driven transaction-manager="transactionManager" />

Таким образом заканчивается длинная конфигурация в jpaContext.xml

7. Создайте файлы JSP для регистрации / входа ученика

Создайте папку с именем «jsp» в WEB-INF (именно здесь будут созданы файлы jsp, как указано в servletConfig.xml для bean-компонента InternalResourceViewResolver).

Создайте файл signup.jsp, чтобы включить форму для получения данных ввода, таких как Имя пользователя, Пароль, Имя, Фамилия, ДатаOfBirth и Адрес электронной почты студента. Снимок страницы регистрации выглядит следующим образом:

Зарегистрироваться

Затем создайте файл login.jsp для включения формы с именами пользователей и паролями. Снимок страницы входа в систему выглядит следующим образом:

авторизоваться

Также создайте success.jsp, чтобы указать успешный вход в систему, и fail.jsp, чтобы указать сбой входа в систему (это просто страницы, используемые для отображения содержимого — логика обработки не используется).

Это приложение использует Twitter начальной загрузки http://getbootstrap.com/ и http://bootswatch.com/united/ в качестве таблиц стилей. Он также использует таблицу стилей DatePicker, чтобы открыть календарь для поля DateOfBirth на странице регистрации ученика ( http://www.eyecon.ro/bootstrap-datepicker/ ).

Ссылочную ссылку на файлы в папке webapp этого приложения можно найти по адресу https://github.com/elizabetht/StudentEnrollmentWithSpring/tree/master/src/main/webapp.

8. Создание пакетов для классов уровня Controller, Model, Repository и Service

Создайте пакеты для классов Spring Controller, Model, Repository и Service в папке src / main / java.

Пример снимка проекта после создания пакета показан ниже:

весна-гибернации-пакет

9. Создайте классы для уровня модели

Создайте класс POJO с именем Student.java внутри пакета com.github.elizabetht.model, чтобы включить детали сущности модели Student во время регистрации. Создайте еще один класс POJO с именем StudentLogin.java внутри того же пакета com.github.elizabetht.model, чтобы включить данные для входа в систему.

Ссылочную ссылку на файлы для классов модели можно найти по адресу https://github.com/elizabetht/StudentEnrollmentWithSpring/tree/master/src/main/java/com/github/elizabetht/model.

10. Создайте класс для уровня репозитория

Создайте интерфейсный класс StudentRepository.java внутри пакета com.github.elizabetht.repository для поддержки операций базы данных уровня репозитория.

Для целей приложения необходимы два метода интерфейса.

  • Чтобы вставить данные регистрации ученика в базу данных
  • Чтобы проверить регистрационные данные студента из базы данных
1
2
3
4
5
6
7
@Repository("studentRepository")
public interface StudentRepository extends JpaRepository<Student, Long> {
 
  @Query("select s from Student s where s.userName = :userName")
  Student findByUserName(@Param("userName") String userName);
 
}

Метод save () поддерживается реализацией Hibernate, поэтому для вставки данных не требуется никаких отдельных операторов SQL.

11. Создайте классы для уровня обслуживания

Создайте интерфейсный класс с именем StudentService.java внутри пакета com.github.elizabetht.service для поддержки операций уровня обслуживания.

1
2
3
4
5
public interface StudentService {
  Student save(Student student);
  boolean findByLogin(String userName, String password);
  boolean findByUserName(String userName);
}

Создайте класс реализации уровня сервиса (действительно POJO) с именем StudentServiceImpl.java внутри пакета com.github.elizabetht.service. Именно в этом заключается логика приложения — либо для сохранения сведений об ученике в базе данных, либо для проверки (уже сохраненных) сведений об ученике из базы данных.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
@Service("studentService")
public class StudentServiceImpl implements StudentService {
 
  @Autowired
  private StudentRepository studentRepository;
 
  @Transactional
  public Student save(Student student) {
      return studentRepository.save(student);
  }
 
  public boolean findByLogin(String userName, String password) { 
      Student stud = studentRepository.findByUserName(userName);
 
      if(stud != null && stud.getPassword().equals(password)) {
          return true;
      }
 
      return false;      
  }
 
  public boolean findByUserName(String userName) {
      Student stud = studentRepository.findByUserName(userName);
 
      if(stud != null) {
          return true;
      }
 
      return false;
  }
 
}

12. Создайте класс для уровня контроллера

Создайте класс POJO уровня контроллера с именем StudentController.java внутри пакета com.github.elizabetht.controller. Именно здесь идет логика маршрутизации приложения — вызывается ли действие регистрации или входа в систему.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
@Controller
@SessionAttributes("student")
public class StudentController {
 
  @Autowired
  private StudentService studentService;
 
  @RequestMapping(value="/signup", method=RequestMethod.GET)
  public String signup(Model model) {
      Student student = new Student();       
      model.addAttribute("student", student);    
      return "signup";
  }
 
  @RequestMapping(value="/signup", method=RequestMethod.POST)
  public String signup(@Valid @ModelAttribute("student") Student student, BindingResult result, Model model) {       
      if(result.hasErrors()) {
          return "signup";
      } else if(studentService.findByUserName(student.getUserName())) {
          model.addAttribute("message", "User Name exists. Try another user name");
          return "signup";
      } else {
          studentService.save(student);
          model.addAttribute("message", "Saved student details");
          return "redirect:login.html";
      }
  }
 
  @RequestMapping(value="/login", method=RequestMethod.GET)
  public String login(Model model) {         
      StudentLogin studentLogin = new StudentLogin();    
      model.addAttribute("studentLogin", studentLogin);
      return "login";
  }
 
  @RequestMapping(value="/login", method=RequestMethod.POST)
  public String login(@Valid @ModelAttribute("studentLogin") StudentLogin studentLogin, BindingResult result) {
      if (result.hasErrors()) {
          return "login";
      } else {
          boolean found = studentService.findByLogin(studentLogin.getUserName(), studentLogin.getPassword());
          if (found) {               
              return "success";
          } else {               
              return "failure";
          }
      }
 
  }
}

13. Создайте файл messages.properties

Как видно выше, аннотация @Valid используется для проверки входных параметров формы, достигающей метода, и результат проверки сохраняется в объекте BindingResult. Для проверки конкретных полей (см. Классы, созданные для уровня модели — https://github.com/elizabetht/StudentEnrollmentWithSpring/tree/master/src/main/java/com/github/elizabetht/model ), используйте аннотации как @NotEmpty, @Size, @Email и @NotNull из различных проверок, доступных в Hibernate Validator.

Пользовательские сообщения, которые должны отображаться при сбое любого из вышеупомянутых валидаторов, указываются в файле messages.properties. Создайте файл с именем messages.properties в папке src / main / resources и включите следующее

1
2
3
4
5
6
7
8
NotEmpty=Field cannot be blank
NotNull=Field cannot be blank
 
Email=Email Address not valid/well-formed
Past=Date of Birth must be in the past
 
Size={0} must be between {2} and {1} characters long
typeMismatch=Invalid format

14. Создайте схему БД в базе данных MYSQL.

Подключитесь к базе данных MySQL, которая будет использоваться для этого приложения, и создайте новую схему базы данных с именем studentEnrollment с помощью MySQL Workbench. Это необходимо, поскольку имя схемы БД studentEnrollment указывается в bean-компоненте dataSource в jpaContext.xml.

После создания схемы DB studentEnrollment создайте таблицу с именем student внутри схемы DB, используя инструкцию CREATE TABLE следующим образом:

01
02
03
04
05
06
07
08
09
10
CREATE TABLE `student` (
  `id` bigint(20) NOT NULL AUTO_INCREMENT,
  `dateOfBirth` datetime NOT NULL,
  `emailAddress` varchar(255) NOT NULL,
  `firstName` varchar(255) NOT NULL,
  `lastName` varchar(255) NOT NULL,
  `password` varchar(8) NOT NULL,
  `userName` varchar(20) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=43 DEFAULT CHARSET=latin1;

15. Развертывание приложения на сервере Tomcat

После выполнения вышеуказанных шагов и успешного создания проекта веб-приложение Java готово к развертыванию на сервере Tomcat 7.

Веб-приложение Java можно развернуть локально, щелкнув правой кнопкой мыши по проекту и выбрав опцию «Запуск от имени -> Запуск на сервере».

То же самое можно развернуть удаленно на любом собственном сервере, который поддерживает Tomcat, скопировав файл WAR (щелкните правой кнопкой мыши по проекту и выберите «Экспортировать как файл WAR») в папку / var / lib / tomcat7 (или соответствующий каталог tomcat) и перезапустите tomcat. сервер.

Это приложение доступно для демонстрации здесь: http://ec2-23-20-137-135.compute-1.amazonaws.com:8080/StudentEnrollmentWithSpring/

16. Клонировать или скачать код

Если вы используете git, клонируйте копию этого проекта здесь: https://github.com/elizabetht/StudentEnrollmentWithSpring.git

Если вы не используете git, загрузите проект в виде файла ZIP или tar.gz здесь: https://github.com/elizabetht/StudentEnrollmentWithSpring/releases/tag/1.6