Neste tutorial vamos criar uma aplicação web simples usando Spring MVC, Hibernate e JSON. Usaremos o Maven para gerenciar dependências e o IntelliJ IDEA para criar, executar e depurar uma aplicação em um servidor Tomcat.

Tenha certeza de que os plugins Spring, Maven e Tomcat estejam habilitados no IntelliJ IDEA Ultimate antes de ir a fundo neste tutorial.

1. Crie um projeto

Abra o 

{span:class=shortcut}Project Wizard{span}
 e selecione 
{span:class=id} Spring MVC {span}
 na seção 
{span:class=id}Spring{span}
. Com o IntelliJ IDEA você pode fazer o deploy de aplicações para o Tomcat, TomEE, Glassfish, JBoss, WebSphere, Jetty, Geronimo, Resin, Cloud Foundry e CloudBees.


Clique em

{span:class=id}Next{span}
e na próxima janela selecione
{span:class=id}Create project from template{span}
e avance.

 
Altere o nome do projeto em 

{span:class=id}Project name{span}
{span:class=id}Project location{span}
 e 
{span:class=id}Base package{span}
 se necessário. Se você já configurou o servidor de aplicação, você pode selecioná-lo no campo 
{span:class=id}Application Server{span}
.

O IDE irá criar um projeto 
{span:class=id}"Helloworld"{span}
 com um Controller simples e uma View.


O novo projeto vem com o arquivo 

{span:class=id}pom.xml{span}
 do Maven. Você pode gerenciar dependências de projeto através deste arquivo ou pelo painel 
{span:class=shortcut}Maven{span}
.

Quando você altera as dependências do Maven, o IntelliJ IDEA aplica as mudanças correspondentes ao projeto automaticamente. Você pode checá-las no diálogo 

{span:class=shortcut}Project Structure → Modules{span}
.

Além das dependências, o IntelliJ IDEA também importa as definições de artefatos do 

{span:class=id}pom.xml{span}
. Você pode verificar as configurações de artefatos no diálogo 
{span:class=shortcut}Project Structure → Artifacts{span}
.

Os artefatos definem a estrutura do que irá no deploy para o servidor de aplicação quando você clicar em 

{span:class=shortcut}Run → Run 'Tomcat 7.0'{span}
.

2. Crie uma configuração de execução

Se você não especificou um 

{span:class=id}Application server{span}
 no 
{span:class=shortcut}Project Wizard{span}
 você pode fazê-lo via 
{span:class=shortcut}Run → Edit Configurations...{span}
.

Não esqueça de especificar os artefatos a enviar no deploy para esta configuração pela aba 

{span:class=shortcut}Deployment{span}
.

Se você configurou pelo menos uma configuração de execução para um servidor de aplicação, o IntelliJ IDEA mostra o painel 

{span:class=shortcut}Application Servers{span}
 para gerenciar o estado da aplicação no servidor. Você pode ver a lista de servidores de aplicação, iniciá-los ou pará-los, ver as aplicações que já sofreram deploy, gerenciar os artefatos a entregar e gerenciar o estado da aplicação.

3. Execute a aplicação

Assim que os artefatos e configurações estiverem definidos, você pode fazer o deploy da aplicação simplesmente executando-a ou pelo atalho no painel 

{span:class=shortcut}Application Servers{span}
.

4. Adicione dependências

Uma vez que vamos criar um banco de dados para nossa aplicação, precisaremos das bibliotecas Spring Data, Hibernate e HSQLDB. Para implementar uma API JSON para nossa aplicação precisaremos da biblioteca JSON. Finalmente, precisaremos da biblioteca JSTL para usar na View da aplicação.

Devemos definir todas essas dependências em nosso arquivo 

{span:class=id}pom.xml{span}
. O IDE irá fazer o download das bibliotecas correspondentes e adicioná-las ao artefato.
Altere a versão de servelt-api para 3.1.0:

<dependency>
    <groupId>javax.servlet</groupId>
    <artifactId>javax.servlet-api</artifactId>
    <version>3.1.0</version>
</dependency>

E acrescente as novas dependências:

<dependency>
   <groupId>jstl</groupId>
   <artifactId>jstl</artifactId>
   <version>1.2</version>
</dependency>

<dependency>
<groupId>org.springframework.data</groupId>
   <artifactId>spring-data-jpa</artifactId>
   <version>1.2.0.RELEASE</version>
</dependency>

<dependency>
   <groupId>org.hibernate.javax.persistence</groupId>
   <artifactId>hibernate-jpa-2.1-api</artifactId>
   <version>1.0.0.Final</version>
</dependency>

<dependency>
   <groupId>org.hibernate</groupId>
   <artifactId>hibernate-entitymanager</artifactId>
   <version>4.3.8.Final</version>
</dependency>

<dependency>
   <groupId>org.hsqldb</groupId>
   <artifactId>hsqldb</artifactId>
   <version>2.3.2</version>
</dependency>

<dependency>
   <groupId>org.json</groupId>
   <artifactId>json</artifactId>
   <version>20141113</version>
</dependency>

Não esqueça de atualizar a tag 

{span:class=id}build{span}
no nó
{span:class=shortcut}plugins\plugin\configuration{span}
o source e o target para a versão do java que estiver utilizando.

<build>
<finalName>user-management</finalName>
<plugins>
    <plugin>
        <artifactId>maven-compiler-plugin</artifactId>
        <configuration>
            <source>1.8</source>
            <target>1.8</target>
        </configuration>
    </plugin>
    <!-- ... -->
</build>

5. Crie o arquivo persistence.xml

Agora vamos definir o arquivo 

{span:class=id}resources/META-INF/persistence.xml{span}
para inicializar o gerenciador de entidades do Hibernate sobre a JPA.

<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.0" xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd">
    <persistence-unit name="defaultPersistenceUnit" transaction-type="RESOURCE_LOCAL">
        <provider>org.hibernate.ejb.HibernatePersistence</provider>
        <properties>
            <property name="hibernate.dialect" value="org.hibernate.dialect.HSQLDialect" />
            <property name="hibernate.connection.url" value="jdbc:hsqldb:mem:spring" />
            <property name="hibernate.connection.driver_class" value="org.hsqldb.jdbcDriver" />
            <property name="hibernate.connection.username" value="sa" />
            <property name="hibernate.connection.password" value="" />
            <property name="hibernate.hbm2ddl.auto" value="create-drop" />
        </properties>
    </persistence-unit>
</persistence>

6. Defina as classes Model

Defina uma classe Model para a entidade user usando annotations JPA.

package com.springapp.mvc;

import javax.persistence.*;

@Entity(name = "account")
public class User {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;

    @Basic
    private String firstName;

    @Basic
    private String lastName;

    @Basic
    private String email;

    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    public String getFirstName() {
        return firstName;
    }

    public void setFirstName(String name) {
        this.firstName = name;
    }

    public String getLastName() {
        return lastName;
    }

    public void setLastName(String lastName) {
        this.lastName = lastName;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }
}

Defina um repositório Spring para a entidade user.

package com.springapp.mvc;

import org.springframework.data.jpa.repository.JpaRepository;

public interface UserRepository extends JpaRepository<User, Long> {
}

7. Registre o repositório, o factory do gerenciador de entidades e o gerenciador de transações

Agora nós devemos registrar o repositório user, uma factory do gerenciador de entidades e um gerenciador de transações no arquivo 

{span:class=id}webapp/WEB-INF/mvc-dispatcher-servlet.xml{span}
.

<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:jpa="http://www.springframework.org/schema/data/jpa"
       xmlns:tx="http://www.springframework.org/schema/tx"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/data/jpa http://www.springframework.org/schema/data/jpa/spring-jpa.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd">
    <context:component-scan base-package="com.springapp.mvc"/>
    <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <property name="prefix" value="/WEB-INF/pages/"/>
        <property name="suffix" value=".jsp"/>
    </bean>
    <jpa:repositories base-package="com.springapp.mvc"/>
    <bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalEntityManagerFactoryBean">
        <property name="persistenceUnitName" value="defaultPersistenceUnit"/>
    </bean>
    <bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
        <property name="entityManagerFactory" ref="entityManagerFactory"/>
    </bean>
    <tx:annotation-driven transaction-manager="transactionManager"/>
</beans>

O Modelo para nossa aplicação está pronto. Agora podemos implementar o Controller.

8. Defina o Controller

Vamos renomear 

{span:class=id}HelloController{span}
para 
{span:class=id}UserController{span}
e adicionar o seguinte código:

package com.springapp.mvc;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

@Controller
public class UserController {
    @Autowired
    private UserRepository userRepository;

    @RequestMapping(value = "/", method = RequestMethod.GET)
    public String listUsers(ModelMap model) {
        model.addAttribute("user", new User());
        model.addAttribute("users", userRepository.findAll());
        return "users";
    }

    @RequestMapping(value = "/add", method = RequestMethod.POST)
    public String addUser(@ModelAttribute("user") User user, BindingResult result) {

        userRepository.save(user);

        return "redirect:/";
    }

    @RequestMapping("/delete/{userId}")
    public String deleteUser(@PathVariable("userId") Long userId) {

        userRepository.delete(userRepository.findOne(userId));

        return "redirect:/";
    }
}

Como você pode ver, definimos três métodos para listar, adicionar e excluir entidades user. Os métodos são mapeados para as URLs correspondentes.

9. Defina a View

Vamos renomear a View 

{span:class=id}hello{span}
 (e o arquivo 
{span:class=id}hello.jsp{span}
correspondente) para 
{span:class=id}users{span}
 (e 
{span:class=id}users.jsp{span}
, respectivamente). Se você renomear o nome da View a partir de seu uso, o IntelliJ IDEA aplicará as mudanças correspondentes para is arquivos JSP automaticamente.

<!doctype html>
<%@taglib uri="http://www.springframework.org/tags" prefix="spring" %>
<%@taglib uri="http://www.springframework.org/tags/form" prefix="form" %>
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<html>
<head>
    <meta charset="utf-8">
    <title>Spring MVC Application</title>
    <meta content="IE=edge,chrome=1" http-equiv="X-UA-Compatible">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.4/css/bootstrap.min.css">
    <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.4/css/bootstrap-theme.min.css">
</head>
<body>
<div class="container">
    <div class="row">
        <div class="span8 offset2">
            <h1>Users</h1>
            <form:form method="post" action="add" commandName="user" class="form-horizontal">
            <div class="control-group">
                <form:label cssClass="control-label" path="firstName">First Name:</form:label>
                <div class="controls">
                    <form:input path="firstName"/>
                </div>
            </div>
            <div class="control-group">
                <form:label cssClass="control-label" path="lastName">Last Name:</form:label>
                <div class="controls">
                    <form:input path="lastName"/>
                </div>
            </div>
            <div class="control-group">
                <form:label cssClass="control-label" path="email">Email:</form:label>
                <div class="controls">
                    <form:input path="email"/>
                </div>
            </div>
            <div class="control-group">
                <div class="controls">
                    <input type="submit" value="Add User" class="btn"/>
                    </form:form>
                </div>
            </div>

            <c:if test="${!empty users}">
                <h3>Users</h3>
                <table class="table table-bordered table-striped">
                    <thead>
                    <tr>
                        <th>Name</th>
                        <th>Email</th>
                        <th>&nbsp;</th>
                    </tr>
                    </thead>
                    <tbody>
                    <c:forEach items="${users}" var="user">
                        <tr>
                            <td>${user.lastName}, ${user.firstName}</td>
                            <td>${user.email}</td>
                            <td>
                                <form action="delete/${user.id}" method="post"><input type="submit"
                                                                                      class="btn btn-danger btn-mini"
                                                                                      value="Delete"/></form>
                            </td>
                        </tr>
                    </c:forEach>
                    </tbody>
                </table>
            </c:if>
        </div>
    </div>
</div>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.4/js/bootstrap.min.js"></script>
</body>
</html>

10. Execute a aplicação

A aplicação deve estar pronta agora.

11. Depure a aplicação

Se você precisar depurar a aplicação, apenas adicione um breakpoint e execute novamente a aplicação em modo de depuração via 

{span:class=shortcut}Run → Debug 'Tomcat 7.0'...{span}
.

12. Adicione API JSON

Finalmente, vamos entregar os usuários criados por JSON implementando este simples método no UserController:

@RequestMapping(value = "/api/users", method = RequestMethod.GET)
public
@ResponseBody
String listUsersJson(ModelMap model) throws JSONException {
    JSONArray userArray = new JSONArray();
    for (User user : userRepository.findAll()) {
        JSONObject userJSON = new JSONObject();
        userJSON.put("id", user.getId());
        userJSON.put("firstName", user.getFirstName());
        userJSON.put("lastName", user.getLastName());
        userJSON.put("email", user.getEmail());
        userArray.put(userJSON);
    }
    return userArray.toString();
}

Execute a aplicação e abra http://localhost:8080/api/users.

Baixe o código final e os arquivos de projeto do IntelliJ IDEA no GitHub.