Java中用Gson解析json字符串


=Start=

缘由:

因为阿里开源的fastjson前段时间爆出的漏洞实在是太多了(而且有些漏洞他们还喜欢偷偷处理,不及时通知广大用户。。。),虽然它用起来很方便,但是,安全第一,早换gson保平安。

正文:

参考解答:

Gson 提供简洁的 toJson() 和 fromJson() 方法以在Java对象和json字符串之间进行转换:

  • toJson() – Java object to JSON
  • fromJson() – JSON to Java object

一些常用的Demo展示,方便以后使用:

package com.ixyzero.learn.utils;

import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.google.gson.reflect.TypeToken;

import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.util.List;
import java.util.Map;

/**
* Created by ixyzero on 2019/9/13.
*/
public class LearnGson {
public static void main(String[] args) {
// Gson gson = new Gson();

// pretty print
Gson gson = new GsonBuilder().setPrettyPrinting().create();

// 将 JSON 字符串转换成 Map 对象
String json = "{\"name\":\"ixyzero.com\", \"age\":11}";
Map<String, Object> map = gson.fromJson(json, new TypeToken<Map<String, Object>>() {}.getType());

// JDK 1.8 支持的 Lambda 表达式
map.forEach((x, y) -> System.out.println("key : " + x + " , value : " + y));

// 常规 for 循环打印 Map
for (String key : map.keySet()) {
System.out.println("Key: " + key + ", Value: " + map.get(key));
}
System.out.println();


// 将 JSON 文件转换成 Map 对象
try {
map = gson.fromJson(new FileReader("/path/to/input.json"), new TypeToken<Map<String, Object>>() {}.getType());
} catch (FileNotFoundException e) {
e.printStackTrace();
}

// JDK 1.8 支持的 Lambda 表达式
map.forEach((x, y) -> System.out.println("key : " + x + " , value : " + y));
System.out.println();


// 将 JSON 数组转换成 List 对象
json = "[{\"name\":\"ixyzero.com\"}, {\"name\":\"test\"}]";
List<Map<String, String>> list = gson.fromJson(json, new TypeToken<List<Map<String, String>>>() {}.getType());

list.forEach(x -> System.out.println(x));
System.out.println();

for (int i = 0; i < list.size(); i++) {
System.out.println( list.get(i) );
list.get(i).forEach((x, y) -> System.out.println("key : " + x + " , value : " + y));
System.out.println();
}

// 将 Java 对象存入文件(借助 GsonBuilder().setPrettyPrinting().create() 进行格式化)
try (FileWriter writer = new FileWriter("/path/to/output.json")) {
gson.toJson(map, writer);
} catch (IOException e) {
e.printStackTrace();
}

System.out.println();
// 将 Java 对象转换成 json 字符串
String output = gson.toJson(map);
System.out.println(output);
}
}

/**
* content of 'input.json' *

{
"name": "11-27-gson-deserialization",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"prestart": "javac -classpath lib/gson-2.8.0.jar TestMain.java",
"start": "java -classpath .:lib/gson-2.8.0.jar TestMain"
},
"license": "MIT"
}
*/
参考链接:

=END=

,

《 “Java中用Gson解析json字符串” 》 有 10 条评论

  1. 抽象语法树分析寻找FastJSON的Gadgets
    https://www.freebuf.com/articles/web/213327.html
    https://github.com/Lonely-night/fastjson_gadgets_scanner

    Attacking Unmarshallers :: JNDI Injection using Getter Based Deserialization Gadgets
    https://srcincite.io/blog/2019/08/07/attacking-unmarshallers-jndi-injection-using-getter-based-deserialization.html

    CVE-2019-14540: Another gadgets to exploit default typing issue in (Jackson 2.x – 2.9.9.2 and 2.10.0.pr1)
    https://b1ue.cn/archives/201.html

    https://the.bytecode.club/fernflower.txt

  2. fastjson remote code execute poc 直接用intellij IDEA打开即可 首先编译得到Test.class,然后运行Poc.java
    https://github.com/shengqi158/fastjson-remote-code-execute-poc

    FastJson =< 1.2.47 反序列化漏洞浅析
    https://bithack.io/forum/393

    https://bithack.io/forum/397

    Fastjson <= 1.2.47 远程命令执行漏洞利用工具及方法
    https://github.com/CaijiOrz/fastjson-1.2.47-RCE

    fastjson-rce-exploit
    https://github.com/MagicZer0/fastjson-rce-exploit

  3. Google Gson的使用方法及JSON 技术对比
    https://blog.csdn.net/qq_15766297/article/details/70503214
    `
    Gson的应用主要为toJson与fromJson两个转换函数,无依赖,不需要例外额外的jar,能够直接跑在JDK上。而在使用这种对象转换之前需先创建好对象的类型以及其成员才能成功的将JSON字符串成功转换成相对应的对象。类里面只要有get和set方法,Gson完全可以将复杂类型的json到bean或bean到json的转换,是JSON解析的神器。Gson在功能上面无可挑剔,但是性能上面比FastJson有所差距。
    `

  4. 看快手如何干掉Fastjson
    https://mp.weixin.qq.com/s/1UajUkR-LfNT5i0LZrQXrA
    `
    在Fastjson -1.2.48和Fastjson -1.2.60版本漏洞的应急中,我们一直在反思,是不是得干掉Fastjson,怎么说服业务干掉Fastjson。对于Fastjson的代码质量,基础架构部有一些研究基础,认为Fastjson代码质量不是很好,这为后续推动Fastjson下线奠定了基础。

    有了前面的替代方案,接下来就是推动替代,说实话这真是一个很艰难的任务,对我们的挑战非常大。

    第一要务是管住增量,目前是在第三方库的引入上未做强制卡点,但是对于Fastjson这种高危库,安全组在白盒扫描器中添加了相应规则,发现有新增的Fastjson,及时提醒业务方不允许使用。另外也在Check-style禁用了Fastjson,这样研发在开发的过程中就会感知到引入了高危的组件。

    其次是存量Fastjson的替换,和基础架构组对出替代方案,依照业务优先级,优先推动主站等核心业务做替换,这些核心业务本身也很重视安全问题,几方立马就把这个事情推动下去了。这里面的核心挑战就是核心业务核心组件存在Fastjson依赖,第一步得把这里面的依赖给去除,否则其他位置还会间接引入Fastjson依赖。推完核心业务,接着按照类似模式推动对外业务,接着推动对内业务,历时快一年总共推动了不到1000个仓库完成替换。目前已经干掉了95%+Fastjson依赖。

    对于快手来说,在安全工程师不会被饿死这件事上,fastjson已经难以做贡献了(小编表示好慌)。
    `

  5. fastjson这么快老外为啥还是热衷 jackson?
    https://www.zhihu.com/question/44199956
    `
    代码质量不过关、bug多、对社区的反馈不及时等。

    Jackson的扩展性实在太好了。各种奇葩需求都能得到满足。

    Fastjson 确实快,但是和jackson 的差距不大,优势并没有太明显。Jackson还可以加上AfterBurner来使用byte generation,这样和Fastjson的差距就更小了。除了速度胜出外,Fastjson相比较 Jackson 有不少短板。
    1. 可定制性
    2. 代码质量
    3. 文档
    `

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注