0x01 反序列化过程
fastjson将字符串转换为对象的方法主要有parse和parseObject
其中parseObject也会调用parse来解析json,下面来分析下反序列化过程
首先写一个测试的javabean
public class TestBean {
public String isMessage;
public String message;
public int id;
public String getMessage() {
System.out.println("getMessage called");
return message;
}
public void setMessage(String message) {
System.out.println("setMessage called");
this.message = message;
}
public TestBean() {
}
public TestBean(String message, int id) {
this.message = message;
this.id = id;
}
public int getId() {
System.out.println("getId called");
return id;
}
public void setId(int id) {
System.out.println("setId called");
this.id = id;
}
@Override
public String toString() {
return "TestBean{" +
"message='" + message + '\'' +
", id=" + id +
'}';
}
}
反序列化测试代码
import com.alibaba.fastjson.JSON;
public class Derjson {
public static void main(String[] args) {
String text = "{\"@type\":\"TestBean\",\"message\":\"hello\",\"id\":888}";
Object obj = JSON.parseObject(text);
}
}
下断点调试,首先会进入
com.alibaba.fastjson.JSON#parseObject(java.lang.String)
可以看到该方法中调用了parse方法来解析json字符串,跟进该方法
该方法中获取了一个json解析器,一路跟进到
com.alibaba.fastjson.parser.DefaultJSONParser#DefaultJSONParser(java.lang.Object, com.alibaba.fastjson.parser.JSONLexer, com.alibaba.fastjson.parser.ParserConfig)
会在该方法中盘断json字符串是否以{ 或[开头,然后分配不同的解析流程,以其他字符开头的后面的解析过程中会报错
然后回到parse来,接着会进行解析json串的流程
首先是创建一个JSONObject对象,执行
com.alibaba.fastjson.parser.DefaultJSONParser#parseObject(java.util.Map, java.lang.Object)方法
该方法主要是对json相应的结构进行拆解,获取相应的值,进行对应的处理
比如在匹配到@type 键值时,会对其对应的值进行类加载操作
然后获取对应类的反序列化器
跟进getDeserializer,在识别到类是一个普通的javabean时,会调用
com.alibaba.fastjson.parser.ParserConfig#createJavaBeanDeserializer
创建反序列化器,在该方法中又会使用:
com.alibaba.fastjson.util.JavaBeanInfo#build来绑定对应属性的setter
getter处理方法,对于setter方法的规定代码如下:
要求setter方法长度大于4,不是静态方法,返回类型是void或所在类的类型,参数个数是1,第四个字母需要大写
然后会把set去掉,第四位字母小写后作为属性值来和bean中的属性列表来对比,当属性成功被匹配到时,将setter方法与该属性绑定
当没有匹配到时,会将属性名首位大写然后在前面加上is来组成一个新的属性,然后继续将其与bean中的属性列表对比,成功匹配到后将is开头的属性值与setter绑定
对于getter方法的规定如下
要求getter方法大于4,不能是static方法,方法以get开头且第四位大写,方法不能有参数,返回值继承
Collection/Map/AtomicBoolean/AtomicInteger/AtomicLong ;
在绑定完方法后,就开始进行反序列化操作,利用绑定的方法恢复属性的值
值得注意的是,在反序列化的过程中,fastjson如果对json的字段找不到相应的方法时,会尝试对字段进行处理,反序列化方法
com.alibaba.fastjson.parser.d