Genson library in jersey webservices to deserialize data

1.8k Views Asked by At

I have used genson has a way to send complex data objects to jersey rest webservices in java applications.

Although when i try to send floats, i get the following error:

Mai 29, 2014 9:56:47 PM com.sun.jersey.spi.container.ContainerResponse logException
SEVERE: Mapped exception to response: 500 (Internal Server Error)
javax.ws.rs.WebApplicationException: com.owlike.genson.JsonBindingException: Could not deserialize to type class entities.Accelerometer
    at com.owlike.genson.ext.jaxrs.GensonJsonConverter.readFrom(GensonJsonConverter.java:127)
    at com.sun.jersey.spi.container.ContainerRequest.getEntity(ContainerRequest.java:490)
    at com.sun.jersey.server.impl.model.method.dispatch.EntityParamDispatchProvider$EntityInjectable.getValue(EntityParamDispatchProvider.java:123)
    at com.sun.jersey.server.impl.inject.InjectableValuesProvider.getInjectableValues(InjectableValuesProvider.java:86)
    at com.sun.jersey.server.impl.model.method.dispatch.AbstractResourceMethodDispatchProvider$EntityParamInInvoker.getParams(AbstractResourceMethodDispatchProvider.java:153)
    at com.sun.jersey.server.impl.model.method.dispatch.AbstractResourceMethodDispatchProvider$ResponseOutInvoker._dispatch(AbstractResourceMethodDispatchProvider.java:203)
    at com.sun.jersey.server.impl.model.method.dispatch.ResourceJavaMethodDispatcher.dispatch(ResourceJavaMethodDispatcher.java:75)
    at com.sun.jersey.server.impl.uri.rules.HttpMethodRule.accept(HttpMethodRule.java:302)
    at com.sun.jersey.server.impl.uri.rules.RightHandPathRule.accept(RightHandPathRule.java:147)
    at com.sun.jersey.server.impl.uri.rules.ResourceClassRule.accept(ResourceClassRule.java:108)
    at com.sun.jersey.server.impl.uri.rules.RightHandPathRule.accept(RightHandPathRule.java:147)
    at com.sun.jersey.server.impl.uri.rules.RootResourceClassesRule.accept(RootResourceClassesRule.java:84)
    at com.sun.jersey.server.impl.application.WebApplicationImpl._handleRequest(WebApplicationImpl.java:1542)
    at com.sun.jersey.server.impl.application.WebApplicationImpl._handleRequest(WebApplicationImpl.java:1473)
    at com.sun.jersey.server.impl.application.WebApplicationImpl.handleRequest(WebApplicationImpl.java:1419)
    at com.sun.jersey.server.impl.application.WebApplicationImpl.handleRequest(WebApplicationImpl.java:1409)
    at com.sun.jersey.spi.container.servlet.WebComponent.service(WebComponent.java:409)
    at com.sun.jersey.spi.container.servlet.ServletContainer.service(ServletContainer.java:540)
    at com.sun.jersey.spi.container.servlet.ServletContainer.service(ServletContainer.java:715)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:728)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:305)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
    at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:51)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:243)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:222)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:123)
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:502)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:100)
    at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:953)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:408)
    at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1041)
    at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:603)
    at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:310)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
    at java.lang.Thread.run(Thread.java:745)
Caused by: com.owlike.genson.JsonBindingException: Could not deserialize to type class entities.Accelerometer
    at com.owlike.genson.Genson.deserialize(Genson.java:442)
    at com.owlike.genson.ext.jaxrs.GensonJsonConverter.readFrom(GensonJsonConverter.java:125)
    ... 38 more
Caused by: com.owlike.genson.JsonBindingException: Could not deserialize to property 'y' of class class entities.Accelerometer
    at com.owlike.genson.reflect.PropertyMutator.couldNotDeserialize(PropertyMutator.java:49)
    at com.owlike.genson.reflect.PropertyMutator.deserialize(PropertyMutator.java:32)
    at com.owlike.genson.reflect.BeanDescriptor.deserialize(BeanDescriptor.java:110)
    at com.owlike.genson.reflect.BeanDescriptor.deserialize(BeanDescriptor.java:93)
    at com.owlike.genson.convert.BeanViewConverter.deserialize(BeanViewConverter.java:105)
    at com.owlike.genson.convert.NullConverter$NullConverterWrapper.deserialize(NullConverter.java:57)
    at com.owlike.genson.Genson.deserialize(Genson.java:440)
    ... 39 more
Caused by: com.owlike.genson.JsonBindingException: No constructor has been found for type float
    at com.owlike.genson.reflect.BeanDescriptor.deserialize(BeanDescriptor.java:96)
    at com.owlike.genson.convert.BeanViewConverter.deserialize(BeanViewConverter.java:105)
    at com.owlike.genson.convert.NullConverter$NullConverterWrapper.deserialize(NullConverter.java:57)
    at com.owlike.genson.reflect.PropertyMutator.deserialize(PropertyMutator.java:30)

Accelerometer is the class i am trying to pass and has a parameter namely y that is of type float. what can be this error?

here is the accelerometer class:

@Entity
public class Accelerometer implements Serializable {


    private static final long serialVersionUID = -4328956850876279601L;

    @Id
    @GeneratedValue(strategy = GenerationType.TABLE)
    private long id;
    private float x;
    private float y;
    private float z;
    private long time;
    @Column(name = "yProcessed", nullable = false, columnDefinition = "int default '0'")
    private int yProcessed = 0;
    @Column(name = "zClass", nullable = false, columnDefinition = "double default 0.0")
    private double zClass = 0d;

    public Accelerometer(){

    }

    public long getId() {
        return id;
    }

    public void setId(long id) {
        this.id = id;
    }

    public float getX() {
        return x;
    }

    public void setX(
            float x) {
        this.x = x;
    }

    public float getY() {
        return y;
    }

    public void setY(
            float y) {
        this.y = y;
    }

    public float getZ() {
        return z;
    }

    public void setZ(
            float z) {
        this.z = z;
    }

    public long getTime() {
        return time;
    }

    public void setTime(
            long time) {
        this.time = time;
    }
}

the json i am passing is the following:

{"time":1401398020864,"zClass":0.0,"y":-0.7086837,"yProcessed":0,"z":9.002198,"x":0.45968673}

this should work i am getting the problem in the y field of this. I dont get it i send locations as well that have a - field wheter latitude or longitude but they are double. Cant floats have -?

1

There are 1 best solutions below

3
On BEST ANSWER

In Genson 0.99 there are missing Converters for float and short.

They have been added for 1.0 release (but its still in devlopment). To solve the problem temporarily you can use double instead of float (the easy solution) or provide converters :

@HandleClassMetadata
@WithoutBeanView
public final static class FloatConverter implements Converter<Float> {

    public Float deserialize(ObjectReader reader, Context ctx) {
        return reader.valueAsFloat();
    }

    public void serialize(Float obj, ObjectWriter writer, Context ctx) {
        writer.writeValue(obj.floatValue());
    }
}

Then you will need to register it and provide your custom Genson configuration to Jersey:

@Provider
public class GensonCustomResolver implements ContextResolver<Genson> {
  // configure the Genson instance
  private final Genson genson = new Genson.Builder().withConverter(new FloatConverter()).with(new JAXBBundle()).create();

  @Override
  public Genson getContext(Class<?> type) {
      return genson;
  }
}