This commit is contained in:
Looly 2022-06-23 00:27:09 +08:00
parent 8ee7124797
commit a8ca13d8d6
8 changed files with 65 additions and 49 deletions

View File

@ -6,7 +6,11 @@ import cn.hutool.core.lang.mutable.MutableEntry;
import java.util.function.Predicate; import java.util.function.Predicate;
/** /**
* JSON字符串解析器 * JSON字符串解析器实现
* <ul>
* <li>JSON字符串 --&gt; {@link JSONTokener} --&gt; {@link JSONObject}</li>
* <li>JSON字符串 --&gt; {@link JSONTokener} --&gt; {@link JSONArray}</li>
* </ul>
* *
* @author looly * @author looly
* @since 5.8.0 * @since 5.8.0

View File

@ -12,6 +12,7 @@ import cn.hutool.json.serialize.GlobalSerializeMapping;
import cn.hutool.json.serialize.JSONArraySerializer; import cn.hutool.json.serialize.JSONArraySerializer;
import cn.hutool.json.serialize.JSONDeserializer; import cn.hutool.json.serialize.JSONDeserializer;
import cn.hutool.json.serialize.JSONObjectSerializer; import cn.hutool.json.serialize.JSONObjectSerializer;
import cn.hutool.json.xml.JSONXMLUtil;
import java.io.File; import java.io.File;
import java.io.IOException; import java.io.IOException;
@ -201,7 +202,7 @@ public class JSONUtil {
* @return JSONObject * @return JSONObject
*/ */
public static JSONObject parseFromXml(final String xmlStr) { public static JSONObject parseFromXml(final String xmlStr) {
return XML.toJSONObject(xmlStr); return JSONXMLUtil.toJSONObject(xmlStr);
} }
// -------------------------------------------------------------------- Parse end // -------------------------------------------------------------------- Parse end
@ -362,7 +363,7 @@ public class JSONUtil {
* @return XML字符串 * @return XML字符串
*/ */
public static String toXmlStr(final JSON json) { public static String toXmlStr(final JSON json) {
return XML.toXml(json); return JSONXMLUtil.toXml(json);
} }
// -------------------------------------------------------------------- toString end // -------------------------------------------------------------------- toString end
@ -735,7 +736,7 @@ public class JSONUtil {
* @since 4.0.8 * @since 4.0.8
*/ */
public static JSONObject xmlToJson(final String xml) { public static JSONObject xmlToJson(final String xml) {
return XML.toJSONObject(xml); return JSONXMLUtil.toJSONObject(xml);
} }
/** /**

View File

@ -12,7 +12,7 @@ import cn.hutool.json.JSONException;
import cn.hutool.json.JSONObject; import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONParser; import cn.hutool.json.JSONParser;
import cn.hutool.json.JSONTokener; import cn.hutool.json.JSONTokener;
import cn.hutool.json.XML; import cn.hutool.json.xml.JSONXMLUtil;
import cn.hutool.json.serialize.GlobalSerializeMapping; import cn.hutool.json.serialize.GlobalSerializeMapping;
import cn.hutool.json.serialize.JSONSerializer; import cn.hutool.json.serialize.JSONSerializer;
@ -149,7 +149,7 @@ public class ObjectMapper {
final String jsonStr = StrUtil.trim(source); final String jsonStr = StrUtil.trim(source);
if (StrUtil.startWith(jsonStr, '<')) { if (StrUtil.startWith(jsonStr, '<')) {
// 可能为XML // 可能为XML
XML.toJSONObject(jsonObject, jsonStr, false); JSONXMLUtil.toJSONObject(jsonObject, jsonStr, false);
return; return;
} }
mapFromTokener(new JSONTokener(StrUtil.trim(source), jsonObject.getConfig()), jsonObject); mapFromTokener(new JSONTokener(StrUtil.trim(source), jsonObject.getConfig()), jsonObject);

View File

@ -1,5 +1,15 @@
/** /**
* JSON封装基于json.org官方库改造 * JSONJavaScript Object Notation JavaScript对象表示法封装包含以下组件
* <ul>
* <li>JSONObject使用键值对表示的数据类型使用"{}"包围</li>
* <li>JSONArray使用列表表示的数据类型使用"[]"包围</li>
* </ul>
* JSON封装主要包括JSON表示和JSON转换
*
* <pre>
* Java对象 &lt;----&gt; JSON对象 &lt;----&gt; JSON字符串
* </pre>
*
* *
* @author looly * @author looly
* *

View File

@ -4,8 +4,6 @@ import cn.hutool.core.text.StrUtil;
import cn.hutool.json.InternalJSONUtil; import cn.hutool.json.InternalJSONUtil;
import cn.hutool.json.JSONException; import cn.hutool.json.JSONException;
import cn.hutool.json.JSONObject; import cn.hutool.json.JSONObject;
import cn.hutool.json.XML;
import cn.hutool.json.XMLTokener;
/** /**
* XML解析器将XML解析为JSON对象 * XML解析器将XML解析为JSON对象
@ -50,7 +48,7 @@ public class JSONXMLParser {
token = x.nextToken(); token = x.nextToken();
if (token == XML.BANG) { if (token == JSONXMLUtil.BANG) {
c = x.next(); c = x.next();
if (c == '-') { if (c == '-') {
if (x.next() == '-') { if (x.next() == '-') {
@ -76,19 +74,19 @@ public class JSONXMLParser {
token = x.nextMeta(); token = x.nextMeta();
if (token == null) { if (token == null) {
throw x.syntaxError("Missing '>' after '<!'."); throw x.syntaxError("Missing '>' after '<!'.");
} else if (token == XML.LT) { } else if (token == JSONXMLUtil.LT) {
i += 1; i += 1;
} else if (token == XML.GT) { } else if (token == JSONXMLUtil.GT) {
i -= 1; i -= 1;
} }
} while (i > 0); } while (i > 0);
return false; return false;
} else if (token == XML.QUEST) { } else if (token == JSONXMLUtil.QUEST) {
// <? // <?
x.skipPast("?>"); x.skipPast("?>");
return false; return false;
} else if (token == XML.SLASH) { } else if (token == JSONXMLUtil.SLASH) {
// Close tag </ // Close tag </
@ -99,7 +97,7 @@ public class JSONXMLParser {
if (!token.equals(name)) { if (!token.equals(name)) {
throw x.syntaxError("Mismatched " + name + " and " + token); throw x.syntaxError("Mismatched " + name + " and " + token);
} }
if (x.nextToken() != XML.GT) { if (x.nextToken() != JSONXMLUtil.GT) {
throw x.syntaxError("Misshaped close tag"); throw x.syntaxError("Misshaped close tag");
} }
return true; return true;
@ -122,7 +120,7 @@ public class JSONXMLParser {
if (token instanceof String) { if (token instanceof String) {
string = (String) token; string = (String) token;
token = x.nextToken(); token = x.nextToken();
if (token == XML.EQ) { if (token == JSONXMLUtil.EQ) {
token = x.nextToken(); token = x.nextToken();
if (!(token instanceof String)) { if (!(token instanceof String)) {
throw x.syntaxError("Missing value"); throw x.syntaxError("Missing value");
@ -133,9 +131,9 @@ public class JSONXMLParser {
jsonobject.append(string, ""); jsonobject.append(string, "");
} }
} else if (token == XML.SLASH) { } else if (token == JSONXMLUtil.SLASH) {
// Empty tag <.../> // Empty tag <.../>
if (x.nextToken() != XML.GT) { if (x.nextToken() != JSONXMLUtil.GT) {
throw x.syntaxError("Misshaped tag"); throw x.syntaxError("Misshaped tag");
} }
if (jsonobject.size() > 0) { if (jsonobject.size() > 0) {
@ -145,7 +143,7 @@ public class JSONXMLParser {
} }
return false; return false;
} else if (token == XML.GT) { } else if (token == JSONXMLUtil.GT) {
// Content, between <...> and </...> // Content, between <...> and </...>
for (; ; ) { for (; ; ) {
token = x.nextContent(); token = x.nextContent();
@ -160,7 +158,7 @@ public class JSONXMLParser {
jsonobject.append("content", keepStrings ? token : InternalJSONUtil.stringToValue(string)); jsonobject.append("content", keepStrings ? token : InternalJSONUtil.stringToValue(string));
} }
} else if (token == XML.LT) { } else if (token == JSONXMLUtil.LT) {
// Nested element // Nested element
if (parse(x, jsonobject, tagName, keepStrings)) { if (parse(x, jsonobject, tagName, keepStrings)) {
if (jsonobject.size() == 0) { if (jsonobject.size() == 0) {

View File

@ -1,8 +1,8 @@
package cn.hutool.json; package cn.hutool.json.xml;
import cn.hutool.core.util.CharUtil; import cn.hutool.core.util.CharUtil;
import cn.hutool.json.xml.JSONXMLParser; import cn.hutool.json.JSONException;
import cn.hutool.json.xml.JSONXMLSerializer; import cn.hutool.json.JSONObject;
/** /**
* 提供静态方法在XML和JSONObject之间转换 * 提供静态方法在XML和JSONObject之间转换
@ -11,7 +11,7 @@ import cn.hutool.json.xml.JSONXMLSerializer;
* @see JSONXMLParser * @see JSONXMLParser
* @see JSONXMLSerializer * @see JSONXMLSerializer
*/ */
public class XML { public class JSONXMLUtil {
/** /**
* The Character '&amp;'. * The Character '&amp;'.

View File

@ -1,4 +1,8 @@
package cn.hutool.json; package cn.hutool.json.xml;
import cn.hutool.json.JSONConfig;
import cn.hutool.json.JSONException;
import cn.hutool.json.JSONTokener;
/** /**
* XML分析器继承自JSONTokener提供XML的语法分析 * XML分析器继承自JSONTokener提供XML的语法分析
@ -15,11 +19,11 @@ public class XMLTokener extends JSONTokener {
static { static {
entity = new java.util.HashMap<>(8); entity = new java.util.HashMap<>(8);
entity.put("amp", XML.AMP); entity.put("amp", JSONXMLUtil.AMP);
entity.put("apos", XML.APOS); entity.put("apos", JSONXMLUtil.APOS);
entity.put("gt", XML.GT); entity.put("gt", JSONXMLUtil.GT);
entity.put("lt", XML.LT); entity.put("lt", JSONXMLUtil.LT);
entity.put("quot", XML.QUOT); entity.put("quot", JSONXMLUtil.QUOT);
} }
/** /**
@ -73,7 +77,7 @@ public class XMLTokener extends JSONTokener {
return null; return null;
} }
if (c == '<') { if (c == '<') {
return XML.LT; return JSONXMLUtil.LT;
} }
sb = new StringBuilder(); sb = new StringBuilder();
for (; ; ) { for (; ; ) {
@ -130,17 +134,17 @@ public class XMLTokener extends JSONTokener {
case 0: case 0:
throw syntaxError("Misshaped meta tag"); throw syntaxError("Misshaped meta tag");
case '<': case '<':
return XML.LT; return JSONXMLUtil.LT;
case '>': case '>':
return XML.GT; return JSONXMLUtil.GT;
case '/': case '/':
return XML.SLASH; return JSONXMLUtil.SLASH;
case '=': case '=':
return XML.EQ; return JSONXMLUtil.EQ;
case '!': case '!':
return XML.BANG; return JSONXMLUtil.BANG;
case '?': case '?':
return XML.QUEST; return JSONXMLUtil.QUEST;
case '"': case '"':
case '\'': case '\'':
q = c; q = c;
@ -197,15 +201,15 @@ public class XMLTokener extends JSONTokener {
case '<': case '<':
throw syntaxError("Misplaced '<'"); throw syntaxError("Misplaced '<'");
case '>': case '>':
return XML.GT; return JSONXMLUtil.GT;
case '/': case '/':
return XML.SLASH; return JSONXMLUtil.SLASH;
case '=': case '=':
return XML.EQ; return JSONXMLUtil.EQ;
case '!': case '!':
return XML.BANG; return JSONXMLUtil.BANG;
case '?': case '?':
return XML.QUEST; return JSONXMLUtil.QUEST;
// Quoted string // Quoted string

View File

@ -2,7 +2,6 @@ package cn.hutool.json.xml;
import cn.hutool.json.JSONObject; import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil; import cn.hutool.json.JSONUtil;
import cn.hutool.json.XML;
import org.hamcrest.CoreMatchers; import org.hamcrest.CoreMatchers;
import org.hamcrest.MatcherAssert; import org.hamcrest.MatcherAssert;
import org.junit.Assert; import org.junit.Assert;
@ -22,11 +21,11 @@ public class XMLTest {
@Test @Test
public void escapeTest(){ public void escapeTest(){
final String xml = "<a>•</a>"; final String xml = "<a>•</a>";
final JSONObject jsonObject = XML.toJSONObject(xml); final JSONObject jsonObject = JSONXMLUtil.toJSONObject(xml);
Assert.assertEquals("{\"a\":\"\"}", jsonObject.toString()); Assert.assertEquals("{\"a\":\"\"}", jsonObject.toString());
final String xml2 = XML.toXml(JSONUtil.parseObj(jsonObject)); final String xml2 = JSONXMLUtil.toXml(JSONUtil.parseObj(jsonObject));
Assert.assertEquals(xml, xml2); Assert.assertEquals(xml, xml2);
} }
@ -34,10 +33,10 @@ public class XMLTest {
public void xmlContentTest(){ public void xmlContentTest(){
final JSONObject jsonObject = JSONUtil.createObj().set("content","123456"); final JSONObject jsonObject = JSONUtil.createObj().set("content","123456");
String xml = XML.toXml(jsonObject); String xml = JSONXMLUtil.toXml(jsonObject);
Assert.assertEquals("123456", xml); Assert.assertEquals("123456", xml);
xml = XML.toXml(jsonObject, null, new String[0]); xml = JSONXMLUtil.toXml(jsonObject, null, new String[0]);
Assert.assertEquals("<content>123456</content>", xml); Assert.assertEquals("<content>123456</content>", xml);
} }
} }