1

I´m trying to wrap my head around REST services and Jackson. I have this entity:

 package de.dpunkt.myaktion.model;

import com.fasterxml.jackson.annotation.JsonIgnore;
import javax.persistence.*;
import javax.validation.constraints.DecimalMin;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
import java.util.List;

@NamedQueries({
        @NamedQuery(name = Campaign.findByOrganizer, query = "SELECT c FROM Campaign c WHERE c.organizer = :organizer ORDER BY c.name"),
        @NamedQuery(name = Campaign.findAll, query = "SELECT a FROM Campaign a ORDER BY a.name"),
        @NamedQuery(name = Campaign.getAmountDonatedSoFar, query = "SELECT SUM(d.amount) FROM Donation d WHERE d.campaign = :campaign")


})
@Entity
public class Campaign {
    public static final String findByOrganizer = "Campaign.findByOrganizer";
    public static final String findAll = "Campaign.findAll";
    public static final String getAmountDonatedSoFar = "Campaign.getAmountDonatedSoFar";

@NotNull
@Size(min = 4, max = 30, message = "{campaign.name.size}")
private String name;

@NotNull(message = "{campaign.targetAmount.notNull}")
@DecimalMin(value = "10.00", message = "{campaign.targetAmount.decimalMin}")
private Double targetAmount;

@NotNull(message = "{campaign.donationMinimum.notNull}")
@DecimalMin(value = "1.00", message = "{campaign.donationMinimum.decimalMin}")
private Double donationMinimum;

@Transient
private Double amountDonatedSoFar;

@AttributeOverrides({
@AttributeOverride(name = "name", column = @Column(name = "accountName"))})
@Embedded    
private Account account;

@GeneratedValue
@Id
private Long id;


@OneToMany(mappedBy = "campaign", cascade = CascadeType.REMOVE)
@JsonIgnore private List<Donation> donations;


@ManyToOne
@JsonIgnore private Organizer organizer;

public Campaign() {
    account = new Account();
}

public String getName() {
    return name;
}

public void setName(String name) {
    this.name = name;
}

public Double getTargetAmount() {
    return targetAmount;
}

public void setTargetAmount(Double targetAmount) {
    this.targetAmount = targetAmount;
}

public Double getDonationMinimum() {
    return donationMinimum;
}

public void setDonationMinimum(Double donationMinimum) {
    this.donationMinimum = donationMinimum;
}

public Double getAmountDonatedSoFar() {
    return amountDonatedSoFar;
}

public void setAmountDonatedSoFar(Double amountDonatedSoFar) {
    this.amountDonatedSoFar = amountDonatedSoFar;
}

public Account getAccount() {
    return account;
}

public void setAccount(Account account) {
    this.account = account;
}

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

public Long getId() {
    return id;
}


public List<Donation> getDonations() {
    return donations;
}

public void setDonations(List<Donation> donations) {
    this.donations = donations;
}


public Organizer getOrganizer() {
    return organizer;
}

public void setOrganizer(Organizer organizer) {
    this.organizer = organizer;
}

}

Please note the two @JsonIgnore-annotated fields, organizer and donations. My intention is to provide a list of Campaigns via REST, ignoring the organizer and the list of donations. I test this with cURL, like this:

curl -k -b cookie.txt https://localhost:8443/my-aktion/rest/organizer/campaign/list

The output is:

{"name":"testname","targetAmount":12.0,"donationMinimum":12.0,"amountDonatedSoFar":0.0,"account":{"name":"1212","nameOfBank":"1212","iban":"1212"},"id":1,"donations":[]}

That´s the first thing that strikes me as odd: organizer is rightly ignored, donations aren´t. And, Wildfly (8.2.0) throws following Exceptions :

 11:17:38,282 ERROR [io.undertow.request] (default task-30) UT005023: Exception handling request to /my-aktion/rest/organizer/campaign/list: org.jboss.resteasy.spi.UnhandledException: Response is committed, can't handle exception
    at org.jboss.resteasy.core.SynchronousDispatcher.writeException(SynchronousDispatcher.java:148) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.core.SynchronousDispatcher.writeResponse(SynchronousDispatcher.java:432) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.core.SynchronousDispatcher.invoke(SynchronousDispatcher.java:376) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.core.SynchronousDispatcher.invoke(SynchronousDispatcher.java:179) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.plugins.server.servlet.ServletContainerDispatcher.service(ServletContainerDispatcher.java:220) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.plugins.server.servlet.HttpServletDispatcher.service(HttpServletDispatcher.java:56) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.plugins.server.servlet.HttpServletDispatcher.service(HttpServletDispatcher.java:51) [resteasy-jaxrs-3.0.10.Final.jar:]
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:790) [jboss-servlet-api_3.1_spec-1.0.0.Final.jar:1.0.0.Final]
    at io.undertow.servlet.handlers.ServletHandler.handleRequest(ServletHandler.java:85) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.security.ServletSecurityRoleHandler.handleRequest(ServletSecurityRoleHandler.java:61) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.ServletDispatchingHandler.handleRequest(ServletDispatchingHandler.java:36) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at org.wildfly.extension.undertow.security.SecurityContextAssociationHandler.handleRequest(SecurityContextAssociationHandler.java:78)
    at io.undertow.server.handlers.PredicateHandler.handleRequest(PredicateHandler.java:43) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.security.SSLInformationAssociationHandler.handleRequest(SSLInformationAssociationHandler.java:131) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.security.ServletAuthenticationCallHandler.handleRequest(ServletAuthenticationCallHandler.java:56) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.server.handlers.DisableCacheHandler.handleRequest(DisableCacheHandler.java:33) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.server.handlers.PredicateHandler.handleRequest(PredicateHandler.java:43) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.security.handlers.AuthenticationConstraintHandler.handleRequest(AuthenticationConstraintHandler.java:51) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.security.handlers.AbstractConfidentialityHandler.handleRequest(AbstractConfidentialityHandler.java:45) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.security.ServletConfidentialityConstraintHandler.handleRequest(ServletConfidentialityConstraintHandler.java:63) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.security.ServletSecurityConstraintHandler.handleRequest(ServletSecurityConstraintHandler.java:56) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.security.handlers.AuthenticationMechanismsHandler.handleRequest(AuthenticationMechanismsHandler.java:58) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.security.CachedAuthenticatedSessionHandler.handleRequest(CachedAuthenticatedSessionHandler.java:70) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.security.handlers.SecurityInitialHandler.handleRequest(SecurityInitialHandler.java:76) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.server.handlers.PredicateHandler.handleRequest(PredicateHandler.java:43) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at org.wildfly.extension.undertow.security.jacc.JACCContextIdHandler.handleRequest(JACCContextIdHandler.java:61)
    at io.undertow.server.handlers.PredicateHandler.handleRequest(PredicateHandler.java:43) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.server.handlers.PredicateHandler.handleRequest(PredicateHandler.java:43) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.ServletInitialHandler.handleFirstRequest(ServletInitialHandler.java:261) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.ServletInitialHandler.dispatchRequest(ServletInitialHandler.java:247) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.ServletInitialHandler.access$000(ServletInitialHandler.java:76) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.servlet.handlers.ServletInitialHandler$1.handleRequest(ServletInitialHandler.java:166) [undertow-servlet-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.server.Connectors.executeRootHandler(Connectors.java:197) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at io.undertow.server.HttpServerExchange$1.run(HttpServerExchange.java:759) [undertow-core-1.1.0.Final.jar:1.1.0.Final]
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) [rt.jar:1.8.0_31]
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) [rt.jar:1.8.0_31]
    at java.lang.Thread.run(Thread.java:745) [rt.jar:1.8.0_31]
Caused by: com.fasterxml.jackson.databind.JsonMappingException: failed to lazily initialize a collection of role: de.dpunkt.myaktion.model.Campaign.donations, could not initialize proxy - no Session (through reference chain: java.util.ArrayList[0]->de.dpunkt.myaktion.model.Campaign["donations"])
    at com.fasterxml.jackson.databind.JsonMappingException.wrapWithPath(JsonMappingException.java:232) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.JsonMappingException.wrapWithPath(JsonMappingException.java:197) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.std.StdSerializer.wrapAndThrow(StdSerializer.java:187) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:647) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:152) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.std.CollectionSerializer.serializeContentsUsing(CollectionSerializer.java:145) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.std.CollectionSerializer.serializeContents(CollectionSerializer.java:87) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.std.CollectionSerializer.serializeContents(CollectionSerializer.java:23) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.std.AsArraySerializerBase.serialize(AsArraySerializerBase.java:183) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.DefaultSerializerProvider.serializeValue(DefaultSerializerProvider.java:236) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ObjectWriter.writeValue(ObjectWriter.java:604) [jackson-databind-2.4.1.jar:2.4.1]
    at org.jboss.resteasy.plugins.providers.jackson.ResteasyJackson2Provider.writeTo(ResteasyJackson2Provider.java:199) [resteasy-jackson2-provider-3.0.10.Final.jar:]
    at org.jboss.resteasy.core.interception.AbstractWriterInterceptorContext.writeTo(AbstractWriterInterceptorContext.java:129) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.core.interception.ServerWriterInterceptorContext.writeTo(ServerWriterInterceptorContext.java:62) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.core.interception.AbstractWriterInterceptorContext.proceed(AbstractWriterInterceptorContext.java:118) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.security.doseta.DigitalSigningInterceptor.aroundWriteTo(DigitalSigningInterceptor.java:143) [resteasy-crypto-3.0.10.Final.jar:]
    at org.jboss.resteasy.core.interception.AbstractWriterInterceptorContext.proceed(AbstractWriterInterceptorContext.java:122) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.plugins.interceptors.encoding.GZIPEncodingInterceptor.aroundWriteTo(GZIPEncodingInterceptor.java:100) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.core.interception.AbstractWriterInterceptorContext.proceed(AbstractWriterInterceptorContext.java:122) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.core.ServerResponseWriter.writeNomapResponse(ServerResponseWriter.java:99) [resteasy-jaxrs-3.0.10.Final.jar:]
    at org.jboss.resteasy.core.SynchronousDispatcher.writeResponse(SynchronousDispatcher.java:427) [resteasy-jaxrs-3.0.10.Final.jar:]
    ... 35 more
Caused by: org.hibernate.LazyInitializationException: failed to lazily initialize a collection of role: de.dpunkt.myaktion.model.Campaign.donations, could not initialize proxy - no Session
    at org.hibernate.collection.internal.AbstractPersistentCollection.throwLazyInitializationException(AbstractPersistentCollection.java:575) [hibernate-core-4.3.7.Final.jar:4.3.7.Final]
    at org.hibernate.collection.internal.AbstractPersistentCollection.withTemporarySessionIfNeeded(AbstractPersistentCollection.java:214) [hibernate-core-4.3.7.Final.jar:4.3.7.Final]
    at org.hibernate.collection.internal.AbstractPersistentCollection.initialize(AbstractPersistentCollection.java:554) [hibernate-core-4.3.7.Final.jar:4.3.7.Final]
    at org.hibernate.collection.internal.AbstractPersistentCollection.read(AbstractPersistentCollection.java:142) [hibernate-core-4.3.7.Final.jar:4.3.7.Final]
    at org.hibernate.collection.internal.PersistentBag.iterator(PersistentBag.java:294) [hibernate-core-4.3.7.Final.jar:4.3.7.Final]
    at com.fasterxml.jackson.databind.ser.std.CollectionSerializer.serializeContents(CollectionSerializer.java:90) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.std.CollectionSerializer.serializeContents(CollectionSerializer.java:23) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.std.AsArraySerializerBase.serialize(AsArraySerializerBase.java:183) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:505) [jackson-databind-2.4.1.jar:2.4.1]
    at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:639) [jackson-databind-2.4.1.jar:2.4.1]
    ... 52 more

I see an error trying to lazy initialize a collection of Donations, but why even try? Isn´t the @JsonIgnore annotation there to prevent exactly this?

Jannis Alexakis
  • 1,209
  • 3
  • 19
  • 37
  • 1
    i guess json ignore just not add the string json to the output when serialize, so the manipulations will needs to execute. – anurag gupta Feb 26 '15 at 10:55
  • The json you're showing us is not even valid json. Please show us real output. – JB Nizet Feb 26 '15 at 11:08
  • @JB Nizet There was a bracket missing, corrected. – Jannis Alexakis Feb 26 '15 at 12:38
  • @anurag gupta Sorry, I don´t understand what you mean – Jannis Alexakis Feb 26 '15 at 12:38
  • @jsonignore only prevents including the field when you serialize the class into json. the exception is from hibernate, try this http://stackoverflow.com/questions/21574236/org-hibernate-lazyinitializationexception-could-not-initialize-proxy-no-sess – MarianP Feb 26 '15 at 13:01
  • or if you want it not initialized by hibernate put the jsonignore on the getter method http://stackoverflow.com/questions/23628526/failed-to-lazily-initialize-a-collection-of-role-in-manytomany-relationship-desp – MarianP Feb 26 '15 at 13:02
  • RestEasy doesn't use Jackson by default. The default JSON marshaller is Jettison. have you configured it to use Jackson? – JB Nizet Feb 26 '15 at 13:07
  • @JB Nizet I have it configured to use JAckson. But now it works anyway. All I did was change the Jackson version in web.xml, from 2.5.1 to 2.3.2 (purely arbitrary, I was grasping at straws) and rebuild the whole project, then it worked. So, just to make sure, I changed the version back to 2.5.1 and rebuilt. And it still works...I really don´t understand what happened here. – Jannis Alexakis Feb 26 '15 at 14:40
  • There was a bug in jackson with collections. I do not know, if it was fixed. The error occurs because of lazyloading. The context to load the data is not any more available. Ensure that every data is loaded before you give it back via jax-rs. – Christian13467 Apr 28 '17 at 08:59

0 Answers0