À procura de uma maneira produtiva de trabalhar com web services SOAP
December 8th, 2008Com a minha mudança de alocação da Globo.com para a Globosat, continuo trabalhando bastante com integração de aplicações, mas agora com um ferramental e paradigmas diferentes.
Na Globo.com eu trabalhei muito com open source, e estava acostumado a montar as aplicações a partir de componentes “crus”, em vez de usar ferramentas sofisticadas. Open source faz parte da cultura da empresa, e tínhamos uma boa liberdade de escolha de tecnologias e arquiteturas.
Como falei algumas vezes no passado, nós migramos boa parte da arquitetura legada com EJBs para serviços REST usando por baixo o Jersey, Spring e Ibatis. A produtividade no desenvolvimento de serviços REST me agrada muito, e mesmo alguém que não conheça muito de serviços REST consegue desenvolver um serviço sem tanto esforço.
Agora vou trabalhar mais com serviços SOAP, mas usando ferramentas muito produtivas, como o Aqualogic ESB e o Workshop, entre outros. Essas ferramentas facilitam muito o trabalho oferecendo Abstrações Opacas. Como ainda estou muito ligado ao trabalho com Open Source, eu venho tentando no meu tempo vago encontrar ferramentas open source com a mesma proposta.
Neste momento estou tentando encontrar a maneira mais produtiva de se trabalhar com web services SOAP usando open source. No passado eu desenvolvi serviços com o XFire, com o Axis 2 e com o JAX-WS, mas achei interessante reavaliar as opções existentes atualmente.
Nos últimos dias eu fiz testes com o Axis 2, com o Apache CXF e com o JAX-WS.
Eu não gosto muito do Axis 2. Você até consegue desenvolver serviços rapidamente com ele, mas ele gera um código tão sujo que é muito triste colocar qualquer coisa em produção com ele, sabendo que você vai ter que manter depois aquele código. Além disso, para utilizá-lo você precisa levar nada menos que 51 jars para sua aplicação, o que transforma qualquer aplicação em um mastodonte. Um outro problema dessa lista massiva de dependências é que a chance de uma aplicação pré-existente ter conflitos de dependências com o Axis é grande.
Na prática, eu só utilizaria o Axis 2 (e mesmo assim com má vontade) para desenvolver serviços se fosse numa estrutura como o WSO2 Web Services Application Server, que é um servidor de aplicações “dedicado” a serviços Axis.
O Apache CXF oferece um “front-end” com JAX-WS (que é o mais recomendado) e um “front-end” alternativo, que usa o Aegis Databinding. Por enquanto olhei apenas o front-end com JAX-WS, mas não vi nenhuma vantagem em utilizar o CXF em vez da implementação de referência presente no Glassfish. Se pintar disposição eu darei uma olhada no front-end com Aegis Databinding, mas por enquanto não tenho grandes expectativas em relação a ele não.
Para finalizar, fiz muitos experimentos com a implementação de referência do JAX-WS, embutido no Glassfish V2. A forma de trabalho que achei mais produtiva nestes meus testes foi desenvolvendo com JAX-WS no Netbeans (utilizei a versão 6.5).
Tentei desenvolver a partir de classes Java, e a partir do WSDL, e esta última me trouxe melhores resultados.A melhor forma que achei foi começar desenhando os schemas XML com o editor do Netbeans:
Criei um Complex Type para cada classe de domínio, e 1 Complex Type para o Request de cada operação e 1 Complex Type para o Response de cada operação. Tendo feito isso, criei depois 1 Element para o Request de cada operação e 1 Element para o Response de cada operação. Com o schema XML criado dessa forma, criei em seguida o WSDL, com o editor do Netbeans também:
Na criação do WSDL, coloquei nas mensagens de Request/Response das operações os Elementos declarados no schema XML anterior. É importante prestar atenção nisso. Usando Elementos nas mensagens, você está criando serviços no modelo Document/Literal. Se você colocar nas mensagens um Complex Type diretamente, em vez de colocar um Elemento, você estará criando um serviço no modelo RPC/Literal. Eu particularmente prefiro Document/Literal, e o código gerado pelo JAX-WS neste modelo me agrada mais.
A implementação do serviço com JAX-WS ficou parecida com isso aqui:
package org.brunopereira.cadastro; import javax.jws.WebService; import org.brunopereira.schema.cadastroclientes.CadastroClienteRequestType; import org.brunopereira.schema.cadastroclientes.CadastroClienteResponseType; import org.brunopereira.schema.cadastroclientes.Cliente; import org.brunopereira.wsdl.cadastrocliente.CadastroClientePortType; @WebService(serviceName = "CadastroClienteService", portName = "CadastroClientePort", endpointInterface = "org.brunopereira.wsdl.cadastrocliente.CadastroClientePortType", targetNamespace = "http://brunopereira.org/wsdl/CadastroCliente", wsdlLocation = "WEB-INF/wsdl/CadastroCliente/CadastroCliente.wsdl") public class CadastroCliente implements CadastroClientePortType { public CadastroClienteResponseType cadastrarCliente(CadastroClienteRequestType request) { System.out.println("Cadastro de cliente foi invocado!! Será feito o roteamento para o serviço adequado!!"); Cliente cliente = request.getCliente(); CadastroClienteResponseType response = new CadastroClienteResponseType(); response.setCliente(cliente); return response; } }
O código do cliente foi gerado bem facilmente a partir do WSDL também, e ficou bem limpo. O que achei bem fraco foi a parte de teste dos serviços tanto no Netbeans como no Eclipse. No Eclipse você só consegue usar os plugins de teste se você tiver desenvolvido os serviços dentro do Eclipse, o que inviabilizou o meu uso. E o Netbeans tem um suporte que só serve pra HelloWorld, pra aqueles serviços de Calculadora, que você passa uns parâmetros primitivos e recebe um resultado simples. A interface do testador do meu serviço ficou dessa forma:

Dá pra ver que não serve para nada além de um HelloWorld basicão.
Bom, de uma maneira geral, o suporte a Web Services no Netbeans é muito melhor do que no Eclipse, que pra piorar só suporta a criação de serviços com o Axis. Até agora a maneira mais produtiva que encontrei de trabalhar com serviços SOAP foi essa que descrevi. Nos próximos dias olharei o que tem de interessante no projeto Metro e no JBoss ESB. Se encontrar coisas interessantes falarei mais por aqui. Ah, e se alguém tiver dicas para melhorar esta forma de trabalho que descrevi, por favor me avisem, pois estou avaliando muita coisa e não dá tempo de dedicar tanto tempo a cada opção dessas.

