This commit is contained in:
Looly 2022-04-18 21:50:33 +08:00
parent 571d76f578
commit 5a1ae69c21
3 changed files with 56 additions and 5 deletions

View File

@ -1,11 +1,11 @@
package cn.hutool.json;
import cn.hutool.core.io.IoUtil;
import cn.hutool.core.util.StrUtil;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.Reader;
import java.io.StringReader;
@ -67,13 +67,13 @@ public class JSONTokener {
}
/**
* 从InputStream中构建
* 从InputStream中构建使用UTF-8编码
*
* @param inputStream InputStream
* @param config JSON配置
*/
public JSONTokener(InputStream inputStream, JSONConfig config) throws JSONException {
this(new InputStreamReader(inputStream), config);
this(IoUtil.getUtf8Reader(inputStream), config);
}
/**

View File

@ -3,6 +3,7 @@ package cn.hutool.json;
import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.ArrayIter;
import cn.hutool.core.convert.Convert;
import cn.hutool.core.io.IoUtil;
import cn.hutool.core.lang.Filter;
import cn.hutool.core.lang.mutable.Mutable;
import cn.hutool.core.lang.mutable.MutablePair;
@ -13,6 +14,8 @@ import cn.hutool.json.serialize.GlobalSerializeMapping;
import cn.hutool.json.serialize.JSONObjectSerializer;
import cn.hutool.json.serialize.JSONSerializer;
import java.io.InputStream;
import java.io.Reader;
import java.util.Enumeration;
import java.util.Iterator;
import java.util.Map;
@ -24,6 +27,8 @@ import java.util.ResourceBundle;
* <li>Map JSONObject将键值对加入JSON对象</li>
* <li>Map.Entry JSONObject</li>
* <li>CharSequence JSONObject使用JSONTokener解析</li>
* <li>{@link Reader} JSONObject使用JSONTokener解析</li>
* <li>{@link InputStream} JSONObject使用JSONTokener解析</li>
* <li>JSONTokener JSONObject直接解析</li>
* <li>ResourceBundle JSONObject</li>
* <li>Bean JSONObject调用其getters方法getXXX或者isXXX获得值加入到JSON对象例如如果JavaBean对象中有个方法getName()值为"张三"获得的键值对为name: "张三"</li>
@ -75,7 +80,7 @@ public class ObjectMapper {
return;
}
if (ArrayUtil.isArray(source) || source instanceof JSONArray) {
if (source instanceof JSONArray) {
// 不支持集合类型转换为JSONObject
throw new JSONException("Unsupported type [{}] to JSONObject!", source.getClass());
}
@ -91,6 +96,12 @@ public class ObjectMapper {
} else if (source instanceof CharSequence) {
// 可能为JSON字符串
mapFromStr((CharSequence) source, jsonObject, filter);
} else if (source instanceof Reader) {
mapFromTokener(new JSONTokener((Reader) source, jsonObject.getConfig()), jsonObject, filter);
} else if (source instanceof InputStream) {
mapFromTokener(new JSONTokener((InputStream) source, jsonObject.getConfig()), jsonObject, filter);
} else if (source instanceof byte[]) {
mapFromTokener(new JSONTokener(IoUtil.toStream((byte[]) source), jsonObject.getConfig()), jsonObject, filter);
} else if (source instanceof JSONTokener) {
// JSONTokener
mapFromTokener((JSONTokener) source, jsonObject, filter);
@ -111,7 +122,7 @@ public class ObjectMapper {
* 初始化
*
* @param jsonArray 目标{@link JSONArray}
* @param filter 键值对过滤编辑器可以通过实现此接口完成解析前对值的过滤和修改操作{@code null}表示不过滤
* @param filter 键值对过滤编辑器可以通过实现此接口完成解析前对值的过滤和修改操作{@code null}表示不过滤
* @throws JSONException 非数组或集合
*/
@SuppressWarnings({"rawtypes", "unchecked"})
@ -128,6 +139,12 @@ public class ObjectMapper {
} else if (source instanceof CharSequence) {
// JSON字符串
mapFromStr((CharSequence) source, jsonArray, filter);
}else if (source instanceof Reader) {
mapFromTokener(new JSONTokener((Reader) source, jsonArray.getConfig()), jsonArray, filter);
} else if (source instanceof InputStream) {
mapFromTokener(new JSONTokener((InputStream) source, jsonArray.getConfig()), jsonArray, filter);
} else if (source instanceof byte[]) {
mapFromTokener(new JSONTokener(IoUtil.toStream((byte[]) source), jsonArray.getConfig()), jsonArray, filter);
} else if (source instanceof JSONTokener) {
mapFromTokener((JSONTokener) source, jsonArray, filter);
} else {

View File

@ -28,7 +28,10 @@ import org.junit.Assert;
import org.junit.Ignore;
import org.junit.Test;
import java.io.ByteArrayInputStream;
import java.io.StringReader;
import java.math.BigDecimal;
import java.nio.charset.StandardCharsets;
import java.sql.Timestamp;
import java.util.Date;
import java.util.HashMap;
@ -143,6 +146,37 @@ public class JSONObjectTest {
Assert.assertEquals(new JSONArray(), json.getJSONObject("data").getJSONArray("cards"));
}
@Test
public void parseBytesTest() {
String jsonStr = "{'msg':'这里还没有内容','data':{'cards':[]},'ok':0}";
//noinspection MismatchedQueryAndUpdateOfCollection
JSONObject json = new JSONObject(jsonStr.getBytes(StandardCharsets.UTF_8));
Assert.assertEquals(new Integer(0), json.getInt("ok"));
Assert.assertEquals(new JSONArray(), json.getJSONObject("data").getJSONArray("cards"));
}
@Test
public void parseReaderTest() {
String jsonStr = "{'msg':'这里还没有内容','data':{'cards':[]},'ok':0}";
final StringReader stringReader = new StringReader(jsonStr);
//noinspection MismatchedQueryAndUpdateOfCollection
JSONObject json = new JSONObject(stringReader);
Assert.assertEquals(new Integer(0), json.getInt("ok"));
Assert.assertEquals(new JSONArray(), json.getJSONObject("data").getJSONArray("cards"));
}
@Test
public void parseInputStreamTest() {
String jsonStr = "{'msg':'这里还没有内容','data':{'cards':[]},'ok':0}";
final ByteArrayInputStream in = new ByteArrayInputStream(jsonStr.getBytes(StandardCharsets.UTF_8));
//noinspection MismatchedQueryAndUpdateOfCollection
JSONObject json = new JSONObject(in);
Assert.assertEquals(new Integer(0), json.getInt("ok"));
Assert.assertEquals(new JSONArray(), json.getJSONObject("data").getJSONArray("cards"));
}
@Test
@Ignore
public void parseStringWithBomTest() {