我有一个Spring Boot 2
应用程序,其中包含私有属性和公共获取者/设置器的模型。杰克逊是2.10.0
版本。
我需要一个自定义序列化器来输出JSON
而不扩展某些引用。根据我所读到的内容,如果该属性是私有的,则Jackson
无法访问它,并且随之而来的是编译错误。除非在它应该工作的时候有公共获取者。但事实并非如此。
但是,如果我将模型中的属性设置为公共,则没有错误。
同样,如果我在序列化器中使用 getter 而不是属性,那么一切都很好。
我误读了这个,序列化者真的把私人当作私人?
@JsonSerialize(using = ClimateSerializer.class)
public class Climate {
@Id
@GeneratedValue(strategy = GenerationType.AUTO, generator = "climate_gen")
private long id;
private float temperature;
private float humidity;
.... getters and setters
}
序列化程序
public class ClimateSerializer extends StdSerializer<Climate> {
public ClimateSerializer() {
this(null);
}
public ClimateSerializer(Class<Climate> t) {
super(t);
}
@Override
public void serialize(
final Climate value, final JsonGenerator jgen, final SerializerProvider provider)
throws IOException, JsonProcessingException {
jgen.writeStartObject();
jgen.writeNumberField("id", value.getId());
jgen.writeNumberField("temperature", value.getTemperature());
jgen.writeNumberField("humidity", value.getHumidity());
jgen.writeEndObject();
}
}
这将编译。
如果将写入*字段调用替换为
jgen.writeNumberField("id", value.id);
etc
etc
然后我得到一个编译错误。无法访问私有财产。这与我所读到的背道而驰。如果有公共获取者,Jackson
可以使用私有财产。
显然,直接使用吸气剂是可以的。它有效。但我想知道我读过的各种文档是否是错误的。
如果要实现自定义序列化程序并且同时不公开属性,则可以直接在类Climate
实现com.fasterxml.jackson.databind.JsonSerializable
接口:
class Climate implements JsonSerializable {
private long id;
private float temperature;
private float humidity;
@Override
public void serialize(JsonGenerator gen, SerializerProvider serializers) throws IOException {
gen.writeStartObject();
gen.writeNumberField("id", id);
gen.writeNumberField("temperature", temperature);
gen.writeNumberField("humidity", humidity);
gen.writeEndObject();
}
@Override
public void serializeWithType(JsonGenerator gen, SerializerProvider serializers, TypeSerializer typeSer) {
}
}
您的问题与Jackson
没有直接关系。而是使用访问修饰符。当您要使用默认序列化时,Jackson
使用包装在许多功能中的反射来序列化给定POJO
类以JSON
。因此,确实Jackson
可以使用私有字段,但在您的情况下,您希望实现自定义序列化程序,并且需要自己使用反射来使其工作。在其他情况下,您可以使用default
访问修饰符并将自定义序列化程序ClimateSerializer
和类Climate
放在同一个包中以使其正常工作。