如何在 Jackson 中为特定类配置 setter 和 getter 名称约定?
Posted
技术标签:
【中文标题】如何在 Jackson 中为特定类配置 setter 和 getter 名称约定?【英文标题】:How to configure setter and getter name convention in Jackson for a particular class? 【发布时间】:2022-01-05 02:47:33 【问题描述】:有一个自定义命名getter 和setter 的类。在这里,它们没有“get”或“set”前缀。
这种特殊配置只需要一个类,不需要全局。
我在 Jackson 开发线程中看到一个讨论提到
https://github.com/FasterXML/jackson-databind/issues/2674, https://github.com/FasterXML/jackson-databind/issues/1325@JsonPOJO
注释正是为此目的, 但我在 Jackson 的最新版本 (v2.13
) 中找不到。
如何表达“使用名称与 JSON 中的字段完全相同的 setter”的意图?
与以下相同,但以更简洁的方式没有为每个 setter 加上 @JsonProperty
或 @JsonSetter
:
class MyModel
private String first;
private int second;
public String first()
return this.first;
@JsonProperty("first")
public void first(String value)
this.first = value;
public int second()
return this.second;
@JsonProperty("second")
public void second(int value)
this.second = value;
【问题讨论】:
【参考方案1】:您可以覆盖默认的访问器命名策略,如下所示。
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.DeserializationFeature;
import com.fasterxml.jackson.databind.MapperFeature;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.introspect.DefaultAccessorNamingStrategy;
import lombok.AllArgsConstructor;
import lombok.NoArgsConstructor;
import lombok.ToString;
public class CustomPropertyNaming
public static void main( String[] args )
try
/* ObjectMapper instance configuration:
* (a) Override the default accessor naming strategy
* (b) Set FAIL_ON_UNKNOWN_PROPERTIES to false to avoid looking for other method names as properties (eg, toString()).
* (c) Set REQUIRE_SETTERS_FOR_GETTERS to true to handle 'toString()' being construed as a property getter */
ObjectMapper m = new ObjectMapper();
m.setAccessorNaming( new DefaultAccessorNamingStrategy.Provider().withGetterPrefix( "" ).withSetterPrefix( "" ) );
m.configure( DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false );
m.configure( MapperFeature.REQUIRE_SETTERS_FOR_GETTERS, true );
/* Serialization */
String json = m.writeValueAsString( MyModel.of( "ONE", 2 ) );
System.out.println( "Serialized: " + json );
/* Deserialization */
MyModel mm = m.readValue( json, MyModel.class );
System.out.println( "Deserialized: " + mm );
catch( JsonProcessingException e )
e.printStackTrace();
@NoArgsConstructor @AllArgsConstructor(staticName = "of") @ToString
private static class MyModel
private String first;
private int second;
public String first()
return this.first;
public void first( String value )
this.first = value;
public int second()
return this.second;
public void second( int value )
this.second = value;
运行上述类的输出
Serialized: "first":"ONE","second":2
Deserialized: CustomPropertyNaming.MyModel(first=ONE, second=2)
(我在MyModel
上使用过Lombok。你可能有你的构造函数和toString()
。)
关于此解决方案的几点说明。
由于现在属性名称和访问器名称相同,Jackson 倾向于将每个零参数方法视为 getter,将每个单参数方法视为 setter。这需要处理。我在这里所做的方式是添加一些在代码 cmets 中解释的配置。DefaultAccessorNamingStrategy.Provider
具有您可能想要探索的其他一些可配置性。
【讨论】:
谢谢库马尔。问题是,正如问题中提到的,“只有一个班级,而不是全球范围内”才需要这样做。我想要一个注释来改变特定类的反序列化。 Hi @diziaq, (a) "for only one class, not global": 如代码所示,可以只为这个类创建一个ObjectMapper
(并且可能被缓存和重用)。 (b) 注释:我找不到任何用于此目的的 Jackson 注释以上是关于如何在 Jackson 中为特定类配置 setter 和 getter 名称约定?的主要内容,如果未能解决你的问题,请参考以下文章
Java Jackson如何在自定义序列化程序中为对象使用默认序列化程序
如何在intelliJ IDEA中为我现有的Kotlin项目生成build.gradle文件