Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance. Project price only 1 $
You can buy this project and download/modify it how often you want.
/*
* Copyright (c) 2013-2024 Hutool Team and hutool.cn
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.dromara.hutool.json.convert;
import org.dromara.hutool.core.array.ArrayUtil;
import org.dromara.hutool.core.bean.BeanUtil;
import org.dromara.hutool.core.bean.copier.BeanCopier;
import org.dromara.hutool.core.convert.*;
import org.dromara.hutool.core.convert.impl.DateConverter;
import org.dromara.hutool.core.convert.impl.TemporalAccessorConverter;
import org.dromara.hutool.core.lang.Opt;
import org.dromara.hutool.core.map.MapWrapper;
import org.dromara.hutool.core.reflect.ConstructorUtil;
import org.dromara.hutool.core.reflect.TypeReference;
import org.dromara.hutool.core.reflect.TypeUtil;
import org.dromara.hutool.core.reflect.kotlin.KClassUtil;
import org.dromara.hutool.core.text.StrUtil;
import org.dromara.hutool.core.util.ObjUtil;
import org.dromara.hutool.json.*;
import org.dromara.hutool.json.serialize.JSONDeserializer;
import org.dromara.hutool.json.serialize.JSONStringer;
import java.io.Serializable;
import java.lang.reflect.Type;
import java.time.temporal.TemporalAccessor;
import java.util.Date;
import java.util.Iterator;
import java.util.Optional;
/**
* JSON转换器,实现Object对象转换为{@link JSON},支持的对象:
*
*
任意支持的对象,转换为JSON
*
JSON转换为指定对象Bean
*
*
* @author looly
* @since 6.0.0
*/
public class JSONConverter implements Converter, Serializable {
private static final long serialVersionUID = 1L;
/**
* 单例
*/
public static final JSONConverter INSTANCE = new JSONConverter(null);
static {
final RegisterConverter converter = RegisterConverter.getInstance();
converter.register(JSONObject.class, INSTANCE);
converter.register(JSONArray.class, INSTANCE);
}
/**
* 创建JSON转换器
*
* @param config JSON配置
* @return JSONConverter
*/
public static JSONConverter of(final JSONConfig config) {
return new JSONConverter(config);
}
private final JSONConfig config;
/**
* 构造
*
* @param config JSON配置
*/
public JSONConverter(final JSONConfig config) {
this.config = config;
}
@Override
public Object convert(Type targetType, Object value) throws ConvertException {
if (null == value) {
return null;
}
if (value instanceof JSONStringer) {
// 被JSONString包装的对象,获取其原始类型
value = ((JSONStringer) value).getRaw();
}
// JSON转对象
if (value instanceof JSON) {
if (targetType instanceof TypeReference) {
// 还原原始类型
targetType = ((TypeReference) targetType).getType();
}
return toBean(targetType, (JSON) value);
}
// 对象转JSON
final Class targetClass = TypeUtil.getClass(targetType);
if (null != targetClass) {
if (JSON.class.isAssignableFrom(targetClass)) {
return toJSON(value);
}
// 自定义日期格式
if (Date.class.isAssignableFrom(targetClass) || TemporalAccessor.class.isAssignableFrom(targetClass)) {
final Object date = toDateWithFormat(targetClass, value);
if (null != date) {
return date;
}
}
}
return ConvertUtil.convertWithCheck(targetType, value, null, config.isIgnoreError());
}
/**
* 实现Object对象转换为JSON对象,根据RFC8259规范,支持的对象:
*
*
String: 转换为相应的对象,"和'包围的字符串返回原字符串,""返回{@code null}
*
Array、Iterable、Iterator:转换为JSONArray
*
Bean对象:转为JSONObject
*
Number、Boolean:返回原对象
*
null:返回{@code null}
*
*
* @param obj 被转换的对象
* @return 转换后的对象
* @throws JSONException 转换异常
*/
public Object toJSON(Object obj) throws JSONException {
if (null == obj) {
return null;
}
if (obj instanceof Optional) {
obj = ((Optional) obj).orElse(null);
} else if (obj instanceof Opt) {
obj = ((Opt) obj).getOrNull();
}
final JSON json;
if (obj instanceof JSON || obj instanceof Number || obj instanceof Boolean) {
return obj;
} else if (obj instanceof CharSequence) {
return toJSON((CharSequence) obj);
} else if (obj instanceof MapWrapper) {
// MapWrapper实现了Iterable会被当作JSONArray,此处做修正
json = new JSONObject(obj, config);
} else if (obj instanceof Iterable || obj instanceof Iterator || ArrayUtil.isArray(obj)) {// 列表
json = new JSONArray(obj, config);
} else {// 对象
json = new JSONObject(obj, config);
}
return json;
}
/**
* 实现{@link CharSequence}转换为JSON对象,根据RFC8259规范
* 转换为相应的对象,"和'包围的字符串返回原字符串,""返回{@code null}
*
* @param str 被转换的字符串
* @return 转换后的对象
* @throws JSONException 转换异常
*/
public Object toJSON(final CharSequence str) throws JSONException {
if (null == str) {
return null;
}
final String jsonStr = StrUtil.trim(str);
if (jsonStr.isEmpty()) {
// https://www.rfc-editor.org/rfc/rfc8259#section-7
// 未被包装的空串理解为null
return null;
}
final char firstC = jsonStr.charAt(0);
// RFC8259,JSON字符串值、number, boolean, or null
final JSONParser jsonParser = JSONParser.of(new JSONTokener(jsonStr), config);
final Object value = jsonParser.nextValue();
if (jsonParser.getTokener().nextClean() != JSONTokener.EOF) {
// 对于用户提供的未转义字符串导致解析未结束,报错
throw new JSONException("JSON format error: {}", jsonStr);
}
switch (firstC) {
case '"':
case '\'':
return InternalJSONUtil.quote((CharSequence) value);
default:
if (ObjUtil.equals(jsonStr, value)) {
// 对于直接的字符串,如abc,按照字符串处理
return InternalJSONUtil.quote((CharSequence) value);
}
return value;
}
}
// ----------------------------------------------------------- Private method start
/**
* JSON转Bean,流程为:
*