1

seeing periodic exceptions thrown when calling writeValueAsString() to marshall to JSON periodically...but, they always work when retried...

This is thrown by Jackson's API (v2.7.5) when parsing/marshaling a (non null) Java Date value to JSON...

here is our setup that is defined class level and reused across multiple threads/requests

private ObjectMapper mapper = new ObjectMapper();
mapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);

and the full stack trace...

com.fasterxml.jackson.databind.JsonMappingException: (was java.lang.ArrayIndexOutOfBoundsException) (through reference chain: MyIndex["createdAt"])
at com.fasterxml.jackson.databind.JsonMappingException.wrapWithPath(JsonMappingException.java:232)
at com.fasterxml.jackson.databind.JsonMappingException.wrapWithPath(JsonMappingException.java:197)
at com.fasterxml.jackson.databind.ser.std.StdSerializer.wrapAndThrow(StdSerializer.java:186)
at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:640)
at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:152)
at com.fasterxml.jackson.databind.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:541)
at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:632)
at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:152)
at com.fasterxml.jackson.databind.ser.DefaultSerializerProvider.serializeValue(DefaultSerializerProvider.java:114)
at com.fasterxml.jackson.databind.ObjectMapper._configAndWriteValue(ObjectMapper.java:2811)
at com.fasterxml.jackson.databind.ObjectMapper.writeValueAsString(ObjectMapper.java:2268) 
Ben ODay
  • 20,784
  • 9
  • 45
  • 68
  • 4
    I'm not sure I see how this is a duplicate, @JarrodRoberson. He's got some object which he serializing to JSON using Jackson. Jackson is throwing the exception, not his code, so where is he going to check his indices? – DavidS Jun 27 '16 at 22:47
  • `ObjectMapper` is thread safe on serializing. Is your POJO shared between threads? – Sotirios Delimanolis Jun 27 '16 at 23:00
  • 1
    Are you using the latest version of Jackson, Ben? It looks like some ArrayIndexOutOfBounds exceptions have been fixed in the past... – DavidS Jun 27 '16 at 23:01
  • the class with the ObjectMapper reference is used by multiple threads...also, using Jackson 2.3.0...I'll try again with 2.7.5...thx – Ben ODay Jun 28 '16 at 06:18
  • no luck, getting the same error with 2.7.5...randomly – Ben ODay Jun 28 '16 at 17:33
  • I added a manual retry and writeValueAsString() works every time with the same data immediately after throwing that exception...sure seems like a threading/race condition to me. I'm going to make the shared instance ThreadLocal next to see if that solves it... – Ben ODay Jun 28 '16 at 17:53

1 Answers1

0

further testing showed the root cause was non thread safe use of SimpleDateFormatter in the getter method of the class that Jackson was serializing...so Jackson is off the hook (and I'm back on it)...

changed to use a ThreadLocal<DateFormat> and all is well...

public class ThreadLocalDateFormat extends ThreadLocal<DateFormat>
{
    private String dateFormat;

    public ThreadLocalDateFormat(String dateFormat)
    {
        this.dateFormat = dateFormat;
    }

    @Override
    protected DateFormat initialValue()
    {
        return new SimpleDateFormat(dateFormat);
    }
}

thanks for the help...

Ben ODay
  • 20,784
  • 9
  • 45
  • 68