当前位置:网站首页>Gson的@JsonAdater注解的几种方式
Gson的@JsonAdater注解的几种方式
2022-07-01 06:25:00 【ydfind】
Gson的@JsonAdater注解的几种方式
总结
可以通过自定义TypeAdapter和TypeAdapterFactory的方式,自定义gson的序列化和反序列规则,TypeAdapterFactory可以拿到上下文gson、TokenType类型;
也可以通过继承JsonReader重新写一次代码,在beginArray和endArray想办法跳过array的string形式的左右 双引号", gson.fromJson(myJsonReader, Type)也可以实现 解析时自动将String变为List,但采用注解@JsonAdapter的方式更为正规一些;
问题描述
json字符串:
{
"cityIds": "[1,2,1001,13131]",
"types": "[{\"name\": \"biz\",\"details\": [1]}]"
}
java对象定义:
@Data
public static class RequestParams {
// json字符串里对应的是String
private List<TypeItem> types;
private List<Integer> cityIds;
}
@Data
public static class TypeItem {
private String name;
private List<Integer> details;
}
可以看到json里面cityIds和types都是String,而pojo里则是List,使用gson的fromJson将json转为pojo会发生报错
方式一
@JsonAdapter(StringCollectionTypeAdapterFactory.class)
private List<TagItem> tags;
@JsonAdapter(StringCollectionTypeAdapterFactory.class)
private List<Integer> cityIds;
public static class StringCollectionTypeAdapterFactory implements TypeAdapterFactory {
@Override
public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> typeToken) {
// 为了write的时候能使用到elementTypeAdapter
Type type = typeToken.getType();
Class<? super T> rawType = typeToken.getRawType();
if (!Collection.class.isAssignableFrom(rawType)) {
return null;
}
Type elementType = $Gson$Types.getCollectionElementType(type, rawType);
TypeAdapter<?> elementTypeAdapter = gson.getAdapter(TypeToken.get(elementType));
TypeAdapter<T> result = new Adapter(gson, elementTypeAdapter, typeToken);
return result;
}
private static final class Adapter<E> extends TypeAdapter<Collection<E>> {
private final TypeAdapter<E> elementTypeAdapter;
private final Gson gson;
private final TypeToken listType;
public Adapter(Gson context, TypeAdapter<E> elementTypeAdapter, TypeToken listType) {
this.elementTypeAdapter = elementTypeAdapter;
this.gson = context;
this.listType = listType;
}
@Override public Collection<E> read(JsonReader in) throws IOException {
if (in.peek() == JsonToken.NULL) {
in.nextNull();
return null;
}
List<E> list = gson.fromJson(in.nextString(), listType.getType());
return list;
}
// write后可以将array的string格式,重新变成array
@Override public void write(JsonWriter out, Collection<E> collection) throws IOException {
if (collection == null) {
out.nullValue();
return;
}
out.beginArray();
for (E element : collection) {
elementTypeAdapter.write(out, element);
}
out.endArray();
}
}
}
方式二-write原样
public static class StringCollectionTypeAdapterFactory1 implements TypeAdapterFactory {
@Override
public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> typeToken) {
return new Adapter(gson, typeToken);
}
private static final class Adapter<E> extends TypeAdapter<Collection<E>> {
private final Gson gson;
private final TypeToken listType;
public Adapter(Gson context, TypeToken listType) {
this.gson = context;
this.listType = listType;
}
@Override public Collection<E> read(JsonReader in) throws IOException {
if (in.peek() == JsonToken.NULL) {
in.nextNull();
return null;
}
List<E> list = gson.fromJson(in.nextString(), listType.getType());
return list;
}
@Override public void write(JsonWriter out, Collection<E> collection) throws IOException {
if (collection == null) {
out.nullValue();
return;
}
out.value(gson.toJson(collection));
}
}
}
方式三-简单写法
private static class CollectionStringTypeAdapterFactory implements TypeAdapterFactory {
@Override
public <T> TypeAdapter<T> create(Gson gson, TypeToken<T> type) {
return new TypeAdapter<T>() {
@Override
public void write(JsonWriter out, T value) throws IOException {
if (value == null) {
out.nullValue();
return;
}
gson.getAdapter(type).write(out, value);
}
@Override
public T read(JsonReader in) throws IOException {
if (in.peek() == JsonToken.NULL) {
return null;
}
if (in.peek() == JsonToken.BEGIN_ARRAY) {
return gson.getAdapter(type).read(in);
}
T collection = gson.fromJson(in.nextString(), type.getType());
return collection;
}
};
}
}
测试用例如下所示:
@Test
public void testGson1() {
Gson gson = new Gson();
RequestParams requestParam;
String json;
// 1.自动将string转为属性的List
json = "{\"id\": \"000000\",\"types\": \"[{\\\"name\\\":\\\"name1\\\",\\\"list\\\":[1,2]},{\\\"name\\\":\\\"name2\\\",\\\"list\\\":[3,4]}]\",\"keywordIds\": \"[12,13]\"}";
System.out.println(json);
requestParam = gson.fromJson(json, new TypeToken<RequestParams>() {}.getType());
Assert.assertTrue(requestParam.getTypes().get(0).getClass().getName().indexOf("TypeItem") >= 0);
System.out.println(gson.toJson(requestParam));
// 2.jsonArray也可以转为List
json = "{\"id\": \"000000\",\"keywordIds\": [12,13],\"types\": [{\"name\":\"name1\",\"list\":[1,2]},{\"name\":\"name2\",\"list\":[3,4]}]}";
requestParam = gson.fromJson(json, new TypeToken<RequestParams>() {}.getType());
Assert.assertTrue(requestParam.getTypes().get(0).getClass().getName().indexOf("TypeItem") >= 0);
System.out.println(gson.toJson(requestParam));
// 3.换行的方式呢
json = "{\n" +
"\t\"id\": \"000000\",\n" +
"\t\"keywordIds\": [12,13],\n" +
"\t\"types\": [{\"name\":\"name1\",\"list\":[1,2]},{\"name\":\"name2\",\"list\":[3,4]}]\n" +
"}";
requestParam = gson.fromJson(json, new TypeToken<RequestParams>() {}.getType());
Assert.assertTrue(requestParam.getTypes().get(0).getClass().getName().indexOf("TypeItem") >= 0);
System.out.println(gson.toJson(requestParam));
// 4.能否将List里面的Integer变成String呢
json = "{\n" +
"\t\"id\": \"000000\",\n" +
"\t\"keywordIds\": [12,13],\n" +
"\t\"types\": [{\"name\":\"name1\",\"list1\":[1,2]},{\"name\":\"name2\",\"list1\":[3,4]}]\n" +
"}";
requestParam = gson.fromJson(json, new TypeToken<RequestParams>() {}.getType());
Assert.assertTrue(requestParam.getTypes().get(0).getClass().getName().indexOf("TypeItem") >= 0);
System.out.println(gson.toJson(requestParam));
// 5.能否将List里面的Integer变成String
json = "{\n" +
"\t\"id\": \"000000\",\n" +
"\t\"keywordIds1\": [12,13],\n" +
"\t\"types\": [{\"name\":\"name1\",\"list1\":[1,2]},{\"name\":\"name2\",\"list1\":[3,4]}]\n" +
"}";
requestParam = gson.fromJson(json, new TypeToken<RequestParams>() {}.getType());
Assert.assertTrue(requestParam.getTypes().get(0).getClass().getName().indexOf("TypeItem") >= 0);
System.out.println(gson.toJson(requestParam));
// 6.自动将string转为属性的List, 并且list里面的Integer变为String
json = "{\"id\": \"000000\",\"types\": \"[{\\\"name\\\":\\\"name1\\\",\\\"list1\\\":[1,2]},{\\\"name\\\":\\\"name2\\\",\\\"list1\\\":[3,4]}]\",\"keywordIds1\": \"[12,13]\"}";
System.out.println(json);
requestParam = gson.fromJson(json, new TypeToken<RequestParams>() {}.getType());
Assert.assertTrue(requestParam.getTypes().get(0).getClass().getName().indexOf("TypeItem") >= 0);
System.out.println(gson.toJson(requestParam));
}
@Data
public static class RequestParams {
private String id;
@JsonAdapter(CollectionStringTypeAdapterFactory.class)
private List<TypeItem> types;
@JsonAdapter(CollectionStringTypeAdapterFactory.class)
private List<Integer> keywordIds;
@JsonAdapter(CollectionStringTypeAdapterFactory.class)
private List<String> keywordIds1;
}
@Data
public static class TypeItem {
private String name;
private List<Integer> list;
private List<String> list1;
}
边栏推荐
- ForkJoin和Stream流测试
- [unity shader ablation effect _ case sharing]
- Although pycharm is marked with red in the run-time search path, it does not affect the execution of the program
- Recueillir des trésors dans le palais souterrain (recherche de mémoire profonde)
- Golang panic recover custom exception handling
- webapck打包原理--启动过程分析
- 局域网监控软件有哪些功能
- 地宮取寶(記憶化深搜)
- Promise
- Camouflage request header Library: Anti useragent
猜你喜欢

【#Unity Shader#Amplify Shader Editor(ASE)_第九篇】

浅谈SIEM

Tidb single machine simulation deployment production environment cluster (closed pit practice, personal test is effective)

C语言课设学生选修课程系统(大作业)

Discrimination between left and right limits of derivatives and left and right derivatives

ForkJoin和Stream流测试
![阿里OSS Postman Invalid according to Policy: Policy Condition failed: [“starts-with“, “$key“, “test/“]](/img/3c/7684b7c594f7871471f89007294703.png)
阿里OSS Postman Invalid according to Policy: Policy Condition failed: [“starts-with“, “$key“, “test/“]

async 与 await

Record MySQL troubleshooting caused by disk sector damage

Top 10 Free 3D modeling software for beginners in 2022
随机推荐
Teach you how to implement a deep learning framework
Record MySQL troubleshooting caused by disk sector damage
[unity shader custom material panel part II]
C语言课设学生信息管理系统(大作业)
[ITSM] what is ITSM and why does it department need ITSM
Distributed lock implementation
Pychart configuring jupyter
lxml模块(数据提取)
Mongodb: I. what is mongodb? Advantages and disadvantages of mongodb
High order binary search tree
Requests module (requests)
To sort out the anomaly detection methods, just read this article!
证券类开户有什么影响 开户安全吗
B-树系列
【Unity Shader 描边效果_案例分享第一篇】
ManageEngine Zhuohao helps you comply with ISO 20000 standard (IV)
How does the port scanning tool help enterprises?
码力十足学量化|如何在财务报告寻找合适的财务公告
SQL语句
【企业数据安全】升级备份策略 保障企业数据安全