You are on page 1of 13

artigo

RESTful Web Services e a
API JAX-RS
Conheça o poder dos serviços REST e a implementação de
Referência da Sun, o Jersey.

Com o surgimento de vários padrões para comunicação
entre aplicações com Web Services, aparece uma solução
simples e inovadora chamada REST. Seguindo os conceitos
de praticidade do protocolo HTTP, REST surge como uma
nova opção para problemas de integração nos projetos de
software, tornando-se uma opção viável aos Web Services
baseados em SOAP, WSDL e WS-*. Neste artigo vamos abordar
o que é REST, apresentar a API JAX-RS para geração de web
services baseados em REST e, por fim, vamos demonstrar
diversas maneiras de testar e consumir serviços RESTful com
diversos códigos de exemplo.

N o ano 2000, um dos principais autores da especificação HTTP,
o cientista Roy Fielding, apresentou em sua tese de doutorado
(ver referências) uma nova forma de integrar sistemas hipermídias distri-
buídos chamada REST (Representational State Transfer), baseada nos mes-
mos princípios de arquitetura por trás da World Wide Web (www), atraindo
assim grande atenção.

Uma das grandes novidades no lançamento da especificação Java EE 6 é
Wagner Roberto dos Santos BJODMVTÍPEB+43 RVFEFmOFB"1*+"934 +BWB"1*GPS3&45GVM8FC
(wrsconsulting@gmail.com): é lead editor da queue Arquitetura Service). Neste artigo, vamos entender os conceitos por trás do REST e
do portal Infoq Brasil (www.infoq.com/br), é entusiasta do
NetBeans IDE, tendo diversas participações na criação de plugins,
veremos o quanto é simples desenvolver serviços REST com Java fazendo
traduções e testes do IDE. Palestrante em diversos eventos VTPEBTBOPUBÎÜFTEP+"934
nacionais e vencedor de muitos prêmios de desenvolvimento,
possui as certificações SCJA, SCJP, SCSNI, SCJWSD, SCBCD e Veremos também diversas maneiras de se consumir e testar um serviço
CSM, atualmente presta consultoria como Arquiteto Java e
Metodologias Ágeis. Nas horas vagas, mantém o blog http:// REST, com o uso de bibliotecas JavaScript e outras opções para o consumo
netfeijao.blogspot.com/. destes serviços em Java.

br. sem rótulo para formato de dados chamado MIME type. um nome  (URN) ou ambos. A internamente PDF Reader para arquivos pdf. e assim por diante. então você utiliza um cliente HTTP todos os dias. LDAP etc. como abrir precisa implementar uma das várias versões do protocolo HTTP. que precisa se preocupar apenas com a programação da aplicação. Introdução ao HTTP – Hypertext Transfer Recursos Web Protocol Recursos web são todos os recursos hospedados em um servidor web. um cliente web qualquer faz uma requi- URL é o formato mais conhecido por ser o meio de localização de sição HTTP (Request) para o servidor que hospeda a página www. geralmente na Inter- navegador do usuário. a da web. o servi. livro. arquivos Flash e muitos outros tipos de estática html até um web service. identificação.jsp. Uma URI pode ser classificada como um local (URL). Facilitando a vida tanto do usuário eletrônicos de e-mail. status de retorno entre outras informações. No exemplo da figura 8. é qualquer fonte de conteúdo que gere um valor para Atualmente bilhões de páginas HTML. um código de barras ou o SBN de um dor. podemos citar desde uma simples página arquivos de música MP3. mundoj. Por exemplo. estado (stateless). Como exemplo. Neste caso. o media player para versão mais atual do protocolo HTTP é a versão 1. MIME foi projetado inicialmente para resolver os problemas en- dos seguro que garante que a informação não será danificada ou contrados ao mover tipos de mensagem diferentes entre sistemas perdida durante o transporte. Segue um exemplo dessa sintaxe em um caso real: Figura 8. que não precisa se preocupar que suas informações sejam especificação HTTP foi atualizada para descrever os tipos de conte- perdidas durante uma transação. a URL define a localização deste mesmo item na rede.br . Clientes web e servidores. por exemplo. Para um servidor ser considerado um conteiner web. e facilita a vida do desenvolvedor údo multimídia com o uso de rótulos MIME. que utiliza um protocolo de transmissão de da. uma URI é uma string compacta única utilizada ções HTTP a objetos em servidores web e os apresentam na tela do para identificar um recurso físico ou abstrato. ou seja.mundoj. os navegadores conseguem renderizar o formato dos res web.com. como o tipo do objeto. definidos para diversos propósitos como DNS. o URN significa (Uniform Resource Name) e pode ser atribuído a um servidor retorna para o cliente uma resposta HTTP (Response) em nome de uma pessoa ou pode ser utilizado para identificar um conjunto com outras informações. para rotular um tipo de arquivo html. Os navegodores web fazem requisi- Em computação. como. filmes AVI. existem diversos URI Schemas oficiais registrados pela IANA (Internet Assigned Numbers Authority). recursos que utilizamos ao navegar pela Internet. E o HTTP é o protocolo responsável por transferir esta grande quantidade de informações de uma maneira rápida. Veja um exemplo desta interação na figura net. entre outros. a página /default.com. utilizaríamos o Clientes Web e Servidores tipo text/html. Neste caso um navegador web qualquer como o Mozilla URI Firefox ou o Internet Explorer. a web. Com o sucesso desta solução para e-mail. imagens JPEG. arquivos wmv. de diversos servido- Media Types res web ao redor do mundo para os navegadores web das pessoas Por conta dos diversos tipos de conteúdo que trafegam na internet.1. para documentos texto definimos text/plain. objeto. Ela possui uma sintaxe genérica composta de quatro partes definidas pelo padrão EF*OUFSOFU3'$ BQSFTFOUBEBBCBJYP TDIFNF OBNF  IJFSBSDIJDBM QBSU <  RVFSZ > <  GSBH- NFOU> As URIs são definidas em esquemas que definem uma sintaxe es- pecífica para cada tipo e protocolo associado. 62 www. Ao localizar a página. ele dados e apresentar o recurso de maneira adequada. o protocolo HTTP trata cada recurso trafegado pela web com um Isso tudo é possível porque o HTTP é um protocolo genérico. conteúdo circulam pela internet a cada dia. FTP. em seus desktops. Por conta desta Todo conteúdo da internet é armazenado em um ou mais servido. para arquivos JPEG utilizamos image/jpeg. Enquanto uma URN define a identidade única de um item. o servidor web tenta localizar o documento de- sejado. Se você acessa a internet. conveniente e segura.

como. como TRACE. ou seja. destes recursos e seus identificadores (URIs) e as suas representações que REST. O caminho "produto/ POST Foi projetado para envio de dados de informatica" indica onde o recurso se encontra no servidor. Para tanto.com. para identificação ou especificar o tipo de retorno do recurso. E HEAD Mesmo comportamento que o mé- finalmente o fragmento "bookmark". executar um programa. que não é transmitido para todo GET. O host no trecho "www. PUT O inverso do GET. Segue.- NFEJBOUFBEJHJUBÎÍPEFVNB63- servidores.exemplo. pois o verbo irá determinar Tabela 2.doc a classificação dos tipos de códigos de status que podemos receber de URI que identifica um recurso no disco. recurso. é um estilo de arquitetura de software para sistemas hipermídia distribuídos. ou ainda o 404 Not Found? Métodos Range definido Descrição Quando fazemos uma requisição HTTP a servidor web. JOGPSNBUJDB DPEJHPCPPLNBSL Para quem conhece ambientes web.br/produto/ mais comuns. como: gateways.exemplo.com. Na tabela 1 apresentamos os métodos http://www. http://www. Veja apenas o cabeçalho da resposta. por exemplo. na tabela 2.).br" identifica o servidor. Afinal. conhecidos também como verbos. como. o que é REST? Conforme a definição do criador Roy Fielding em sua tese de doutorado.- JNBHFOTFUD tado Representativo). EPDVNFOUP9. schema. geralmente uma página HTML. proxy e user agents. a query input. fica muito fácil compreender Método Descrição esta URI decompondo o exemplo acima e associando cada parte GET Solicita que o servidor envie um definida na sintaxe genérica com cada parte do nosso exemplo. Realiza operações Podemos reconhecer no exemplo o trecho http como sendo o de escrita no servidor. porém o servidor retorna o servidor. foram disponibilizados alguns méto- dos HTTP.mundoj. neste caso a página do site da revista Mundoj. 300-305 Redirecionamento Toda mensagem HTTP possui um método. ou um sentação de um recurso. livro. OPTIONS e métodos de Código ISBN que é uma URN e que identifica o código de um extensão do HTTP como WebDAV. 500-505 Erro do servidor excluir um arquivo etc.- 9. o exemplo mais comum Elementos de dados: são classificados como os recursos. os dados DPEJHP  RVF VUJMJ[BNPT QBSB BEJDJPOBS JOGPSNBÎÜFT FYUSBT de um formulário para o servidor. Toda resposta do servidor Web a uma requisição vem com um código de status utilizado para identificar o status da operação. O HTTP suporta diversos tipos 200-206 Sucesso de comandos de requisição e chamados de métodos http. Ainda em sua tese. Conectores: são os vários tipos de conectores que REST utiliza para encap- mos atualmente. o metadado é um navegador Web. Fielding afirma que o estilo REST é uma abstração dos Componentes: são classificados pelos seus papéis na ação de uma aplica- elementos arquiteturais de um sistema multimídia distribuído definidos ção. a Web do jeito que conhece. 63 . "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 a ação a ser tomada no recurso. servidor onde está localizado o recurso. cache e tunnel. que define o protocolo utilizado para comunicação com DELETE Solicita a exclusão de um recurso no o recurso. Podemos classificar os conectores como clientes.br/ Código de Status URI que identifica um local (URL). onde utilizamos um navegador web para acessar sular as atividades de acesso aos recursos e a transferência de uma repre- recursos que estamos interessados. por exemplo. que significa Representational State Transfer (ou Transferência de Es. Neste último caso. sendo aplicado apenas no ambiente do cliente. Códigos de status HTTP segmentados em categorias. QPEFTFSVNEPDVNFOUP)5. file:///C:/Wagner/artigos/REST. podemos dizer 100-101 Informacional que estamos enviando uma mensagem.com. os tipos de componentes são classificados como servidores de origem.ÏUPEPTDPNVOTEP)551 *4#/ Ainda existem outros métodos. um servidor web. Quem nunca recebeu o código de retorno 400 de Bad Request. outros exemplos de URIs: 5BCFMB. O método diz ao servidor qual 400-415 Erro do cliente a ação que ele deve tomar (retornar uma página.

br/wagner/fotos/palestra. automatica- A anotação @Path pode ser colocada na declaração de classe ou de um mente associamos estes verbos aos métodos do protocolo HTTP. Métodos HTTP Operações CRUD sos e estes recursos são acessados via URIs (Uniform Resource Identifier).com.br/wagner/fotos/palestra. a arquitetura de um sistema REST geralmente é cliente-servidor e os serviços não possuem estado (stateless). que pode ser adquirido no quadro “Introdução ao HTTP”. Para uma classe ser determinada como um recurso.com. precisamos definir a ação que iremos classe POJO com pelo menos um método anotado com a anotação @ tomar sobre este recurso. em REST estas operações são descritas com o uso de Path. podemos ter uma URI http://www. POST INSERT. Na Listagem 2. Veja alguns exemplos na Listagem 1. demonstraremos como extrair valores como esse de uma Saindo um pouco da teoria proposta pelo dr. Por este elemento defini- o mesmo nome. Neste caso. UPDATE que foi um dos principais autores da especificação do HTTP.exemplo.com. O método PUT nos dá a possibilidade de criar um novo recurso ou substituir exploramos o uso do protocolo HTTP e de URIs de forma natural. Mais adiante.. PUT http://www. como uma div. que possuem método e possui o elemento value obrigatório. fornecido junto a URI. quando criamos web services utili- zando o estilo de arquitetura REST. de modo que 1PEFSÓBNPTUFSFTUFNFTNPSFDVSTPDPNSFQSFTFOUBÎÍPFN9. são Recursos e o que são Representações. Mapeando uma URI para uma classe com @Path. Para um melhor aproveitamento da leitura. 64 www. até pela formação de Fielding PUT CREATE. quatro verbos que são GET. esta URL em browser seria o HTML. } Em RESTful mapeamos os principais métodos HTTP (POST.br . GET http://www. GET E PUT) DPNPQFSBÎÜFT$36% $36%$SFBUF 3FUSJFWF 6QEBUFF%FMFUF EFVNCBODP de dados. Isso mesmo. alterar e excluir os seus recursos.- +40/ +1( possamos fazer uma programação fácil e de alto nível. O método DELETE é utilizado para excluir um re- torna as aplicações mais simples. por exemplo. O formato de uma representação é determinado pelo tipo de conteúdo e no mundo REST a interação com a representação do recurso é determinada Trabalhando com os recursos pelo método HTTP que vamos utilizar. Exemplos de operações REST. ela poderia ser uma página estática HTML. nós estamos utilizando REST há um bom tempo sem darmos conta disso. que {id} é o valor do parâmetro id.jpg Antes de nos aprofundarmos nos conceitos REST. Podemos entender uma URI como um ID único. PUT. retornar. @Path(“/repositorio/{id}”) public class Repositorio { . precisamos distinguir o que Lendo uma foto em um repositório utilizando GET. ou poderia ser um pedaço de uma página.mundoj. Veja a tabela 1. +"934ÏBTPMVÎÍPEP+$1QBSBPFTUJMPEFQSPHSBNBÎÍP3&45"QSPQPTUBmOBM da especificação foi liberada para o público no início de agosto de 2008. o que por outro mais atualizado.br/calcados/tenis/1512 que identifica um DELETE http://www. leves e de alta performance. dados e funcionalidades são considerados recur. curso existente e o método GET que é o método mais utilizado. O objetivo da API é fornecer um conjunto de anotações. pois é uma Representação que foi projetada para Web Services a compreensão dos seres humanos. esta URI é uma URL que aponta para o recurso calcados/ Excluindo uma foto utilizando DELETE. geralmente ao digitarmos esta informação em um browser o retorno provável é em HTML. "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 Em uma arquitetura REST. Os web services RESTful expõem os recursos através de URIs e utilizam os métodos Listagem 2. Admitindo que esta JAX – RS – Java API for RESTful é uma URL válida. Por ser uma URL lógica. utilizando POST.br/wagner/fotos/palestra. que podemos pecificação define um conjunto de APIs Java para auxiliar no desenvolvimento entender como um tênis cujo código é 1512 e a sua representação ao digitar de web services baseados em REST. No mundo web. estamos criando "web services RESTful”. 5BCFMB"TTPDJBÎÍPEPTNÏUPEPT)551DPNPQFSBÎÜFT$36% Ao aplicar os princípios REST no desenvolvimento de uma aplicação web. classes e interfaces Agora porque não criar representações para a leitura de máquinas também? para expor uma classe POJO como um web service RESTful.shopping. do HTTP para criar. mos o prefixo da URI que a classe ou o método irá atender.com. Listagem 1. UPDATE.jpg recurso. pois com ele podemos efetuar operações de leitura em algum recurso ou utilizá-lo como Recursos e representações mecanismo de busca. tenis/1512.exemplo.jpg Podemos atualizar a mesma foto. é recomendado que o leitor tenha um conhecimento básico do Protocolo de Transferência de Hipertexto (HTTP). A es- Ainda neste exemplo. o nosso recurso é calcados/tenis/1512. POST e DELETE. ela tem que ser uma Uma vez que o recurso é identificado. Fielding em sua tese e trazendo URI utilizando anotações específicas. tudo isto para o mundo que conhecemos. Por ser baseado DELETE DELETE em HTTP.exemplo. DELETE. DELETE REST foi concebido baseando-se em HTTP. em Um sistema clássico que utiliza REST e que todos utilizam é a Web.. GET SELECT geralmente via links. etc.com. a classe Repositorio é identificada pela URI relativa “/repositorio/{id}”.

EFGBVMURVBMRVFSUJQPEFSFUPSOP i  w  Listagem 3. na ausência destas anotações. EFSFUPSOPQSJNFJSPDPN9.-FEFQPJTDPN+40/ DPOGPSNFmHVSB O método anotado com @GET. "MÏNEPTNÏUPEPTEFmOJEPTQFMP+"934 QPEFNPTDSJBSVNBBOPUBÎÍPDVTUP- mizada como @MKCOL.”application/json”) @HttpMethod(“MKCOL”) public @interface MKCOL { @Path(“/autores/”) } public Response putPessoa(PessoaBinding pessoa) {} 65 . EPUJQP9. o tratamento da request e response. Representações: Quais são os sabores? sempre que for feita uma requisição a um recurso. Desta @Path(“/vendas/”) maneira. @Path(“/pedidos/{numPedido}/”) public PedidoAsXML getPedido(@PathParam(“numPedido”) Integer id){ @GET // retorna Pedido em formato XML. estas ano- Geralmente a anotação @Path é incluída na declaração de um método tações podem ser aplicadas na declaração de uma classe. a especificação define as anotações @Consumes e @Produces para devidos métodos e o método designado para aquele recurso é invocado. Após diversos tipos de formatos durante um ciclo requisição-resposta. E finalmente após a chamada ao método o objeto fica disponível para o garbage collector. o construtor da classe deve ser público. @ aba “Headers” o parâmetro “Accept” e no campo Value especificar o tipo DELETE. será assumido como exemplo da Listagem 3 como a URI é mapeada com a classe e o método. por padrão. Utilizando a anotação HttpMethod para criar uma anotação customizada. como a ferramenta RESTClient. Primeiro o construtor é chamado pelo As classes de uma aplicação RESTful podem ser declaradas para suportar contêiner. É bom entender o papel e o uso de cada um destes métodos HTTP no momen- to de projetar nossos serviços. irá processar requisições HTTP GET na URI atribuída. será criada uma nova instância de uma classe REST. @Produces({“application/xml”. na qual declaramos que o método consome apenas formatos declaração da anotação ficaria @HttpMethod(“PUT”). "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 A especificação define que no ciclo de vida de um recurso. conforme ilustra a Listagem 4. public class Repositorio { DPNP+40/F9.Testando tipos de retorno para a mesma URI com RESTClient. através do cabeçalho (header) do protocolo HTTP.- DPOGPSNFFYFNQMPEB-JTUBHFN @GET @Produces(“application/xml”) Listagem 5. por exemplo. podemos testar o retorno da cha- mada utilizando uma das ferramentas citadas no tópico “Como consumir 1BSB BDFTTP BPT SFDVSTPT  B FTQFDJmDBÎÍP +"934 EFmOF VN DPOKVOUP EF serviços REST”. Note no declaração da classe. @HEAD. podemos criar métodos customizados e estender a gama dos métodos preexistentes. como fazemos na Listagem 4. para sobrepor o método PUT. ou podemos quando queremos atribuir um caminho mais específico para um recurso. o servidor declara o tipo de conteúdo que será trafegado.RUNTIME) @Consumes(“application/xml”.METHOD) @PUT @Retention(RetentionPolicy. No caso da anotação @Produces. como na Listagem 3. o contêiner efetua as injeções de dependência nos isso. como @GET. com uso da anotação HttpMethod. Também podemos alternar um método padrão para a anotação customizada. por conta disto. Seria possível. Para isso podería- Com a anotação @Consumes. utilizar estas anotações na declaração do método para sobrescrever a de forma a especializar nosso método. Mapeando uma URI para uma classe com @Path. Uso da anotação @Consumes. por exemplo.-F+40/ Listagem 4. a Listagem 6. @PUT. por outro lado. Declarando o tipo de retorno com a anotação @Produces. Com estas anotações. “application/json”}) public PessoaConverter getPessoa(@QueryParam(“CPF”) String numCPF) { } // Retorna representação em XML ou JSON } } Acessando os recursos Pegando o exemplo da Listagem 5. @Target(ElementType. e incluir na anotações correspondentes aos métodos HTTP. podemos definir mais de um tipo de retorno da URI solicitada. respectivamente. podemos definir os tipos mos simplesmente informar como valor para anotação HttpMethod o valor do de mídia que um recurso em particular consome. Elas devem ser atribuídas a métodos públicos. O comportamento do recurso é determinado pelo mé- todo HTTP ao qual o recurso está respondendo. Para este primeiro passo. Listagem 6. ela é utilizada para mapear uma requisi- ção de um cliente com o cabeçalho do cliente (parâmetro Accept). Com esta anotação. Como o exemplo da método que queremos sobrepor. utilizar os métodos Figura 1. Por exemplo. @POST. por exemplo. definidos pelo WebDAV.

@HeaderParam(“CPF”) String numCPF. idade). Anotação Aplicado em Descrição PathParam Parâmetro. Para a recuperação destas informações. Para os parâmetros de URI (path). Uso da anotação FormParam. median- te a aplicação da anotação @Context. vinculados à sessão. um cookie HTTP na invocação de um método. Já para parâmetros de cookie existe @CookieParam. Para contextualizar. mas o seu uso é bem similar. Trata-se de um formulário HTML e de um " FTQFDJmDBÎÍP +"934 EJTQÜF EF VN SFDVSTP QBSB B PCUFOÎÍP EF JO- método que irá receber estas informações. <form method=”POST” action=”/Mundoj/autores”> Nome: <input type=”text” name=”nomeAutor”> <br> Idade: <input type=”number” name=”idade”> </form> @Path(“/Mundoj/”) public class EditoraResource { @GET @Path(“/autores/”) public PessoaBinding getPessoa(@FormParam(“nomeAutor”) String name. método. FormParam Parâmetro. da URI. Anotações JAX-RS para extração de informações da URI. Para os parâmetros de query extraído do valor de um utilizamos a anotação @QueryParam. campo ou Extrai dados do cabeçalho } método. statusCivil). idade. 66 www. CookieParam Parâmetro. @FormParam(“idade”) int idade) { return new PessoaBinding(name. metro indicado na query de método. O valor da anotação identifica o nome Listagem 7. identifica um alvo a ser injetado pelo contêiner. veja râmetro. para os da URI.rs. Especifica que o valor do @Path(“/Mundoj/”) parâmetro será extraído de public class EditoraResource { um parâmetro de formulário @GET no body da requisição. campo ou Extrai os valores (chave/va- public PessoaBinding getPessoa(@PathParam(“nomeAutor”) String name. que ao ser aplicada sobre um campo. numCPF. O contêiner fornece instâncias dos recursos listados na tabela 3. conseguimos injetar o valor de os providers. formações do contexto da aplicação e de requisições individuais. método. URI em um único método. /B-JTUBHFN WFNPTBBQMJDBÎÍPEFWÈSJBTBOPUBÎÜFTEFQBSÉNFUSPEF Tabela 2. } } /P FYFNQMP EB -JTUBHFN  OÍP EFNPOTUSBNPT P VTP EBT BOPUBÎÜFT CookieParam e FormParam. Veja um exemplo simples na Listagem 8. Figura 2. método. Desta forma. apresentado na figura 2. parâmetro. existe a anotação @PathParam. "SUJHPt"VNFOUBOEPBQFSGPSNBODFEP)JCFSOBUFDPN&IDBDIF "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 Extraindo parâmetros e valores da URI na requisição.ws. campo ou proprie- VNFYFNQMPOB-JTUBHFN dade de um bean. Estas informações são disponíveis tanto para as classes recursos quanto para No caso da anotação CookieParam.com. vinculamos o valor do parâmetro de uma URI a uma URI e atribui a um pa- algum parâmetro de entrada de um método. No caso de FormParam. esta anotação pode capturar todos os valores submetidos Dados de contexto de um formulário HTML e injetá-los nos parâmetros desejados. Para os parâmetros de formulário. campo ou pro- requisição. campo ou Especifica que o valor do +"934 GPSOFDF BMHVNBT BOPUBÎÜFT QBSB FYUSBJS JOGPSNBÎÜFT EF VNB método. Para fica o nome do parâmetro os parâmetros de header existe @HeaderParam e. este recurso com a biblioteca curl. existe O valor da anotação identi- @FormParam. @Produces(“application/xml”) @Path(“/autores/{nomeAutor}/”) MatrixParam Parâmetro.br . finalmente. Existem seis tipos de parâmetros (ver tabela 2) que podemos priedade de um bean será extrair para utilizar em nossa classe recurso. de uma requisição HTTP. Mapeando os parâmetros de uma URI para os parâmetros de um do parâmetro na query. parâmetro indicado na URI. } HeaderParam Parâmetro. vamos fazer uma chamada a Listagem 8.core. Fragmentando a URI para demonstrar anotações de mapeamento. campo ou Extrai os valores de cookies @MatrixParam(“statusCivil”) String statusCivil) { return new PessoaBinding(name. parâmetros de matriz existe a anotação @MatrixParam.mundoj. Para entender melhor como será feito o DE- PARA da URI para os parâmetros de entrada. método ou parâmetro. QueryParam Parâmetro. existe a anotação cookie ou a classe Cookie do javax. campo ou Extrai o valor de um parâ- Estas anotações podem ser aplicadas diretamente a parâmetros de um método. que representa o valor de @Context. lor) da matriz de parâmetros @QueryParam(“idade”) int idade.

getAbsolutePath()).io. text segurança. Classe Descrição pelo método entity. o retorno será um corpo vazio com status de diferentes tipos de mensagens. como o caminho absoluto da URI. automaticamente serializar (marshal) e deserealizar (unmarshal) o corpo Para os retornos do tipo void.getNome() método evaluatePreconditions(). baseado em parâ- +”</h1></body></html>”. " FTQFDJmDBÎÍP +"934 EFmOF RVF QBSB BMHVOT UJQPT P DPOUÐJOFS QPEF de acordo com o provider padrão. podemos Todos os tipos de mídias-texto java. pois ela é uma classe abstrata 5PEPT PT UJQPT EF NÓEJBT   StreamingOutput que implementa o padrão de projeto Builder. passando como parâmetro a URI que obtemos através YNMFBQQMJDBUJPO . e o esquema de autenticação utilizado. um código HTML simples. 5PEPTPTUJQPTEFNÓEJBT  java. Pois informações de tipos genéricos injetada em um parâmetro de método ou campo de são apagadas ao utilizar uma instância. Para tratar o retorno ao cliente foi disponibilizada a classe abstrata Response.File /B-JTUBHFN OPNÏUPEPQVU1FTTPB GB[FNPTVTPEPNÏUPEP3FTQPOTF 5PEPTPTUJQPTEFNÓEJBT  javax. como uma entity tag.transform. entre outras informações.xml. a negociação @Consumes(“application/xml”) do conteúdo e as pré-condições da chamada ao @Path(“/Mundoj/update/”) método e determina a melhor representação pelo public Response putPessoa(PessoaBinding pessoa) { String retorno = “<html><body><h1>Bem vindo “+pessoa.io. adicionar dados no Header. SecurityCon. especifica- UriInfo Esta classe fornece informações relativas à URI NPTPUJQPEFNÓEJBUSBGFHBEP OFTUFDBTP5&95@)5. Response response = Response. Com essa classe. type(MediaType. entre as informações. Pode ser lizada e reter informações genéricas.ACCEPTED). conforme veremos a seguir. adicionar cookies. Entity providers Tratando o retorno dos métodos ao cliente Entity providers fornecem serviços de mapeamento entre representa- Os tipos de retorno de uma chamada a um método recurso podem ser do ções e seus tipos associados Java. retornados como chave- valor pela classe MultivaluedMap. Resource. quando uma classe precisa Tipo de mídia Tipo Java fornecer metadados para ambiente de execução. adicionar 5PEPTPTUJQPTEFNÓEJBT  java.Fornece informações relacionadas ao contexto de status(Response. Existem dois tipos de entity providers. no são mapeados ao entity body da Response cada um de uma maneira. Na chamada ao método type seguinte. definimos um contrato entre a ins- tância de retorno e o ambiente de execução. muito útil quando precisamos retornar uma Response persona- HttpHeaders Fornece informações sobre o Header HTTP. ainda melhor.Status.String criar uma instância utilizando sua classe interna ResponserBuilder.lang.InputStream metadados. genérico. podemos construir objetos do tipo Response.-/PmOBM GB[FNPT requisitada.created(uriInfo. informar a 5PEPTPTUJQPTEFNÓEJBT  java. "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 uma entidade à requisição. Esses tipos de retor. os valores do Listagem 9.io. metros. listados na tabela 4. header da requisição HTTP. Lista de recursos injetados pelo contêiner pela anotação @Context.TEXT_HTML).- UFYUYNM BQQMJDBUJPO javax. Providers Esta classe fornece um meio para efetuar lookups build(). busca.DataSource Note que não a instanciamos diretamente. GenericType ou outro tipo Java.Reader linguagem.activation. parâmetros de query. No nosso exemplo. } Tabela 3. uma classe. Tratando a Response do cliente. tipo void. MessageBodyReader e MessageBodyWriter. em instâncias de providers baseado em critérios de return response. somente MessageBodyWriter Dentro do método. entity(retorno). 204 do HTTP. 5PEPTPTUJQPTEFNÓEJBT  CZUF<> Podemos estender esta classe diretamente ou. que constrói o objeto Response. os uma chamada ao método build. por exemplo. @Context protected UriInfo uriInfo. podemos saber os tipos de mídia e linguagens aceitas. Por UFYU essa classe.Source estático created. entre outras informações. Na -JTUBHFN OØTBVUJMJ[BNPTQBSBCVTDBSPDBNJOIP E por fim o objeto GenericEntity representa uma entidade de um tipo absoluto da request. @PUT Request O uso de Request simplifica o suporte. primeiramente efetuamos uma chamada ao método 5JQPT9.

esta subclasse é utilizada exclusiva.YNM da classe injetada UriInfo. YNMFBQQMJDBUJPO . Esta classe retorna o objeto ResponseBuilder.- UFYUYNM BQQMJDBUJPO KBWBYYNMCJOE+"9#&MFNFOU F que é uma subclasse de Response. 5JQPT9.

Conteúdo de Formulário MultivaluedMap<String. Após a chamada ao método created. podemos coded) efetuar chamadas recursivas aos métodos de parametrização. no qual atri- buímos o código de status HTTP 202 (Accepted) e logo após atribuímos 5BCFMB5JQPTEFNÓEJBFTFVTUJQPT+BWBDPSSFTQPOEFOUFT 67 . String> (application/x-www-form-urlen- Por ResponseBuilder ser uma classe de construção (Builder). chamamos o método status.YNM DMBTTFT+"9#EFBQMJDBÎÍP mente para criar instâncias de Response.

o valor de retorno é mapeado @GET para o corpo da entidade de um método HTTP com uso da interface @Produces(“application/xml”) MessageBodyWriter<T>. tputStream para objetos Java do tipo T. Testando e consumindo serviços REST mentação de StreamingOutput. a especificação define a providers com o mesmo nome em diferentes bibliotecas. Annotation annotations[]. para o tratamento das responses. Class<?> type. MJNJUBÎÍP B"1*+"934QFSNJUFRVFBDSJBÎÍPEF1SPWJEFSTQBSB. @Path(“/autores/{personName}/{idade: [0-9]+}/”) public PessoaBinding getPessoa(@PathParam(“personName”) String name. da Sun. idade. } Para criar nosso próprio provider customizado. ma maneira que registramos MessageBodyReaders e MessageBodyWriters. parâmetro de método com uso da interface MessageBodyReader<T>.build(). que é mapeada para Response. "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 Para requisições HTTP. estes tipos pa. public boolean isWriteable(Class<?> type. o contêiner irá em tempo de execução p.isAssignableFrom(type). @HeaderParam(“CPF”) String numCPF) throws IdadeInvalidaException { if (idade <= 0 || idade > 120) Tratando exceções throw new IdadeInvalidaException(“Idade Inválida!”). Object> headers. public Response toResponse(IdadeInvalidaException ex) { return Response. esta classe implementa um MessageBo- @Provider dyWriter para uma classe Properties. essa exceção é mapeada a um Porém. podemos utilizar um código de status server-side.store(out. e essa já é uma das promessas para a 68 www. Type genericType.getMessage()). idade. na Listagem 10.status(412). @PathParam(“idade”) int idade. Mapeando uma exceção Java para uma Response. @GET Annotation annotations[].com. } return new PessoaBinding(name. Para tanto. @HeaderParam(“CPF”) String numCPF) { drões não atendam à necessidade de negócio e tenhamos que lidar com if (idade <= 0 || idade > 120){ tipos que não sejam suportados pelos tipos default. que ao ser aplicado sobre uma classe. MediaType mediaType) { return Properties. null). a implementação Caso a aplicação necessite de informações adicionais.br .mundoj. Veja um exemplo extraído de um sample da implementação de referência Listagem 12.FTTBHF entity(“Idade inválida!”). MediaType mediaType. @Produces(“text/plain”) } @Provider } public class PropertiesProvider implements MessageBodyWriter<Properties> { public void writeTo(Properties p. numCPF). Body customizáveis. é importante ressaltar que esta funcionalidade apesar de muito código de status HTTP adequado. Veja um exemplo na ou um código de status diferente. Annotation annotations[]. numCPF). } public long getSize(Properties p. 1PS QBESÍP  RVBOEP VNB DMBTTF +"934 PV VN NÏUPEP QSPWJEFS MBOÎB uma exceção em tempo de execução. return new PessoaBinding(name. MultivaluedMap<String. Uso de exceção com WebApplicationException. o método pode retornar o objeto Res.build()). podemos criar nossos próprios providers e customizar este mapeamento.class. como HTTP Headers desta interface deve estar anotada com @Provider. interface ExceptionMapper. 1BSB USBUBNFOUP EF FYDFÎÜFT  B FTQFDJmDBÎÍP +"934 EFmOF B FYDFÎÍP } WebApplicationException que estende RuntimeExcetion. Esta exceção permite que abortemos a " FTQFDJmDBÎÍP +"934  DPNP WJNPT BOUFSJPSNFOUF  Ï VNB ØUJNB PQÎÍP FYFDVÎÍPEFVNTFSWJÎP+"934 para criar web services REST e fornece meios de desenvolver componentes Como parâmetro de construtor.status(412). para contornar esta throw new WebApplicationException(Response. Type genericType. public class IdadeInvalidaExceptionMapper implements ExceptionMapper<IdadeInvalidaException>{ Listagem 10. Listagem 12. a especificação disponibi- liza a anotação @Provider. estamos automaticamente registrando esta classe junto ao contêiner. com métodos para conversão de InputStream/Ou. podendo ocasio- nar conflitos. Ao utilizarmos a exceção IdadeInvalidaException em um método RESTful OutputStream out) throws IOException { como no método da Listagem 13. que podem utilizar exceção conforme a necessidade. que pode ser lançada por um método de recurso por um provider ou por uma imple. @Path(“/autores/{personName}/{idade: [0-9]+}/”) } public PessoaBinding getPessoa(@PathParam(“personName”) String name. identificar o provider e irá mapear esta exceção com IdadeInvalidaExceptio- } nMapper. Para isto. podemos mapear o corpo da entidade para um Listagem 11. Com ela. Veja um exemplo na Listagem 11. MediaType mediaType) { @Produces(“application/xml”) return -1. Uso de exceção de negócio. o Jersey. seus componentes client-side em Java. mas não descreve como os desenvolvedores devem desenvolver HTTP ou até um objeto Response. Pode ser que no desenvolvimento de nossas aplicações.entity(ex. Listagem 13. Type genericType. Na Listagem 12 perceba que registramos a classe ExceptionMapper da mes- Class<?> type. } @PathParam(“idade”) int idade. Nós podemos customizar a nossa útil pode ser tornar um problema em grandes projetos. ponse que encapsule a entidade. Uso da tag @Provider.

"SUJHPt"VNFOUBOEPBQFSGPSNBODFEP)JCFSOBUFDPN&IDBDIF "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 QSØYJNBSFMFBTFEP+"934 RESTClient Pelo fato de nossos serviços RESTful serem URIs e a forma de acesso a estes ser. montamos um pequeno guia para os desenvolvedores e estudiosos que querem aprender um pouco mais sobre REST. 69 . Felizmente wnload (veja o site nas referências) do arquivo jar (com dependências). urllib2 e httplib em Python. RESTClient é uma aplicação Swing própria para viços serem os próprios métodos HTTP. 1º montar os dados que irão trafegar pela requisição HTTP. cliente/".getView(). como a URI. Mas para qualquer linguagem que seja feita uma tela bem intuitiva. HTTPWe. Uso da biblioteca cURL. app."phon Test Script. basta digitar no campo URL o caminho desejado. selecionar localhost:8080 algum método HTTP na aba Method.A Revista do profissional Java!”)."name":"Livermore Ainda é possível fazer testes unitários baseados em JUnit 3. e DPNFÎBSBVUJMJ[BSEJHJUBOEPPDPNBOEPKBWBoKBSSFTUDMJFOU99KBSXJUI as linguagens mais populares de programação possuem métodos/bibliotecas EFQFOEFODJFTKBS FNRVF99ÏPOÞNFSPEBWFSTÍPBUVBM0VUSBPQÎÍP HTTP. como. pela opção Enterprises". Ao optar por qualquer uma das opções será apresentada da Apache para Java. FTPS etc. a requisição ao serviço RESTful. Para utilizar. entre outros. e enviá-los para um servi. é executar RESTClient diretamente pela sua aplicação. Listagem 14."discountCodeRef":{"@uri":"http:// de utilizá-la."addre ssline1":"9754 Main Street". Ela suporta protocolos como HTTP.com". no qual iremos apresentar algumas bibliotecas para teste e consumo de serviços RESTful. Como o nome sugere. Para facilitar a pesquisa. 2º formatar estes dados como uma requisição HTTP.O."state":"FL".x. É possível testá-los curl -v –X DELETE http://localhost:8080/ContatosMJ/resources/customers/99/ clicando com o botão direito do mouse em cima do projeto e selecionar Registro excluído com sucesso ! a opção “Test RESTful Web Services” (figura 4). dor HTTP apropriado. podemos deduzir facilmente o modo Limit":"50000". A Listagem 14 apresenta exemplos de como fazer uma requisição GET e POST com uso da biblioteca cURL."customerId":"2". sendo uma ferramenta de linha de comando. outra opção para testar Web Services customers/2/cliente/ RESTful é utilizar o suporte do próprio IDE. lembrando que esta opção só estará disponível se o projeto WEB possuir serviços REST. e é relativamente fácil trabalhar diretamente com requests e responses HTTP. HTTP public static void main(String[] args) { header (se houver) e o método HTTP desejado. que é uma ferramenta de transferência de ar- quivos entre cliente-servidor desenvolvida em C."fax":"305-456-8889". podemos trabalhar diretamente com auxiliar nos testes de serviços RESTful. conforme segue: Listagem 15. Como podemos ver. passando como query parameter name = Testando Web Services RESTful no NetBeans JumboComLtda curl -d name=JumboComLtda http://localhost:8080/ ContatosMJ /resources/ Para quem é usuário do NetBeans."addressline2":"P. FTP."zip":"33055"} // Fazendo uma requisição POST. e":"305-456-8888". como fazemos na C3FRVFTUFN$ PQFOVSJFN3VCZ FPQBDPUFKBWBOFU FPQSPKFUP)UUQ$MJFOU Listagem 15. ela não possui uma interface gráfica. por exemplo. libcurl em PHP."city":"Miami"."e mail":"www. cURL Se o intuito for apenas testar os serviços REST desenvolvidos e validar o retorno. temos que passar por alguns passos. com um projeto Web criado // Excluindo um registro com DELETE. basta efetuar o do- requisições HTTP ou utilizar bibliotecas para facilitar este trabalho. RESTMain app = new RESTMain(“Mundoj . curl http://localhost:8080/ContatosMJ/resources/customers/2/cliente/ result: {"@uri":"http://localhost:8080/ ContatosMJ/resources/customers/2/ Figura 3. Box 567". HTTPS. pelo parâmetro –X e os serviços RESTful devidamente configurados. } FGFUVBSPQBSTJOHEPTEBEPTSFUPSOBEPT 9. Chamando o Aplicativo RESTClient via código. o mais simples é utilizar ferramentas existentes na web como é o caso da biblioteca cURL. e executar a consulta clicando no /CustomerDB/resources/customers/2/cliente/discountCode/". como na figura 3."credit Pela aparência da interface gráfica.- +40/FUD QBSBBTFTUSVUVSBT de dados que o seu programa precisa.tsoftt."discountCode CPUÍP <> 0 SFTVMUBEP TFSÈ BQSFTFOUBOEP OP CMPDP )551 3FTQPOTF ":"77"}. Tela inicial do RESTClient.

@XmlElement public String getNome() { Para iniciar o teste. private String nome. Fluxo JAXB. considere o exemplo da Listagem 16. por fim.-#JOEJOH GPSOFDFB"1* BTGFSSBNFOUBTF return cpf. dentro return nome.xml. será feito o build e o deploy da aplicação web. da seção Response. propOrder={“nome”. Estas anotações estão presentes no pacote javax. fornece compiladores que compilam Schemas public String getStatusCivil() { 9. RVFOPTQFSNJUFNDSJBSVNBSFQSFTFOUBÎÍPFN+BWBEFVN4DIFNB9.com.-QBSBSFQSFTFOUBÎÜFT+BWB } } Além disso. Classe PessoaBinding com anotações JAXB. os dados do } cabeçalho e o status da chamada. de acordo com os serviços criados. F QPTTVFN BOPUBÎÜFT BTTPDJBEBT B QBDPUFT +BWB !9NM4DIFNB  ! 9NM4DIFNB5ZQFFUD BTDMBTTFT+BWB !9NM5ZQFF!9NM3PPU&MFNFOU  BQSPQSJFEBEFFDBNQPT !9NM&MFNFOF!9NM"UUSJCVUF  Para exemplificar.br . esta é uma classe 10+0SFQSFTFOUBOEPVNBQFTTPB DPNBOPUBÎÜFT+"9#"PGB[FSVNNBS- TIBMMJOHEFVNBJOTUÉODJBEBDMBTTF1FTTPB#JOEJOHQBSB9. private String statusCivil. e private String cpf.annotations. @XmlRootElement(name=”pessoa”) @XmlType(name=””. alterar e validar a representação Java 70 www. podemos analisar os dados de retorno. criar novos parâmetros para a requisição (botão “Add Parameter”). após a execução.-7FKBTVBBSRVJUFUVSBOB figura 6. Schema Generator Application Code Portable Package Schema +"97BOOPUBUFE javax. visível no canto superior esquerdo da figura 5. "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 "SUJHPt"VNFOUBOEPBQFSGPSNBODFEP)JCFSOBUFDPN&IDBDIF contra regras de um Schema e.- } @XmlElement e objetos Java.”statusCivil”}) public class PessoaBinding { /* Construtores e Setters omitidos */ Figura 5.xml.-+BWB Annotation-driven Customization Schema Object Binding Binding Compiler Factory Framework Delarations Implementation Application Schema to Java Java to Schema Figura 6. VNGSBNFXPSLRVFBVUPNBUJ[BPNBQFBNFOUPFOUSFEPDVNFOUPT9. podemos acessar. } JAXB @XmlAttribute(name=”num_cpf”) public String getCpf() { +"9# +BWB"SDIJUFDUVSFGPS9. return idade.mundoj. basta clicar no botão “Test”. private int idade.bind. o NetBeans ainda gera o public int getIdade() { arquivo WADL.- QBSB PCKFUPT +BWB &N UFNQP EF FYFDVÎÍP  QPEFNPT EFTFSJBMJ[BS return statusCivil.- UFSFNPTP SFTVMUBEPBQSFTFOUBEPOB-JTUBHFN Listagem 16.- e ao final do processo será disponibilizada uma página de testes web. podemos serializar (marshal) o DPOUFÞEPEFVNPCKFUP+BWBFNDPOUFÞEP9. &TUÈGPSBEFTUFBSUJHPVNFTUVEPNBJTBQSPGVOEBEPTPCSFP+"9# NBT 'JHVSB0QÎÍPEFUFTUBSTFSWJÎPT3&45GVMDPNP/FU#FBOT BQFOBT QBSB DPOIFDJNFOUP  B "1* +"9# BDBCPV TF UPSOBOEP B GPSNB QBESÍPEFNBQFBNFOUPFOUSF+BWBF9. @XmlElement Além disso. como mostra a figura 5.-$PN+"9# UFNPTBOPUBÎÜFT Ao selecionar esta opção. Na página apresentada é possível testar todos os serviços disponíveis. Ou seja.bind classes 9.”idade”. também é possível selecionar o tipo de método HTTP para teste e o tipo MIME de retorno. VONBSTIBM PDPOUFÞEPEFVNBSRVJWP9. Tela de testes de Web Services RESTful.

JAKARTA COMMONS − HTTPCLIENT FOUSFFMFT QSPWFEPSFTQBSB+"9# QBSBRVBOEPPUJQPEFDPOUFÞEPUSB- GFHBEPGPSEPUJQPYNM BQQMJDBUJPOYNM UFYUYNMFBQQMJDBUJPO . Convertendo código XML para objeto JAXB em chamada PUT com REST.0” encoding=”UTF-8”?> <pessoa num_cpf=”123456789”> @PUT <nome>Wagner</nome> @Consumes(“application/xml”) <idade>29</idade> @Path(“/Mundoj/ “) <statusCivil>Casado</statusCivil> public void putPessoa(PessoaBinding pessoa) { </pessoa> // Operação de update } $PNPWJNPTBOUFSJPSNFOUFOPUØQJDPi+"934o+BWB"1*GPS3&45GVM8FC Services”. <?xml version=”1. Listagem 19. "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 Listagem 17. a especificação já fornece alguns Entity Providers padrões. XML gerado após marshalling de classe JAXB PessoaBinding.

println(“Chamada GET”). 25 System. } 1 public void testHTTPClient() { 2 try { Ao fazermos o consumo deste serviço RESTful. PUT. Possui suporte ao protocolo HTTPS. suporte a cookie.out.println(“ Status Code: “+statusCodePUT+ ” \nResponse Body:\n”+responseBody). 21 StringRequestEntity requestEntity = new StringRequestEntity( responseBody.setConnectionTimeout(30000).println(“ Status Code: “+statusCodeGET+ ” \nResponse Body:\n”+responseBody).getResponseBodyAsString(). 7 DMBTTF1FTTPB#JOEJOHWJB)551#PEZ$POGPSNFBQSFTFOUBB-JTUBHFN 8 /* Executando chamada com método HTTP GET */ 9 String getURI = “http://localhost:8080/TestesWS/Mundoj/autores/ Wagner/?idade=29”. Digest e criptografia NTLM. 14 String responseBody = get. 26 System. return dao. Neste caso a declaração do serviço seria similar ao méto- do da Listagem 18. no UPSOPVJOEFQFOEFOUFFN FRVFGPJDPODFCJEPQBSBGBDJMJUBSPEF- OPTTPFYFNQMP DSJBSVNTFSWJÎP3&45GVMDVKPSFUPSOPTFKBBDMBTTF+"9# senvolvimento de aplicações que utilizam o protocolo HTTP. CHARSET).getParams(). poderíamos então. HEAD. 11 Header meuHeader = new Header(“CPF”. // Retorna uma entidade Pessoa // como PessoaBinding Listagem 20. 17 18 /* Executando chamada com método HTTP PUT */ 19 String putURI = “http://localhost:8080/TestesWS/Mundoj/autores/ update/”. suporte ao gerenciamento de conexões para uso em aplicações multithread. 27 } catch (Exception ex) {/* OMITIDO */} 28 } 'JHVSB3FUPSOPEPTFSWJÎP3&45GVMDVKPSFUPSOPÏVNBDMBTTF+"9# 71 .println(“Chamada PUT”). 9. 5 final String CONTENT_TYPE = “application/xml”.setRequestEntity(requestEntity). vamos perceber que a 3 HttpClient client = new HttpClient(new /multiThreadedHttpConnectionManager()).out. conversão é feita automaticamente pelo entity provider padrão para 4 client. Consumindo serviços REST via GET e PUT com HTTPClient.setRequestHeader(meuHeader). 12 get.YNM  HttpClient é um subprojeto open source da Jakarta Commons que se Ainda na classe PessoaBinding da Listagem 16. 13 int statusCodeGET = client. e implementa todos os métodos HTTP (GET. 10 GetMethod get = new GetMethod(getURI). DELETE. 20 PutMethod put = new PutMethod(putURI). OPTIONS e TRACE). demonstramos o uso da biblioteca HttpClient. um com uma chamada GET e outra com uma chamada PUT.getPessoaAsBinding(id).getHttpConnectionManager().”123456789”). POST. 24 responseBody = put. 22 put. Listagem 18.-%FNBOFJSBJOWFSTBQPEFSÓBNPTDSJBSVNTFSWJÎP3&45GVMQBSBSFDF. 23 int statusCodePUT = client.executeMethod(put).out. CONTENT_TYPE. PessoaBinding.getResponseBodyAsString(). Serviço RESTful cujo retorno é uma classe JAXB. 15 System.executeMethod(get). ber requisições PUT e receber como parâmetro de entrada do método a 6 final String CHARSET = “UTF8”. no qual public PessoaBinding getPessoa(@PathParam(“idPessoa”) Integer id) { consumimos dois serviços RESTful.out. Ele é um projeto escrito totalmente em Java. @Produces(“application/xml”) @Path(“/Mundoj/{idPessoa}/”) Na Listagem 20. possui @GET mecanismos de autenticação Basic. 16 System.

Na linha 13. imprimindo Response Body: o valor da tag nome do código xml enviado.- Chamada PUT Status Code: 202 Listagem 21. /B-JTUBHFN WJNPTVNFYFNQMPEFVNTFSWJÎPRVFSFUPSOB9. Response Body: <html> function showCustomer(str){ <body><h1>Bem vindo Wagner</h1></body> xmlHttp=GetXmlHttpObject(). mas vale lem- </pessoa> brar que JavaScript não é Java. Na linha 10. "SUJHPt"VNFOUBOEPBQFSGPSNBODFEP)JCFSOBUFDPN&IDBDIF "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 Retorno da chamada ao método classe StringRequestEntity na linha 21. temos um exemplo de uma função em JavaScript que DPOTPNFVNTFSWJÎP3&45GVMDVKPSFUPSOPÏVN9. o tipo de conteúdo (CONTENT_TYPE) e o charset. Ext-JS.nodeValue. e possui uma grande gama de frameworks Ajax. o character set e a URI de acesso ao serviço REST. customers/58/&apos.us. Primeiro. Consumindo um serviço RESTful (retorno XML) com Ajax. E também onde } será armazenado uma ou mais conexões HTTP. agente HTTP que irá conter os atributos de persistência com cookies. Na Listagem 21.. desde então temos todas as vantagens <statusCivil>Casado</statusCivil> EP "+"9 BP OPTTP EJTQPS 1BSB RVFN EFTFOWPMWF JOUFSGBDFT 8&#  FTUF recurso resolveu grandes problemas no lado do cliente. passando como parâmetro no construtor a chave e o valor que represen- tam o parâmetro e o valor do cabeçalho. entre outros. Depois xmlHttp.  YNMWFSTJPOFODPEJOH65'TUBOEBMPOFZFT  QFTTPBOVN@DQG JavaScript <nome>Wagner</nome> (SBÎBT BP PCKFUP 9. passamos function stateChanged() { um número fictício de CPF.http://localhost:8080/ ContatosMJ/resources/ das aos métodos HTTP. instanciamos a classe HttpClient que é o nosso return. na linha 3.mundoj. Na linha 12 atribuímos o objeto header para if (xmlHttp.com. por exemplo.documentElement. é que podemos trabalhar tuar uma chamada via método PUT. Prototype. uma das grandes vantagens dos serviços REST. e credenciais de autenticação através da classe HttpState. Na linha 11 criamos um objeto Header. que implementa o método HTTP PUT e o uso da Entre eles. Dojo.. mas agora para efe. document. OBTMJOIBT FEFDMBSBNPTBTWBSJÈWFJTRVFSJSÍPEFUFSNJOBSPUJQPEF conteúdo. representa o método GET. // omitido código do método </html> if (xmlHttp==null) { alert(“Your browser does not support AJAX!”). não possui threads.aculo.- QPEFSÓBNPTGBDJMNFOUF } VUJMJ[BS+"9#QBSBUSBCBMIBSPSFUPSOPDPNPVNPCKFUP+BWB'JOBMNFOUF } nas linhas 15 e 16 imprimimos no console o retorno da chamada a estes métodos.onreadystatechange=stateChanged.-)UUQ3FRVFTU  DPOTFHVJNPT OPT DPNVOJDBS DPN JEBEFJEBEF servidores de forma assíncrona.open(&apos. e ar.- NBT A partir da linha 18. var xmlDoc=xmlHttp.true). xmlHttp. método PutMethod. 72 www. Na linha 4 atribuímos um timeout para a conexão de 30 segundos.getElementById(“nome”). Com esta classe.responseXML. JSON.getElementsByTagName(“name”)[0]. no nosso exemplo. como o próprio nome indica. JQuery. fazemos a chamada ao serviço RESTful via HTTP GET. passando como parâmetro a URL do } nosso serviço RESTful (getURI). SFTQPOTF#PEZ1FMPGBUPEPSFUPSOPTFSFN9. Na linha 14. em que faremos chama. como.innerHTML= mazenamos o código de status do retorno na variável statusCodeGET. xmlHttp. extraímos os dados da Response como String para a variável xmlDoc.readyState==4){ o objeto GetMethod. atribuímos uma entidade (como String) ao método PUT que será enviado Chamada GET junto a requisição. que passamos como parâmetro de construtor o xml de retorno da chamada que fizemos ao serviço REST GET. as únicas diferenças são o uso do com diversos formatos para troca de informação de um mesmo recurso.childNodes[0].url.br . iniciamos o mesmo processo.GET&apos.send(null). instanciamos a classe GetMethod que. nem tipos. var url=&apos. Status Code: 200 Nas linhas 25 e 26 imprimimos o retorno da requisição PUT. Script.

title == foto){ t IUUQTKBYCEFWKBWBOFUo4JUFEPQSPKFUP+"9# $(“<img/>”). conseguimos um alto nível de controle nas requisições ajax.ajax({ type: “DELETE”. success: function(msg){ $(“#alert”). t IUUQTKFSTFZEFWKBWBOFUo4JUFEPQSPKFUP+FSTFZ getPhotos& photoset_id=72157614488723406&format=json&jsoncallback=?”. que reduzem muito a complexidade e a quantidade de linhas de código.com/”+item.photo. Com seu uso. Uso da função $. Consumindo um serviço REST com a função $. t IUUQKRVFSZDPNo4JUFPmDJBMEPK2VFSZ }). eventos e as interações Ajax para prover um desenvolvimento rápido de aplicações web. Na Listagem 23 mostramos um exemplo de uso da função $. Com a função $. t IUUQUPPMTJFUGPSHIUNMSGDo4JOUBYF(FOÏSJDBEFmOJEBQBSBVNB63* t IUUQXXXJDTVDJFEV_mFMEJOHQVCTEJTTFSUBUJPOSFTU@BSDI@TUZMFIUN o $BQÓ- function(data){ tulo 5 da dissertação de Roy Fielding sobre REST $. QPSÏNÏWÈMJEPMFNCSBSRVFFYJTUFNEJWFSTBTJNQMFNFOUBÎÜFTEB+"9 RS que possuem funcionalidades adicionais não contempladas neste A sintaxe do comando é $.ajax() 'BMBNPTTPCSFBFTQFDJmDBÎÍP+"934DPNEJWFSTPTFYFNQMPTQSÈUJDPT  do jQuery. de modo que tanto os que já possuem conhecimento em REST manipulação dos elementos de um documento HTML. Ela simplifica muito a jetiva. "SUJHPt3&45GVM8FC4FSWJDFTFB"1*+"934 jQuery Considerações finais jQuery é uma biblioteca JavaScript que vem chamando atenção por Neste artigo. sabendo o momento de usá-la se torna uma ferramenta poderosa de integração.photosets. o tratamento de quanto os que estão iniciando tenham proveito. function(i.html(msg). Nessa listagem. usamos dois parâmetros na função $.item){ t IUUQTXBEMEFWKBWBOFUo4JUFEPQSPKFUP8"%-OP(MBTTmTI if (item. ideais para o consumo de serviços REST.static. Na Listagem 22. 73 . Para tratar tipos de retorno JSON. t -JWSP)551o5IF%FmOJUWF(VJEFQPS%BZJE(PVSMFZF#SJBO5PUUZ t IUUQKDQPSHFOKTSEFUBJM JEo+$1QBSBB"1*+"934 $.getJSON(). em termos de facilidade no desenvolvimento e requerer uma A biblioteca jQuery fornece algumas funções para tratamento de requisi. únicas disponíveis no mercado. Dentro da função de callback.attr(“src”.each(data.ajax(). criamos a tag <img> passando como valor PFOEFSFÎPEBGPUPSFUPSOBEBQFMPTFSWJÎP3&45FBJODMVÓNPTOBEJWGPUP Note que a variável data é um map chave-valor dos dados retornados pela função REST.getJSON para consumo de dados no formato JSON.photoset. “http://farm”+item. o parâme- tro type para indicar o método HTTP que queremos executar e a url de chamada.farm+”. t IUUQDPEFHPPHMFDPNQSFTUDMJFOUo4JUFEPQSPKFUP3&45$MJFOU appendTo(“#foto”).getJSON() em um serviço REST do Flickr. o desenvolvedor se livra de preocupações "TTJNDPNPUPEBOPWBUFDOPMPHJB +"934OÍPÏVNBCBMBEFQSBUB NBT relacionadas à compatibilidade de navegadores e aderência à CSS.flickr.ajax(options). Descrevemos diversas maneiras sobre como consumir e testar serviços RESTful. t IUUQUPPMTJFUGPSHIUNMSGDo&TQFDJmDBÎÍP)551 t IUUQXXXXFCEBWPSHTQFDTSGDIUNMIUUQNFUIPETGPS o &YUFOTÜFT )551 } – WebDAV }). procuramos abordar REST de uma maneira simples e ob- conta de sua facilidade de desenvolvimento. url: “http://localhost:8080/Mundoj/autores/”+idAutor+”/”.id+”_”+item.ajax(). as propriedades que passamos para controlar como a requisição é feita e o retorno da chamada. Referências t -JWSP3&45GVM8FC4FSWJDFTQPS-FPOBSE3JDIBSETPOF4BN3VCZ "VUIPS  Listagem 23. t IUUQDVSMIBYYTFo'FSSBNFOUBD63- flickr. obviamente as soluções apresentadas neste artigo não são as Na Listagem 22.secret+”_m. JOGSBFTUSVUVSBNBJTMFWFEJTQFOTBOEPPVTPEFVNNJEEMFXBSF84  ções Ajax. fazemos uma chamada ao serviço REST e passamos o retorno da chamada ao método de callback. utilizada para carregar dados JSON mediante uma requisi- ção HTTP GET. demonstramos o uso das funções $.getJSON(“http://api. } }). em que o parâmetro options são artigo. $. ficando este artigo como um guia de PQÎÜFTt Listagem 22. o jQuery oferece a função $.com/services/rest/?method=flickr.server+”/”+item.ajax().jpg”).