Você quer aprender como criar Web Services RESTful de forma simples e rápida?
No post 4 Conceitos sobre REST que Qualquer Desenvolvedor Precisa Conhecer, nós discutimos uma série de características que um sistema REST deve possuir, mas não demos um foco em web services, e nem mesmo demonstramos algum tipo de implementação.
Neste post, você vai aprender como dar os primeiros passos para criar APIs RESTful com o Spring Boot.
O que é Spring Boot?
O Spring Boot é um framework que tem como base o core de funcionalidades que já estamos familiarizados a utilizar com outros frameworks da família Spring, como injeção de dependências, gerenciamento de dados com JPA, segurança, dentre outros.
Uma das principais características desse framework é fornecer um nível maior de produtividade para desenvolvedores.
Por possuir características de modularidade, aplicações desenvolvidas com o Spring Boot podem fazer uso apenas das funcionalidades necessárias, o que diminui a complexidade de desenvolvimento e operação do sistema.
Com o Spring Boot, você pode gerar um único pacote JAR que contenha tudo o que você precisa, como por exemplo um servidor Web, gerenciador de dados, segurança e etc. Dessa maneira, o seu deploy fica muito mais simplificado.
Além disso, muitas configurações que antes precisavam ser feitas com extensos arquivos XML, agora são feitas de forma programática, e muitas vezes já veem disponibilizadas prontas pra uso.
A seguir nós vamos detalhar o desenvolvimento de um Web Service utilizando o Spring Boot como base, e você vai perceber o quão simples pode ser o desenvolvimento de uma aplicação que faz uso desse framework.
Criando um Web Service RESTful
O primeiro passo para a criação de nosso web service, é a criação de um projeto Maven. Caso você prefira, é possível também a utilização do Gradle, no site de referência do Spring Boot você consegue mais detalhes sobre a criação nesse formato.
Criando o seu projeto Maven a partir do Eclipse ou alguma outra IDE de sua preferência, você deve configurar o seu POM conforme o código abaixo.
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.algaworks</groupId> <artifactId>postrest</artifactId> <version>1.0.0-SNAPSHOT</version> <packaging>jar</packaging> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>1.3.2.RELEASE</version> </parent> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> </dependencies> </project>
Nesse POM, indicamos que desejamos utilizar como referência o projeto do Spring Boot e também declaramos que vamos utilizar recursos para o desenvolvimento de uma aplicação Web.
A dependência spring-boot-starter-web já possui todos os requisitos necessários que nós vamos precisar. Além de possuir um servidor Web embutido (Tomcat), ela possui as dependências que nos permite a criação do nosso web service.
Após a configuração do POM, você deve criar uma classe semelhante ao código mostrado abaixo. Essa classe é responsável pela execução da nossa aplicação.
package com.algaworks; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.EnableAutoConfiguration; import org.springframework.boot.autoconfigure.SpringBootApplication; @SpringBootApplication public class Main { public static void main(String[] args) throws Exception { SpringApplication.run(Main.class, args); } }
Caso o Spring Boot ainda não seja muito familiar e você esteja acostumado a empacotar aplicações Web em formatos WAR, você certamente deve estar se perguntando qual o motivo para criarmos esse método main
, não é mesmo?
Lembra que eu falei que as dependências necessárias são embutidas dentro da própria aplicação? Dessa forma, o método main
é o gatilho que será responsável por iniciar a nossa aplicação.
Não sei se você percebeu quando escrevemos o arquivo pom.xml, mas o formato gerado pela compilação do Maven é um JAR, dessa maneira, o main
será o método a ser invocado na execução do nosso JAR.
Feito essa configuração e codificação inicial, o seu projeto já está pronto para evoluir. Caso queira testar e verificar se tudo está funcionando, você pode executar o método main
, e irá perceber que o Spring Boot inicializará a aplicação pra você.
Como ainda não criamos nada que possa ser de fato acessado, não temos muitas coisas ainda a testar. E para dar continuidade, vamos prosseguir com a criação do nosso Web Service.
A ideia é criamos um Web Service que nos permita a busca e remoção de um recurso (caso o conceito “recurso” esteja um pouco vago, recomendo você ler o meu outro post que detalha este conceito), que eu denominei “Curso”.
A primeira coisa a ser feita, é a criação da classe Curso. Essa classe possui os atributos que vamos utilizar para representar o nosso conceito.
É uma classe simples, basicamente um POJO, mas que nos ajuda a compreender de forma simples como representar um recurso.
package com.algaworks.model; public class Curso { private Integer id; private String nome; private String duracao; public Curso(Integer id, String nome, String duracao) { this.id = id; this.nome = nome; this.duracao = duracao; } // getters e setters omitidos }
Após a criação da representação do nosso recurso Curso, já estamos prontos para criar a classe que será de fato o nosso recurso.
Perceba que a classe Curso que criamos é apenas uma representação, ou seja, são os dados que queremos retornar ao cliente.
O recurso de fato é criado a partir da criação de um controlador, que é responsável por receber e tratar as requisições vindas dos nossos clientes.
package com.algaworks.resource; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import org.springframework.http.HttpStatus; import org.springframework.http.ResponseEntity; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; import org.springframework.web.bind.annotation.RestController; import com.algaworks.model.Curso; @RestController public class CursoResource { private Map<Integer, Curso> cursos; public CursoResource() { cursos = new HashMap<Integer, Curso>(); Curso c1 = new Curso(1, "Workshop Rest", "24hs"); Curso c2 = new Curso(2, "Workshop Spring MVC", "24hs"); Curso c3 = new Curso(3, "Desenvolvimento Web com JSF 2", "60hs"); cursos.put(1, c1); cursos.put(2, c2); cursos.put(3, c3); } @RequestMapping(value = "/cursos", method = RequestMethod.GET) public ResponseEntity<List<Curso>> listar() { return new ResponseEntity<List<Curso>>(new ArrayList<Curso>(cursos.values()), HttpStatus.OK); } }
A anotação @RestController
nos permite criar um controlador com características REST e que possa manipular as requisições vindas dos nossos clientes. Se você já está habituado a utilizar o Spring MVC, essa anotação é muito semelhante a @Controller.
Para simplificar o nosso exemplo, os dados que manipulamos foram colocados em um HashMap que foi inicializado no próprio construtor da classe CursoResource
.
Outra coisa importante para discutirmos é o método listar
. Perceba que o mesmo possui uma anotação @RequestMapping. Essa anotação é a responsável por fazer o mapeamento de nossa URI.
Nessa anotação, estamos determinando que a URI /cursos, a partir do método GET, poderá listar todos os cursos presentes no nosso HashMap.
Além disso, perceba que na linha onde fazemos o retorno dos nossos dados, foi adicionado um HttpStatus.OK. Essa opção indica que o Spring, ao montar nossa resposta, deve enviar um “200 OK” para o nosso cliente.
Ao acessar http://localhost:8080/cursos, você receberá uma resposta conforme a listagem abaixo:
[ { "id": 1, "nome": "Workshop Rest", "duracao": "24hs" }, { "id": 2, "nome": "Workshop Spring MVC", "duracao": "24hs" }, { "id": 3, "nome": "Desenvolvimento Web com JSF 2", "duracao": "60hs" } ]
Outro recurso interessante que o Spring nos provê é o mapeamento de uma parte da URI como fonte de entrada para o nosso método. A implementação abaixo busca um curso a partir de um identificador.
@RequestMapping(value = "/cursos/{id}", method = RequestMethod.GET) public ResponseEntity<Curso> buscar(@PathVariable("id") Integer id) { Curso curso = cursos.get(id); if (curso == null) { return new ResponseEntity<>(HttpStatus.NOT_FOUND); } return new ResponseEntity<Curso>(curso, HttpStatus.OK); }
Perceba que mapeamos a nossa URI com o valor /cursos/{id} e que no parâmetro do nosso método buscar
adicionamos uma anotação @PathVariable
. Essa anotação nos permite fazer o bind do valor fornecido na URI com o parâmetro do nosso método.
É importante notarmos também o tratamento de cursos não encontrados. Perceba que se o ID do curso fornecido na URL não for encontrado no nosso HashMap, uma resposta NOT_FOUND é retornada. Ou seja, o usuário irá receber uma resposta HTTP 404.
Essa tratativa é importante e faz com que o nosso Web Service siga os padrões propostos pelo protocolo HTTP.
Até aqui, nossos métodos sempre trataram requisições GET. Caso seja necessário a tratativa de outras funcionalidades, vamos precisar indicar ao Spring que nosso método aceita outra opção que não seja o GET.
Podemos ver um exemplo com o método DELETE. Esse código nos apresenta um exemplo no qual podemos remover um determinado recurso.
@RequestMapping(value = "/cursos/{id}", method = RequestMethod.DELETE) public ResponseEntity<?> deletar(@PathVariable("id") int id) { Curso curso = cursos.remove(id); if (curso == null) { return new ResponseEntity<>(HttpStatus.NOT_FOUND); } return new ResponseEntity<>(HttpStatus.NO_CONTENT); }
Perceba que fizemos a tratativa caso o recurso não seja encontrado da mesma forma que fizemos na implementação da busca. Além disso, veja que ao invés do código “200 OK”, estamos retornando um “NO_CONTENT”.
Essa é a resposta normalmente utilizada quando executamos a remoção de um recurso. Esse código irá retornar uma resposta “204 NO CONTENT” para o cliente do nosso Web Service.
(Nota: Quer entrar um pouco mais a fundo nos conceitos de WebServices REST com Java? Baixe nosso livreto gratuito!)
Conclusão
Neste post, discutimos sobre algumas características do framework Spring Boot e como ele pode nos ajudar na criação de um Web Service RESTful.
Criamos um serviço bem simples, mas que nos ajuda a compreender de forma rápida como podemos criar Web Services.
Em artigos futuros, vamos continuar discutindo sobre a criação de Web Services RESTful e entender algumas outras funcionalidades que podemos adicionar para criarmos aplicações cada vez melhores.
Deixe seu comentário aí abaixo dizendo o que achou desse artigo e também com sugestões. ;)
Obrigado e até a próxima!
Olá,
o que você achou deste conteúdo? Conte nos comentários.