Pesquisar este blog

terça-feira, 28 de outubro de 2014

Acessando Webservices com PlayFramework Java com Lambda

O PlayFramework possui uma biblioteca de ajuda para acessar os webservices que torna muito simples a utilização destes serviços. Neste post será mostrado como fazer uma chamada a um webservice JSON de exemplo da internet.

Modificando o build

Esta biblioteca de webservice do play é uma biblioteca a parte e você deverá adicioná-la como dependência do seu projeto. Para aqueles que usam o sbt para administrar o build basta adicionar esta dependencia ao seu projeto:
javaWs
Com isso você terá acesso as classes que fazem requisições a webservices.
O código necessário para se fazer uma chamada a um Webservice é bem simples com o play, veja abaixo:
import play.libs.ws.WSResponse;
import play.libs.ws.WSRequestHolder;
import play.mvc.Controller;
import play.mvc.Result;
import static play.libs.F.Promise;
import play.libs.ws.WS;

public class ClienteController extends Controller {
    public static Promise<Result> getClientes(){
        WSRequestHolder holder = WS.url("http://api.geonames.org/citiesJSON");
        holder.setQueryParameter("north","-50");
        holder.setQueryParameter("south","10");
        holder.setQueryParameter("east","-20");
        holder.setQueryParameter("west","55");
        holder.setQueryParameter("lang","pt");
        holder.setQueryParameter("username","demo");
        Promise<WSResponse> promise = holder.get();
        return promise.map(f -> ok(f.asJson()));
    }
}
É sempre bom lembrar que os imports são muito importantes, vamos começar explicando eles:

 import play.libs.ws.WS;
Será utilizado para realizar as requisições http, uma simples chamada WS.url("string_da_url").get irá executar uma chamada HTTP GET no endereço passado para o método url.
O resultado do método GET é uma promessa de resultado, Promise<Result>, o que é um código assincrono que será executado em background.
Ao realizar uma chamada ao método getClientes a máquina virtual java não ficará esperando a resposta da chamada ao webservice para retornar uma resposta ao cliente. Esta execução será feita em background e assim que a chamada ao método HTTP GET retornar uma resposta, o método map será executado.
Repare que o método map, transforma o WSResponse, em uma resposta Result, com o status http 200 (ok), convertendo em json o resultado, através do método asJson.
Aqui não tratamos erros ocorridos nesta chamada ao webservice.
Todo o conteúdo de classes deste post está localizado neste repositorio

segunda-feira, 27 de outubro de 2014

Webservices RESTful com Java no PlayFramework

Webservices RESTful no PlayFramework

O PlayFramework é um framework MVC e para construir webservices nele, primeiro devemos configurar as rotas. As rotas do play são definidas em um arquivo chamado routes, que fica armazenado em um diretório chamado resources. Neste arquivo são definidos os métodos HTTP, o caminho do método chamado e para quais métodos dos controllers serão direcionados estas chamadas. Abaixo é mostrado um exemplo de métodos REST de chamadas a entidade usuário:
GET         /usuario       controllers.UsuarioController.list()
POST       /usuario       controllers.UsuarioController.create()
GET         /usuario/:id  controllers.UsuarioController.get(id:Long)
PUT         /usuario/:id  controllers.UsuarioController.update(id:Long)
DELETE /usuario/:id   controllers.UsuarioController.delete(id:Long)
A definição deste arquivo é bem fácil de ser compreendida. Primeiro definimos os métodos HTTP:
  • GET
  • POST
  • PUT
  • DELETE
Na segunda parte do arquivo, é definido o caminho do método.
  • /usuario
é acessado ao digitarmos o caminho do servidor, a porta e o caminho do método:
http://localhost:9000/usuario
A terceira parte do arquivo routes, define qual mécontrollers.UsuarioController.list() todo do controller será chamado por aquele caminho http. Nesta definição deve-se utilizar o caminho completo da classe, incluindo o pacote e o nome da classe.
  • controllers.UsuarioController.get()
Com isso definimos que o método get da classe controllers.UsuarioController será chamado, quando houver uma chamada GET no caminho /usuario.

Quando o caminho do método contiver algum parâmetro, basta nomear o parâmetro usando o :, que no exemplo acima é o id do usuário. Uma chamada
http://localhost:9000/usuario/123
Irá realizar uma chamada ao método get, convertendo 123 em Long e 123 será usado como argumento do método get.

Definição do controller

A definição do controller é bem simples, só existem duas regras básicas. Primeiro a classe deverá extender a classe abstrata play.mvc.Controller, e todos os seus métodos expostos a chamadas HTTP, deverão retornar um resultado play.mvc.Result. Que nada mais é, que um mapeamento aos status http, por exemplo o ok é um mapeamento ao status HTTP 200 OK.
Abaixo segue um exemplo:
import play.libs.Json;
import play.mvc.Controller;
import play.mvc.Result;

public class UsuarioController extends Controller {   
    public static Result list()
    {
        return ok(Json.toJson(new java.util.ArrayList<Usuario>()));
    }
No exemplo, tem-se a implementação do método list. Repare que no retorno dele, usa-se o método ok, que mapeia o status HTTP 200 para a resposta. E este método irá receber o conteúdo do retorno do método, que neste caso é uma lista de Usuario.
Aqui também é utilizado o objeto Json para converter a lista de usuários em uma string Json.

Definição de métodos com objetos no body

Qualquer método definido no controller pode conter objetos no body, abaixo segue o exemplo do método save, que é um post com um usuário em Json no body:
 public static Result create()
    {
        Usuario newUsuario = Json.fromJson(request().body().asJson(), Usuario.class);
        Usuario inserted = save(newUsuario);
        return created(Json.toJson(inserted));
    }
request().body() retorna o conteúdo do body da chamada, asJson() converte este resultado em json. O método fromJson converte o json no objeto usuário.
Com isso pega-se o resultado json do body da chamada, transforma-o em um objeto json, e converte este json em uma instância do objeto usuário.

Testando:

Os testes do método GET podem ser executados direto no navegador, para isto basta digitar o entereço de execução da sua instância e pronto, por exemplo:
localhost:9000/usuario
Irá executar o método GET do usuário e retornar uma lista de todos os usuários inseridos na sua instância.
Já para testar os outros métodos, devermos ou instalar uma ferramenta de teste de REST, como o SOAPUI ou mesmo instalar uma extensão de REST ao seu navegador, como a RestLet Client.
Para executarmos uma chamada com POST devemos utilizar um json, como o mostrado abaixo:
{ "id": 4, "nome": "DirceuProf", "endereco":{"id": 1, "rua": "Marques de São Vicente", "numero": "3001", "cidade": "Sao Paulo", "estado": "Sao Paulo","cep":"05003000"} }
Lembrando que nos testes você pode, e deve,  alterar os dados que serão inseridos.
Todo o conteúdo de classes deste post está localizado neste repositorio, e apresentação

segunda-feira, 20 de outubro de 2014

Implementando um WebService REST com o PlayFramework no Java

REST/RESTful (representaçao do estado de transferência) é o nome dado a definição das regras, este termo surgiu no ano de 2000 na dissertação de Roy Fielding. Esta é uma decisão arquitetural, é uma abstração da arquitetura da WWW. Um cliente de um serviço REST é bem desacoplado, pois o REST possui regras bem flexíveis.
A definiçao REST é independente de protocolo, ele não está acoplado ao HTTP.
Para construir um aplicativo cliente de uma implementação REST as únicas informações necessárias são: o ponto de entrada e o tipo de arquivos que ele irá utilizar para trocar informações.
REST não é apenas um mapa CRUD dos métodos HTTP, apesar de muitos aplicativos fazerem este tipo de mapeamento.
GET é o método HTTP utilizado para requerer algum tipo de informação do servidor
PUT é um método HTTP que deve ser utilizado para alterar os dados, somente quando todas as informações que estiverem sendo enviadas foram alteradas, ou seja, ele é um update completo dos dados e não um update parcial (de apenas um campo).
POST, por definição é uilizado para fazer tudo o que os outros métodos http não podem fazer, com isso pode-se usá-lo para inserir informações (criar) e para alterar informações, desde que de maneira parcial.

Estilo arquitetural do REST

O estilo arquitetural do REST podem ser aplicadas aos webservices, o que os caracterizarão como webservices RESTful quando eles aplicarem as regras descritas abaixo:
As propriedades do REST devem ser aplicadas aos componentes, conectores e aos elementos de dados.

Client Server

Uma interface uniforme separa os clientes dos servidores, o que caracteriza uma separação de responsabilidades. Os clientes REST não podem ficar responsáveis pelo armazenamento de dados, o que deverá ficar restrito aos servidores, o que aumenta a portabilidade do código do cliente. Os servidores não devem se preocupar com o estado do usuário nem com a interface do cliente, com isso eles ficam mais simples e escaláveis.

Stateless

A comunicação entre o cliente e o servidor acontece sem nenhuma informação de contexto do cliente/usuário ser registrada nos servidores entre as requisições. Cada requisição do cliente deverá conter todas as informações necessárias para ela ser completada. O estado da sessão é mantido no cliente, porém é importante notar que o estado da sessão poderá ser transferido entre os servidores afim de manter o estado de persistência por um período temporal e controlar a autenticação.

Cache

Assim como na internet, os clientes podem cachear as respostas, porém as respostas possuem a capacidade de se definirem como cacheáveis ou não. Um cacheamento bem administrado pode evitar muitas chamadas aos servidores, o que contribui para o aumento da performance e escalabilidade daquele serviço.

Sistema em Camadas

Um cliente nunca deve saber se ele está conectado diretamente ao servidor final, ou se existe algum processo no meio do caminho. Servidores intermediários podem realizar um trabalho de balanceamento de carga ou proverem caches distribuídos, além de também forçar políticas de segurança.

Interfaces uniformes

A uniformização das interfaces é um dos pontos mais importantes do design de Serviços REST. Elas servem para simplificar e desacoplar a arquitetura, o que possibilita a evolução independente de cada parte do sistema. Existem quatro regras da uniformização das interfaces:

Identificação dos recursos

Recursos individuais deverão ser identificados nas requisições, por exemplo utilizando URIs em um serviço REST baseado na web. Estes recursos devem ser conceitualmente separados das respresentações que serão retornadas aos clientes, por exemplo um servidor pode enviar dados em formatos JSON, XML ou HTML, mas nenhum deles deverá ter a mesma representação que elas possuem no armazenamento daquele servidor. Os dados devem possuir estruturas diferentes no banco de dados e nos serviços.

Manipulação dos recursos através destas representações

Quando um cliente possuir uma instância de um recurso, incluindo metadados, ele deve possuir as informações necessárias para modificar ou apagar aquela instância.

Mensagens autodescritivas

Cada mensagem deverá conter todas as informações necessárias para o processamento daquela mensagem, por exemplo uma mensagem que carrega um pdf, deverá conter esta informação nela para que os seus dados sejam processados corretamente.

Hipermedia como engine de estado da aplicação

Os clientes podem fazer transições de estado somente através das ações que foram identificadas com a hipermedia do servidor, ou seja, todas as ações devem estar descritas em algum arquivo loalizado no servidor em que a implementação do REST estiver disponível.

Apresentação
Este post continua aqui com exemplos de código

terça-feira, 14 de outubro de 2014

Usando o método filter para extrair dados de uma collection no Java8

Este post vai descrever o método funcional filter, que foi adicionado no java 8 e ajuda trabalhar com as collections do java.
Para todos os exemplos, podemos considerar as classes deste repositorio

Filter

O método filter é um método funcional bem interessante, com pode-se filtrar os elementos de uma lista. Imagine que voce possui uma lista de usuários, e nesta objeto usuario existe um atributo chamado idade.
Para selecionar todos elementos daquela lista que sejam maiores de 18 anos, você pode usar o método filter, como mostrado abaixo:
List<Usuario> lista = new ArrayList<Usuario>();             lista.add(new Usuario(1,"Menor de idade",17));                  lista.add(new Usuario(2,"Maior de idade", 19));                  lista.add(new Usuario(3,"Idoso",70));                          Stream<Usuario> maioresDeIdade = lista.stream()                      .filter(f -> f.getIdade()>=18);
Da lista obtivemos uma Stream de usuários, que só contem os objetos de usuários onde o atributo idade for maior ou igual a 18. O filter retorna uma nova instância de stream contendo somente os elementos que obedecem a checagem lambida, que neste caso é se a idade é maior ou igual a 18.
Pode-se realizar múltiplas checagens dentro de um filter, como mostrado abaixo:
Stream<Usuario> maioresDeIdade = lista.stream()                      .filter(f -> f.getIdade()>=18 && nome.startsWith("D"));
Checagens com and e or podem ser realizadas da mesma maneira que são feitas nos ifs.
 

segunda-feira, 13 de outubro de 2014

Interface Stream do Java 8

Muitas novidades apareceram na versão 8 do java, e a interface Stream foi uma delas.
Esta interface foi criada para facilitar a vida de quem programa com as collections.
Ela provê métodos funcionais para as collections do java e para criá-la foi criado um método de factory na Interface Collection. Este método pode ser usado da seguinte forma:
List<Usuario> lista = new ArrayList<Usuario>();                                         Stream<Usuario> streamDeUsuarios = lista.stream();
Um ponto importante sobre os streams é, eles não armazenam dados, eles são apenas um Wrapper para as classes já existentes.
Com os streams podemos paralelizar as operações realizdas em uma collection, para isso bastamos utilizar o método parallel.
Stream<Usuario> paralela =  maioresDeIdade.parallel();
Este método retorna uma cópia do stream, podendo ser ele mesmo caso ele já seja uma stream paralela, onde as operações realizadas nesta stream serão processadas em paralelo com multithreads. Para saber mais sobre programação paralela em Java, consulte aqui e aqui.
É claro que usando o método parallel você não precisa fazer nada, simplesmente usando o método parallel, a JVM já faz tudo pra você.
Esta nomenclatura é um pouco confusa no início, já que o pacote de java.io implementa um outro tipo de stream. Não confunda os streams das collections, com os streams de IO (*InputStream, *OutputStream).
Os métodos mais importantes da interface stream são:

  • filter
  • forEach
  • findFirst
  • orElse
  • of
  • reduce
  • count
  • distinct
  • max
  • min
  • first
As streams não possuem suporte a acesso indexado dos dados, você pode acessar o primeiro elemento de um stream, através do método first, mas não há como acessar os outros elementos de uma forma indexada.

quinta-feira, 9 de outubro de 2014

Evitando NullpointerException no Java 8 com Optional Funcional

Neste post será apresentado uma maneira Funcional de como programar um Optional que é uma novidade do java 8

Usando o método map

O método map usa uma expressão Lâmbida para produzir um resultado. Um programador acostumado com as versões <8 do java, tende a utilizar o optional da seguinte maneira:
Optional<Integer> optIntValor = Optional.of(10);
Integer valor;
if(optIntValor.isPresent()){
   valor = optIntValor.get()*2;
} else {
   valor = 0;
}
O uso do if é bem comum na programação orientada a objetos, porém no java 8 é possível programar de uma maneira diferente, usando a programação funcional com as expressões Lâmbida. Para fazer a mesma coisa de uma maneira funcional usamos o seguinte código:
Optional<Integer> optIntValor = Optional.of(10);
Integer valor = optIntValor.map(vlr -> vlr*2).orElse(0);
O que deixa o código bem mais compacto e bem fácil de entender, o método map só é executado quando o Optional tiver um valor e quando ele for executado o seu valor será multiplicado por 2, senão o valor retornado será 0.

Usando o método flatMap

O método flatMap é bem parecido com o map, e seu uso se aplica quando temos dois opicionais.
Imagine uma estrutura de objetos de modelo da seguinte forma:
class Endereco  {
    public Optional<String> getComplemento() {
        return complemento;
    }

    private Optional<String> complemento;
    public Endereco(String rua, Optional<String> complemento){}
}
class Usuario{
    public Optional<Endereco> getEndereco() {
        return endereco;
    }

    private Optional<Endereco> endereco;
    public Usuario(String nome, Optional<Endereco>endereco) {}
}
Considerando que os seus constutores setem os valores corretamente. Para pegar umv valor do complemento do endereço, a partir de uma instancia da classe usuário, devemos passar por dois optionais:
Endereco end = new Endereco("rua",Optional.of("Bloco C 22"))  ;
        Usuario usuario = new Usuario("nome",Optional.of(end));
        Optional<Optional<String>> comp = usuario.getEndereco().map(endereco -> endereco.getComplemento());
E o resultado disto é produzir um objeto Optional do Optional, e para resgatarmos o seu valor teremos que fazer comp.get().get(), mas isso não parece ser algo muito útil.
O método flatMap serve exatamente para isso, nestes casos ele nivela o objeto, eliminando um dos Optionals.
 Optional<String> comp = usuario.getEndereco().flatMap(endereco -> endereco.getComplemento());
Agora o resultado do objeto é um Optional e podemos trabalhar com ele como foi mostrado aqui.
Caso qualquer uma das instâncias dos Optionals forem vazias, ele retornará um valor vazio.

Usando o método filter

O método filter, como o seu nome diz, serve para filtrar valores, imagine que você tem um Optional e gostaria de garantir que o valor contido nele seja maior do que 10, para isso basta usar o método filter
 optIntValor.filter(vlr -> vlr>10);
Caso o valor contido no objeto optIntValor seja menor ou igual a 10 ele irá retornar um optional vazio, do contrário ele irá retornar um optional com o valor que o optIntValor continha.

Expressões Lambda com a interface Function no Java 8

No java 8 o java entrou no mundo da programação funcional através das expressões de Lambda. Para usar estas expressões Lambda, fazemos o uso da interface Function.
Esta interface é definida pelo código:
@FunctionalInterface
public interface Function<T,R>
Esta Function contem dois atributos, o T e o R, onde T é o tipo de entrada desta função e R é o resultado desta função. Uma function sempre é aplicada em um valor, e produz um resultado a partir deste valor.
Por exemplo a sintaxe usada para se criar uma função Lambda usa o operador ->, como mostrado no exemplo abaixo:
Function<Integer,String> f = v -> v.toString();
Esta expressão irá fazer uma simples transformação de Integer para String, v é o valor de entrada da expressão Lambida, e o código que está do lado direito da -> é o que será realizado com o valor v para obter o resultado, que neste caso é simplesmente um toString.
As expressões lambidas podem ser usadas nos métodos funionais da linguagem, entre eles o map, flatMap, filter, etc.

terça-feira, 7 de outubro de 2014

Novidades do Java8

Novidades do Java8

Esta série de posts no blog irão tratar as evoluções que aconteceram nesta versão do Java 8.

Java 8 Optional - Evitando NullPointerExceptions

Java 8 Optional - Evitando NullPointerExceptions

Com a introdução do Optional no java, podemos construir métodos evitando aqueles checks infinitos por variáveis nulas.

Definição do Optional

Optional é uma classe do pacote java.util, ela é tipada, e devemos usá-la no lugar do null. Claro que não poderemos usá-la em qualquer substituição ao null, como esta não é uma classe serializável, e por isso não é indicado o seu uso na camada de modelo, DTO e parâmetros de métodos ou construtores.
Recomenda-se usá-la como retorno de métodos onde existe a possibilidade de retornarmos nulo. Para construir um valor Optional usamos o método of da seguinte forma:
//Valor numérico Inteiro 10
Optional<Integer> optIntValor = Optional.of(10);
//Sem valor
Optional<Integer> optIntVazio = Optional.empty();
Com isto construímos dois objetos opcionais, sendo o primeiro deles com um valor 10 e o segundo, sem nenhum valor o que é equivalente ao null.
Tendo um Optional como retorno de um método, como recuperamos o valor contido nele?
Existem algumas formas de se fazer isso, desde um simples get:
Integer valor = optIntValor.get()
O que recupera o valor do objeto para a nossa variável, mas e se o objeto não tiver nenhum valor? Bom neste caso este método irá disparar uma exceção do tipo NoSuchElementException.
Para evitar esta exceção podemos usar algumas estratégias diferentes descritas abaixo:

Verificar o valor antes  

Aqui vamos usar a mesma estratégia que usamos nas variáveis que podem ser nulas.
if(optIntValor.isPresent()){
            Integer valor = optIntValor.get();
        }                                     else {
            //Código    quando não existir valor
        }
O método isPresente retorna verdadeiro quando o objeto tiver um valor, e falso quando ele não tiver nenhum valor.
Bom até ai fica a impressão que só estamos adicionando código inútil e não estamos fazendo nada de diferente do que fazíamos com o null

Variáveis com valores padrão

Existem casos onde os valores das nossas variáveis podem assumir algum valor, quando não houver nenhum valor atribuído a ela. Por exemplo na criação de uma conta bancária, se não houver nenhuma operação o saldo desta conta será 0, e como fazemos isso com optional no java?
optIntValor.orElse(0);
O método orElse foi criado para suprir estes casos, quando o optional contiver um valor, ele retorna o valor do optional, mas se ele for vazio, ele irá retornar o valor passado como argumento do método. No caso acima ele irá retornar 10, pois na construçao do objeto optIntValor foi setado o valor 10. Caso este método seja aplicado ao outro objeto construído no início deste post:
optIntVazio.orElse(0);
Neste caso, ele iria retorna 0, pois o objeto optIntVazio não contem nenhum valor associado a ele.

Disparando uma exceção se o objeto for vazio

Um outro caso muito comum, é ter que disparar uma exceção caso o valor do objeto seja nulo. Não confundir isso com o construtor dos objetos onde geralmente disparamos uma IllegalArgumentException.
        try {
            optIntVazio.orElseThrow(Exception::new);
        }catch(Exception e){
           
        }
Neste caso ele irá disparar uma Exception caso o optIntVazio não contenha nenhum valor.
Note que tem alguma coisa nova no argumento deste método, ele recebe um objeto do tipo Supplier, explicado aqui, que neste caso é a Exception::new.

Usando o método orElseGet

O método orElse é bem útil quando vamos retornar um objeto que tenha um construtor simples, porém quando temos um objeto Optional que contenha um construtor com vários parâmetros podemos utilizar o método getOrElse que recebe um Supplier como parâmetro. 

Programação funcional com o Java 8. Fazendo funções com o Supplier

No java 8 existem duas interfaces que ajudam na programação funcional com o java e elas fazem parte do pacote java.util.function. Uma lista completa das classes deste pacote pode ser vista aqui.

Supplier

A interface supplier representa uma função que não contem nenhum argumento e produz um resultado de um tipo arbitrário. Uma implementação de Supplier pode referenciar um construtor.

Supplier referenciado por um construtor

Neste tipo de utilizacao, o supplier irá chamar direto um construtor da classe Usuario para instanciá-la.
Supplier<Endereco> supplierEndereco = Endereco::new;
Endereco endereco = supplierEndereco.get();
O :: new indica que o construtor da classe Endereco devera ser chamado. Neste caso estamos chamando o construtor sem argumentos da classe Endereco e o método get retornara o resultado da chamada a este construtor.

Supplier referenciado por um método estático 

Neste tipo de utilização, o supplier utiliza uma instancia de uma fábrica de enderecos para instanciá-lo.
Supplier<Endereco> supplierEndereco = FabricaEndereco::fabricaEndereco;
Endereco endereco = enderecoSupplier.get();

class FabricaEndereco {
  public static Endereco fabricaEndereco() {
    return new Endereco();
  }
}
Aqui basta indicarmos a classe da fábrica e o método que será utilizado para construir o endereço, separados pelo ::. FabricaEndereco é a classe da fábrica de endereços e fabricaEndereco é o método que será utilizado para construir a instância do endereço que será retornada pelo método get().

Supplier referenciando uma instancia

Esta é a forma de utilizar um método local para instanciar a classe endereço
Supplier<Endereco> enderecoSupplier = this::produtorDeEndereco;
Endereco endereco = enderecoSupplier.get();

private Endereco produtorDeEndereco(){
  return new Endereco();
} 
Assim como estamos acostumados a usar no java, o this neste caso indica que utilizaremos um método da instância corrente para construir uma nova instancia do Endereço, que neste caso é o método produtorDeEndereco. Para utilizar este tipo de criação do Supplier, a classe onde ele for utilizado, deverá ter um método produtorDeEndereco que retorne uma instância do endereço.