Skip to content

Instantly share code, notes, and snippets.

@benmccann
Created April 10, 2012 07:21
Show Gist options
  • Save benmccann/2349003 to your computer and use it in GitHub Desktop.
Save benmccann/2349003 to your computer and use it in GitHub Desktop.
Test demonstrating unexpected interaction between Lombok and Jackson
package com.connectifier.data.search;
import java.io.IOException;
import java.util.List;
import junit.framework.Assert;
import lombok.Getter;
import org.junit.Test;
import com.fasterxml.jackson.annotation.JsonAutoDetect;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.dataformat.smile.SmileFactory;
import com.google.common.collect.Lists;
public class LombokTest {
protected static final ObjectMapper SMILE_MAPPER;
static {
SMILE_MAPPER = new ObjectMapper(new SmileFactory());
// Don't include null props or empty lists
SMILE_MAPPER.setSerializationInclusion(JsonInclude.Include.NON_NULL);
// Only include whitelisted props
SMILE_MAPPER.setVisibilityChecker(
SMILE_MAPPER.getSerializationConfig().getDefaultVisibilityChecker()
.withFieldVisibility(JsonAutoDetect.Visibility.NONE)
.withGetterVisibility(JsonAutoDetect.Visibility.NONE)
.withSetterVisibility(JsonAutoDetect.Visibility.NONE)
.withCreatorVisibility(JsonAutoDetect.Visibility.NONE));
}
public static class TestObj {
@JsonProperty
@Getter(lazy=true)
private final List<String> prop = Lists.newArrayList();
@JsonProperty
private List<String> $lombok$lazy1v;
private volatile boolean $lombok$lazy1i;
private final Object $lombok$lazyLock = new Object[0];
public List<String> getCached() {
if (!this.$lombok$lazy1i) {
synchronized (this.$lombok$lazyLock) {
if (!this.$lombok$lazy1i) {
this.$lombok$lazy1v = Lists.newArrayList();
this.$lombok$lazy1i = true;
}
}
}
return this.$lombok$lazy1v;
}
}
@Test
public void testLazyGetter() {
TestObj o = new TestObj();
byte[] bytes = toBytes(o);
TestObj de = fromBytes(bytes, TestObj.class);
// Why does this fail?
Assert.assertNotNull(de.getProp());
}
@Test
public void testManualLazyGetter() {
TestObj o = new TestObj();
byte[] bytes = toBytes(o);
TestObj de = fromBytes(bytes, TestObj.class);
// Why does this pass given that the above fails?
Assert.assertNotNull(de.getCached());
}
public static byte[] toBytes(Object o) {
try {
return SMILE_MAPPER.writeValueAsBytes(o);
} catch (IOException e) {
throw new RuntimeException(e);
}
}
public static <T> T fromBytes(byte[] bytes, Class<T> clazz) {
try {
return SMILE_MAPPER.readValue(bytes, clazz);
} catch (IOException e) {
throw new RuntimeException(e);
}
}
}
@benmccann
Copy link
Author

Depends on:
"com.fasterxml.jackson.core" % "jackson-core" % "2.0.0",
"com.fasterxml.jackson.core" % "jackson-databind" % "2.0.0",
"com.fasterxml.jackson.dataformat" % "jackson-dataformat-smile" % "2.0.0",
"com.google.guava" % "guava" % "11.0.2",
"org.projectlombok" % "lombok" % "0.11.0"

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment