[Resolvido] vRaptor GAE: Problemas ao Deserializar Json

Olá todos,

          Estou criando um projeto vraptor usando o Google App Engine. Pelo que eu sei, o Xstream que está no vraptor-blank-project-gae-3.4.1 foi adaptado para não te problemas com as restrições do Google App Engine.
          
          Ao enviar um para o meu controller, o mesmo dá o seguinte erro:
java.lang.NoClassDefFoundError: sun.reflect.ReflectionFactory is a restricted class. Please see the Google  App Engine developer's guide for more details.
	at com.google.appengine.tools.development.agent.runtime.Runtime.reject(Runtime.java:51)
	at com.thoughtworks.xstream.converters.reflection.Sun14ReflectionProvider.getLazyRefectionFactory(Sun14ReflectionProvider.java:105)
	at com.thoughtworks.xstream.converters.reflection.Sun14ReflectionProvider.getMungedConstructor(Sun14ReflectionProvider.java:97)
	at com.thoughtworks.xstream.converters.reflection.Sun14ReflectionProvider.newInstance(Sun14ReflectionProvider.java:76)
	at com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.instantiateNewInstance(AbstractReflectionConverter.java:313)
	at com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.unmarshal(AbstractReflectionConverter.java:162)
	at com.thoughtworks.xstream.core.TreeUnmarshaller.convert(TreeUnmarshaller.java:82)
	at com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother(TreeUnmarshaller.java:76)
	at com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother(TreeUnmarshaller.java:60)
	at com.thoughtworks.xstream.core.TreeUnmarshaller.start(TreeUnmarshaller.java:137)
	at com.thoughtworks.xstream.core.AbstractTreeMarshallingStrategy.unmarshal(AbstractTreeMarshallingStrategy.java:33)
	at com.thoughtworks.xstream.XStream.unmarshal(XStream.java:965)
	at com.thoughtworks.xstream.XStream.unmarshal(XStream.java:950)
	at com.thoughtworks.xstream.XStream.fromXML(XStream.java:893)
	at br.com.caelum.vraptor.deserialization.JsonDeserializer.deserialize(JsonDeserializer.java:62)
	at br.com.caelum.vraptor.interceptor.DeserializingInterceptor.intercept(DeserializingInterceptor.java:87)
	at br.com.caelum.vraptor.core.LazyInterceptorHandler.execute(LazyInterceptorHandler.java:59)
	at br.com.caelum.vraptor.core.DefaultInterceptorStack.next(DefaultInterceptorStack.java:54)
	at br.com.caelum.vraptor.interceptor.ParametersInstantiatorInterceptor.intercept(ParametersInstantiatorInterceptor.java:93)
	at br.com.caelum.vraptor.core.LazyInterceptorHandler.execute(LazyInterceptorHandler.java:59)
	at br.com.caelum.vraptor.core.DefaultInterceptorStack.next(DefaultInterceptorStack.java:54)
	at br.com.caelum.vraptor.core.ToInstantiateInterceptorHandler.execute(ToInstantiateInterceptorHandler.java:56)
	at br.com.caelum.vraptor.core.DefaultInterceptorStack.next(DefaultInterceptorStack.java:54)
	at br.com.caelum.vraptor.interceptor.FlashInterceptor.intercept(FlashInterceptor.java:83)
	at br.com.caelum.vraptor.core.ToInstantiateInterceptorHandler.execute(ToInstantiateInterceptorHandler.java:54)
	at br.com.caelum.vraptor.core.DefaultInterceptorStack.next(DefaultInterceptorStack.java:54)
	at br.com.caelum.vraptor.interceptor.ExceptionHandlerInterceptor.intercept(ExceptionHandlerInterceptor.java:71)
	at br.com.caelum.vraptor.core.ToInstantiateInterceptorHandler.execute(ToInstantiateInterceptorHandler.java:54)
	at br.com.caelum.vraptor.core.DefaultInterceptorStack.next(DefaultInterceptorStack.java:54)
	at br.com.caelum.vraptor.interceptor.InstantiateInterceptor.intercept(InstantiateInterceptor.java:48)
	at br.com.caelum.vraptor.core.ToInstantiateInterceptorHandler.execute(ToInstantiateInterceptorHandler.java:54)
	at br.com.caelum.vraptor.core.DefaultInterceptorStack.next(DefaultInterceptorStack.java:54)
	at br.com.caelum.vraptor.interceptor.ResourceLookupInterceptor.intercept(ResourceLookupInterceptor.java:69)
	at br.com.caelum.vraptor.core.ToInstantiateInterceptorHandler.execute(ToInstantiateInterceptorHandler.java:54)
	at br.com.caelum.vraptor.core.DefaultInterceptorStack.next(DefaultInterceptorStack.java:54)
	at br.com.caelum.vraptor.core.ToInstantiateInterceptorHandler.execute(ToInstantiateInterceptorHandler.java:56)
	at br.com.caelum.vraptor.core.DefaultInterceptorStack.next(DefaultInterceptorStack.java:54)
	at br.com.caelum.vraptor.core.EnhancedRequestExecution.execute(EnhancedRequestExecution.java:44)
	at br.com.caelum.vraptor.VRaptor$1.insideRequest(VRaptor.java:91)
	at br.com.caelum.vraptor.ioc.spring.SpringProvider.provideForRequest(SpringProvider.java:58)
	at br.com.caelum.vraptor.VRaptor.doFilter(VRaptor.java:88)
	at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1157)
	at com.google.appengine.tools.development.HeaderVerificationFilter.doFilter(HeaderVerificationFilter.java:35)
	at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1157)
	at com.google.appengine.api.blobstore.dev.ServeBlobFilter.doFilter(ServeBlobFilter.java:60)
	at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1157)
	at com.google.apphosting.utils.servlet.TransactionCleanupFilter.doFilter(TransactionCleanupFilter.java:43)
	at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1157)
	at com.google.appengine.tools.development.StaticFileFilter.doFilter(StaticFileFilter.java:122)
	at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1157)
	at com.google.appengine.tools.development.BackendServersFilter.doFilter(BackendServersFilter.java:97)
	at org.mortbay.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1157)
	at org.mortbay.jetty.servlet.ServletHandler.handle(ServletHandler.java:388)
	at org.mortbay.jetty.security.SecurityHandler.handle(SecurityHandler.java:216)
	at org.mortbay.jetty.servlet.SessionHandler.handle(SessionHandler.java:182)
	at org.mortbay.jetty.handler.ContextHandler.handle(ContextHandler.java:765)
	at org.mortbay.jetty.webapp.WebAppContext.handle(WebAppContext.java:418)
	at com.google.appengine.tools.development.DevAppEngineWebAppContext.handle(DevAppEngineWebAppContext.java:78)
	at org.mortbay.jetty.handler.HandlerWrapper.handle(HandlerWrapper.java:152)
	at com.google.appengine.tools.development.JettyContainerService$ApiProxyHandler.handle(JettyContainerService.java:369)
	at org.mortbay.jetty.handler.HandlerWrapper.handle(HandlerWrapper.java:152)
	at org.mortbay.jetty.Server.handle(Server.java:326)
	at org.mortbay.jetty.HttpConnection.handleRequest(HttpConnection.java:542)
	at org.mortbay.jetty.HttpConnection$RequestHandler.content(HttpConnection.java:938)
	at org.mortbay.jetty.HttpParser.parseNext(HttpParser.java:755)
	at org.mortbay.jetty.HttpParser.parseAvailable(HttpParser.java:218)
	at org.mortbay.jetty.HttpConnection.handle(HttpConnection.java:404)
	at org.mortbay.io.nio.SelectChannelEndPoint.run(SelectChannelEndPoint.java:409)
	at org.mortbay.thread.QueuedThreadPool$PoolThread.run(QueuedThreadPool.java:582)

Este é o Json: {‘geolocation’: {‘latitude’: 123,‘longitude’: 542 }}

O meu controler está assim:

@Consumes
package br.com.drover.controller;

import br.com.caelum.vraptor.Consumes;
import br.com.caelum.vraptor.Resource;
import br.com.caelum.vraptor.Result;
import br.com.drover.entity.GeoLocation;

@Resource
public class PainelController {
	
	public PainelController(Result result) {

	}
	
	@Consumes
	public void add(GeoLocation geolocation) {
	...	
	}
	
}

Já procurei diversas vezes por uma solução e não achei. Alguém pode me dar uma luz?

dá uma olhada se vc tá mesmo com a versão do xstream modificada pro gae (isso está no nome do jar)

xstream-xstream-1.3.2-SNAPSHOT-GAE.jar

É essa a lib?

sim… dá uma olhada se o outro jar do xstream tá lá tb… se estiver, tire.

Pra fazer o teste, exclui o projeto e criei novamente. Deu o mesmo erro.

Apenas uma observação: quando eu executo o projeto ele reclama da falta de a lib jetisson.
Baixei a lib jettison-1.3.1 e coloquei junto ao projeto.

Vi diversos posts em que mesmo com a lib xstream-xstream-1.3.2-SNAPSHOT-GAE.jar o esse persiste.

vc pode tentar usar outra lib para deserializar json, como o jackson ou o GSon… Precisa ver se eles são compatíveis com o GAE

pra isso é necessario implementar um deserializer do VRaptor. Se quiser eu te ajudo.

[]'s

Lucas,

    Muito obrigado pela disposição, mas consegui resolver o meu problema. Nos fóruns do GAE vi que algumas pessoas conseguiram resolver esse problema usando a lib que está nesse link: http://jira.codehaus.org/browse/XSTR-566
    No primeiro momento achei que não ia funcionar por que talvez fosse a mesma coisa da xstream-xstream-1.3.2-SNAPSHOT-GAE.jar. 
    Só que eu percebi que a lib que tem nesse bugtracking do Xstream, tem o dobro do tamanho da que existe junto ao blank-projec-gaet do vRaptor. Após perceber isso, fiz a troca imediatamente. E funcionou.  :D 
    Agora eu tenho a curiosidade de saber o porquê de ter funcionado. Será que essa lib é mais recente da existente da xstream-xstream-1.3.2-SNAPSHOT-GAE.jar que tem no vRaptor?

como é um SNAPSHOT, muito provavelmente…

vc pode tentar usar o xstream 1.4.1 tb, ver se funciona

Bem, acabei de testar na versão 1.4.2. Não funcionou.

Lucas, é comum esse erro acontecer , as pessoas não conseguirem resolver e implementar um outro deserializer usando outra lib ao invés do Xstream? Ou isso só aconteceu comigo? :slight_smile:

o xstream não resolve todos os casos… Ele é meio ruim pra deserializar json, infelizmente…

tiveram alguns tópicos sobre isso e algumas pessoas fizeram essas integrações com o gson e jackson ou configurando melhor o xstream
http://groups.google.com/group/caelum-vraptor/browse_thread/thread/884ebb393878ae9a?pli=1

nesse caso é uma limitação do GAE, então precisa implementar usando outra coisa mesmo…

a interface não é tão difícil de implementar, principalmente se vc supor que o método vai ter um parâmetro só (ou o primeiro será o deserializado).

vc pode usar qqer biblioteca json

Na sua opnião, qual é a melhor forma de deserializar json no vRaptor?

o GSon parece bem legal… já usei o jackson, mas vc precisa colocar várias anotações ou fazer o mapper na mão. O net.sf.json tb é nesse estilo…