Neste Tutorial do Spring MVC, aprenderemos como desenvolver uma aplicação web Spring MVC usando o Spring Tool Suite. O framework Spring MVC é amplamente utilizado para aplicações web java.
Spring MVC
Assim como o Framework Struts, o Spring MVC também é baseado nas tecnologias Java EE Servlet e JSP e implementa o padrão de projeto Model–View–Controller.
Tutorial do Spring MVC
Nós já vimos anteriormente como funciona a Injeção de Dependência do Spring e neste tutorial aprenderemos como criar uma aplicação web simples usando o framework Spring MVC. Podemos usar o Eclipse ou IntelliJ IDE para o desenvolvimento de projetos Spring, mas a SpringSource fornece o Spring Tool Suite (STS), que é um IDE baseado no Eclipse e vem com o VMware vFabric tc Server integrado, construído sobre o contêiner Apache Tomcat e otimizado para aplicações baseadas no Spring. Eu usaria o STS para o tutorial do Spring MVC e outros tutoriais futuros, pois facilita a vida do desenvolvedor, fornecendo as seguintes funcionalidades:
- Suporte para criar aplicações Spring esqueleto (MVC, Rest, Batch etc.), bom para começar o projeto do zero. Veremos em breve neste tutorial do Spring MVC como é fácil criar um projeto Spring MVC.
- Fornece recursos úteis, como criar arquivos de configuração Spring, analisar arquivos de configuração e classes para fornecer informações úteis sobre eles.
- Validação automática de aplicações Spring
- Suporte a refatoração para fazer alterações no projeto facilmente, as alterações são refletidas nos arquivos de configuração também.
- Assistência de código não apenas para classes, mas também para arquivos de configuração. Gosto muito desse recurso, pois na maioria das vezes precisamos saber o que podemos usar e seus detalhes.
- Melhor suporte para Programação Orientada a Aspectos (AOP) por meio da integração do AspectJ.
Dando uma olhada em todos os recursos que o STS oferece, fiquei convencido com isso e decidi usá-lo para aplicativos Spring e até agora estou muito feliz com isso. Basta baixar o STS na Página Oficial de Download do STS e instalá-lo. Estou usando o STS 3.4.0.RELEASE, que é baseado no lançamento do Eclipse 4.3.1. Se você não quiser usar o STS e quiser obter suas funcionalidades no Eclipse existente, então você precisa instalar seu plugin na Eclipse Marketplace. Use a imagem abaixo como referência e certifique-se de escolher a versão correta do STS para instalação. O plugin abaixo é bom para o Eclipse Kepler.
Se você não quiser usar o servidor SpringSource, pode implantar o aplicativo em qualquer outro contêiner Java EE, como Tomcat, JBoss, etc. Para este tutorial, usarei o servidor que vem com o STS, mas testei o aplicativo exportando-o como arquivo WAR para um servidor Tomcat separado e está funcionando bem. Agora que nosso ambiente de servidor e IDE está pronto, vamos prosseguir para criar nosso primeiro projeto Spring MVC. Os passos abaixo são válidos tanto para o STS quanto para o Eclipse com plugins do STS.
Criando uma Aplicação Spring MVC no STS ou Eclipse
Passo 1: Crie um Novo Projeto Spring no menu. Passo 2: Na nova janela do projeto, dê o nome como “SpringMVCExample” e escolha o modelo como “Projeto Spring MVC”. Se estiver usando este modelo pela primeira vez, o STS o baixará do site da SpringSource. Se desejar, você pode adicionar o projeto a qualquer conjunto de trabalho.
Passo 3: Quando o modelo for baixado, na próxima tela, você precisará fornecer o nome do pacote de nível superior. Este pacote será usado como pacote base para os componentes do Spring.
Passo 4: Depois que o projeto for criado pelo modelo Spring MVC, ele terá a aparência da imagem abaixo.
Não se preocupe se não ver a classe User.java, os arquivos login.jsp e user.jsp, eles foram adicionados por mim posteriormente. Se o projeto não estiver compilado e você vir alguns erros, execute o Maven/Atualizar Projeto. Certifique-se de marcar as opções “Forçar atualização de Snapshots/Releases”, consulte a imagem abaixo.
No geral, o projeto se parece com qualquer outra aplicação web baseada no Maven com alguns arquivos de configuração do Spring. Agora é hora de analisar as diferentes partes do projeto e expandi-lo um pouco.
Dependências do Spring MVC
O nosso arquivo pom.xml gerado parece com o seguinte.
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="https://maven.apache.org/POM/4.0.0" xmlns:xsi="https://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="https://maven.apache.org/POM/4.0.0 https://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.journaldev</groupId>
<artifactId>SpringMVCExample</artifactId>
<name>SpringMVCExample</name>
<packaging>war</packaging>
<version>1.0.0-BUILD-SNAPSHOT</version>
<properties>
<java-version>1.6</java-version>
<org.springframework-version>4.0.0.RELEASE</org.springframework-version>
<org.aspectj-version>1.7.4</org.aspectj-version>
<org.slf4j-version>1.7.5</org.slf4j-version>
</properties>
<dependencies>
<!-- Spring -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>${org.springframework-version}</version>
<exclusions>
<!-- Exclude Commons Logging in favor of SLF4j -->
<exclusion>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>${org.springframework-version}</version>
</dependency>
<!-- AspectJ -->
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjrt</artifactId>
<version>${org.aspectj-version}</version>
</dependency>
<!-- Logging -->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>${org.slf4j-version}</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>jcl-over-slf4j</artifactId>
<version>${org.slf4j-version}</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
<version>${org.slf4j-version}</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>1.2.15</version>
<exclusions>
<exclusion>
<groupId>javax.mail</groupId>
<artifactId>mail</artifactId>
</exclusion>
<exclusion>
<groupId>javax.jms</groupId>
<artifactId>jms</artifactId>
</exclusion>
<exclusion>
<groupId>com.sun.jdmk</groupId>
<artifactId>jmxtools</artifactId>
</exclusion>
<exclusion>
<groupId>com.sun.jmx</groupId>
<artifactId>jmxri</artifactId>
</exclusion>
</exclusions>
<scope>runtime</scope>
</dependency>
<!-- @Inject -->
<dependency>
<groupId>javax.inject</groupId>
<artifactId>javax.inject</artifactId>
<version>1</version>
</dependency>
<!-- Servlet -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
<version>2.5</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>jsp-api</artifactId>
<version>2.1</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>
<!-- Test -->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.7</version>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<artifactId>maven-eclipse-plugin</artifactId>
<version>2.9</version>
<configuration>
<additionalProjectnatures>
<projectnature>org.springframework.ide.eclipse.core.springnature</projectnature>
</additionalProjectnatures>
<additionalBuildcommands>
<buildcommand>org.springframework.ide.eclipse.core.springbuilder</buildcommand>
</additionalBuildcommands>
<downloadSources>true</downloadSources>
<downloadJavadocs>true</downloadJavadocs>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>2.5.1</version>
<configuration>
<source>1.6</source>
<target>1.6</target>
<compilerArgument>-Xlint:all</compilerArgument>
<showWarnings>true</showWarnings>
<showDeprecation>true</showDeprecation>
</configuration>
</plugin>
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>exec-maven-plugin</artifactId>
<version>1.2.1</version>
<configuration>
<mainClass>org.test.int1.Main</mainClass>
</configuration>
</plugin>
</plugins>
</build>
</project>
O artifactId será o servlet-context para a aplicação web, então você pode alterá-lo se desejar algo diferente. Existem algumas propriedades definidas para as versões do Spring Framework, AspectJ e SLF4j, eu descobri que elas não estavam refletindo as últimas versões, então eu as alterei para a versão estável mais recente até hoje. As dependências do projeto que me interessam são;
- spring-context: Dependência principal do Spring Core. Observe a exclusão do commons logging em favor do SLF4J.
- spring-webmvc: Artefato do Spring para suporte a MVC
- aspectjrt: Referência à API do AspectJ
- SLF4J e Log4j: Para fins de registro, o Spring é muito fácil de configurar para log4j ou API de Logging Java por causa da integração com SLF4J.
- javax.inject – API JSR330 para injeção de dependência
Há outras dependências adicionadas, como Servlet, JSP, JSTL e API JUnit, mas para uma aplicação inicial, podemos ignorá-las.
Tutorial do Spring MVC – Configuração do Log4j
O arquivo log4j.xml gerado parece o seguinte.
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE log4j:configuration PUBLIC "-//APACHE//DTD LOG4J 1.2//EN" "log4j.dtd">
<log4j:configuration xmlns:log4j="https://jakarta.apache.org/log4j/">
<!-- Appenders -->
<appender name="console" class="org.apache.log4j.ConsoleAppender">
<param name="Target" value="System.out" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="%-5p: %c - %m%n" />
</layout>
</appender>
<!-- Application Loggers -->
<logger name="com.journaldev.spring">
<level value="info" />
</logger>
<!-- 3rdparty Loggers -->
<logger name="org.springframework.core">
<level value="info" />
</logger>
<logger name="org.springframework.beans">
<level value="info" />
</logger>
<logger name="org.springframework.context">
<level value="info" />
</logger>
<logger name="org.springframework.web">
<level value="info" />
</logger>
<!-- Root Logger -->
<root>
<priority value="warn" />
<appender-ref ref="console" />
</root>
</log4j:configuration>
Observe que está imprimindo tudo no console, podemos facilmente adicionar apêndices para redirecionar o registro para arquivos.
Tutorial do Spring MVC – Configuração do Descritor de Implantação
Vamos ver nosso web.xml e analisá-lo.
<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="https://java.sun.com/xml/ns/javaee"
xmlns:xsi="https://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="https://java.sun.com/xml/ns/javaee https://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
<!-- The definition of the Root Spring Container shared by all Servlets and Filters -->
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/root-context.xml</param-value>
</context-param>
<!-- Creates the Spring Container shared by all Servlets and Filters -->
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<!-- Processes application requests -->
<servlet>
<servlet-name>appServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/appServlet/servlet-context.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>appServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
</web-app>
ContextLoaderListener
liga o ciclo de vida do ApplicationContext
ao ciclo de vida do ServletContext
e automatiza a criação do ApplicationContext
. ApplicationContext
é o lugar para os beans do Spring e podemos fornecer sua configuração através do parâmetro de contexto contextConfigLocation. O arquivo root-context.xml fornece os detalhes de configuração para WebApplicationContext. DispatcherServlet
é a classe controladora para a aplicação Spring MVC e todas as solicitações do cliente são tratadas por este servlet. A configuração está sendo carregada do arquivo servlet-context.xml.
Tutorial Spring MVC – Arquivos de Configuração
Arquivo root-context.xml:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="https://www.springframework.org/schema/beans"
xmlns:xsi="https://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="https://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd">
<!-- Root Context: defines shared resources visible to all other web components -->
</beans>
Aqui podemos definir beans compartilhados, mas por enquanto não há nada nele. Código do arquivo servlet-context.xml:
<?xml version="1.0" encoding="UTF-8"?>
<beans:beans xmlns="https://www.springframework.org/schema/mvc"
xmlns:xsi="https://www.w3.org/2001/XMLSchema-instance"
xmlns:beans="https://www.springframework.org/schema/beans"
xmlns:context="https://www.springframework.org/schema/context"
xsi:schemaLocation="https://www.springframework.org/schema/mvc https://www.springframework.org/schema/mvc/spring-mvc.xsd
https://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd
https://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">
<!-- DispatcherServlet Context: defines this servlet's request-processing infrastructure -->
<!-- Enables the Spring MVC @Controller programming model -->
<annotation-driven />
<!-- Handles HTTP GET requests for /resources/** by efficiently serving up static resources in the ${webappRoot}/resources directory -->
<resources mapping="/resources/**" location="/resources/" />
<!-- Resolves views selected for rendering by @Controllers to .jsp resources in the /WEB-INF/views directory -->
<beans:bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<beans:property name="prefix" value="/WEB-INF/views/" />
<beans:property name="suffix" value=".jsp" />
</beans:bean>
<context:component-scan base-package="com.journaldev.spring" />
</beans:beans>
Assim é como o arquivo de configuração padrão do Spring se parece, apenas imagine escrever tudo isso por conta própria e você começará a gostar da ferramenta STS. O elemento annotation-driven é usado para informar ao servlet do Controlador que serão usadas anotações para configurações de beans. O elemento resources define a localização onde podemos colocar arquivos estáticos, como imagens, páginas HTML etc., que não queremos que passem pelo framework Spring. InternalResourceViewResolver
é o resolvedor de visualizações, podemos fornecer a localização das páginas de visualização por meio das propriedades de prefixo e sufixo. Portanto, todas as nossas páginas JSP devem estar no diretório /WEB-INF/views/. O elemento context:component-scan é usado para fornecer a localização do pacote base para a varredura das classes do Controlador. Lembre-se do valor do pacote de nível superior fornecido na criação do projeto, é o mesmo valor usado aqui.
Classe do Controlador Spring MVC
O HomeController é criado automaticamente com o método home(), embora eu o tenha estendido um pouco adicionando os métodos loginPage() e login().
package com.journaldev.spring;
import java.text.DateFormat;
import java.util.Date;
import java.util.Locale;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
/**
* Handles requests for the application home page.
*/
@Controller
public class HomeController {
private static final Logger logger = LoggerFactory.getLogger(HomeController.class);
/**
* Simply selects the home view to render by returning its name.
*/
@RequestMapping(value = "/", method = RequestMethod.GET)
public String home(Locale locale, Model model) {
logger.info("Welcome home! The client locale is {}.", locale);
Date date = new Date();
DateFormat dateFormat = DateFormat.getDateTimeInstance(DateFormat.LONG, DateFormat.LONG, locale);
String formattedDate = dateFormat.format(date);
model.addAttribute("serverTime", formattedDate );
return "home";
}
@RequestMapping(value = "/login", method = RequestMethod.GET)
public String loginPage(Locale locale, Model model) {
return "login";
}
@RequestMapping(value = "/home", method = RequestMethod.POST)
public String login(@Validated User user, Model model) {
model.addAttribute("userName", user.getUserName());
return "user";
}
}
@Controller é uma anotação usada para indicar que é uma classe de controlador web. @RequestMapping é usado com classes e métodos para redirecionar a solicitação do cliente para um método específico. Observe que os métodos do manipulador estão retornando String, que deve ser o nome da página de visualização a ser usada como resposta. Como você pode ver, temos três métodos que retornam strings diferentes, então precisamos criar páginas JSP com o mesmo nome. Observe que o método login() será chamado com o método HTTP como POST, portanto, esperamos alguns dados do formulário aqui. Para isso, temos a classe de modelo User marcada para validação usando @Validated annotation. Cada método contém Model como argumento e podemos definir atributos para serem usados posteriormente nas páginas de resposta JSP.
Classes de Modelo Spring MVC
As classes de modelo são usadas para armazenar variáveis de formulário, nosso modelo User parece assim.
package com.journaldev.spring;
public class User {
private String userName;
public String getUserName() {
return userName;
}
public void setUserName(String userName) {
this.userName = userName;
}
}
A simple java bean with the variable name and its getter and setter methods.
Tutorial Spring MVC – Páginas de Visualização
Nós temos três páginas JSP como abaixo. Código home.jsp:
<%@ taglib uri="https://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ page session="false" %>
<html>
<head>
<title>Home</title>
</head>
<body>
<h1>
Hello world!
</h1>
<P> The time on the server is ${serverTime}. </P>
</body>
</html>
Observe o uso de Expressão de Linguagem JSP para obter os valores do atributo. Código login.jsp:
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "https://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Login Page</title>
</head>
<body>
<form action="home" method="post">
<input type="text" name="userName"><br>
<input type="submit" value="Login">
</form>
</body>
</html>
A simple JSP page for the user to provide the userName as input. Notice that form variable name is same as User class variable name. Also, form action is “home” and method is “post”. It’s clear that HomeController login() method will handle this request. user.jsp code:
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "https://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>User Home Page</title>
</head>
<body>
<h3>Hi ${userName}</h3>
</body>
</html>
Página inicial simples para o usuário onde o nome de usuário é exibido, observe que estamos configurando este atributo no método de login.
Teste de Aplicativo de Exemplo Spring MVC
Nossa aplicação está pronta para execução, basta executá-la no servidor VMware tc Server ou em sua escolha de qualquer outro contêiner de servlet, você obterá as seguintes páginas como resposta.
É isso para o Tutorial Spring MVC, você pode ver como é fácil criar uma aplicação Spring MVC usando os plugins do STS. O tamanho do código é muito pequeno e a maior parte da configuração é manipulada pelo Spring MVC para que possamos nos concentrar na lógica de negócios. Baixe o exemplo de projeto Spring MVC pelo link abaixo e brinque com ele.
Source:
https://www.digitalocean.com/community/tutorials/spring-mvc-tutorial