/src/main/java/com/alibaba/fastjson/parser/AbstractJSONParser.java

https://github.com/flydream/fastjson · Java · 240 lines · 209 code · 31 blank · 0 comment · 26 complexity · 6be95f73de259bebf7db64a90e04033f MD5 · raw file

  1. package com.alibaba.fastjson.parser;
  2. import static com.alibaba.fastjson.parser.JSONToken.EOF;
  3. import static com.alibaba.fastjson.parser.JSONToken.FALSE;
  4. import static com.alibaba.fastjson.parser.JSONToken.LBRACE;
  5. import static com.alibaba.fastjson.parser.JSONToken.LBRACKET;
  6. import static com.alibaba.fastjson.parser.JSONToken.LITERAL_FLOAT;
  7. import static com.alibaba.fastjson.parser.JSONToken.LITERAL_INT;
  8. import static com.alibaba.fastjson.parser.JSONToken.LITERAL_STRING;
  9. import static com.alibaba.fastjson.parser.JSONToken.NEW;
  10. import static com.alibaba.fastjson.parser.JSONToken.NULL;
  11. import static com.alibaba.fastjson.parser.JSONToken.RBRACKET;
  12. import static com.alibaba.fastjson.parser.JSONToken.SET;
  13. import static com.alibaba.fastjson.parser.JSONToken.TREE_SET;
  14. import static com.alibaba.fastjson.parser.JSONToken.TRUE;
  15. import java.util.Collection;
  16. import java.util.Date;
  17. import java.util.HashSet;
  18. import java.util.Map;
  19. import java.util.TreeSet;
  20. import com.alibaba.fastjson.JSONArray;
  21. import com.alibaba.fastjson.JSONException;
  22. import com.alibaba.fastjson.JSONObject;
  23. public abstract class AbstractJSONParser {
  24. @SuppressWarnings("rawtypes")
  25. public Object parseObject(final Map object) {
  26. return parseObject(object, null);
  27. }
  28. @SuppressWarnings("rawtypes")
  29. public abstract Object parseObject(final Map object, Object fieldName);
  30. public JSONObject parseObject() {
  31. JSONObject object = new JSONObject();
  32. parseObject(object);
  33. return object;
  34. }
  35. @SuppressWarnings("rawtypes")
  36. public final void parseArray(final Collection array) {
  37. parseArray(array, null);
  38. }
  39. @SuppressWarnings({ "unchecked", "rawtypes" })
  40. public final void parseArray(final Collection array, Object fieldName) {
  41. final JSONLexer lexer = getLexer();
  42. if (lexer.token() != JSONToken.LBRACKET) {
  43. throw new JSONException("syntax error, expect [, actual " + JSONToken.name(lexer.token()));
  44. }
  45. lexer.nextToken(JSONToken.LITERAL_STRING);
  46. for (;;) {
  47. if (isEnabled(Feature.AllowArbitraryCommas)) {
  48. while (lexer.token() == JSONToken.COMMA) {
  49. lexer.nextToken();
  50. continue;
  51. }
  52. }
  53. Object value;
  54. switch (lexer.token()) {
  55. case LITERAL_INT:
  56. value = lexer.integerValue();
  57. lexer.nextToken(JSONToken.COMMA);
  58. break;
  59. case LITERAL_FLOAT:
  60. if (lexer.isEnabled(Feature.UseBigDecimal)) {
  61. value = lexer.decimalValue(true);
  62. } else {
  63. value = lexer.decimalValue(false);
  64. }
  65. lexer.nextToken(JSONToken.COMMA);
  66. break;
  67. case LITERAL_STRING:
  68. String stringLiteral = lexer.stringVal();
  69. lexer.nextToken(JSONToken.COMMA);
  70. if (lexer.isEnabled(Feature.AllowISO8601DateFormat)) {
  71. JSONScanner iso8601Lexer = new JSONScanner(stringLiteral);
  72. if (iso8601Lexer.scanISO8601DateIfMatch()) {
  73. value = iso8601Lexer.getCalendar().getTime();
  74. } else {
  75. value = stringLiteral;
  76. }
  77. } else {
  78. value = stringLiteral;
  79. }
  80. break;
  81. case TRUE:
  82. value = Boolean.TRUE;
  83. lexer.nextToken(JSONToken.COMMA);
  84. break;
  85. case FALSE:
  86. value = Boolean.FALSE;
  87. lexer.nextToken(JSONToken.COMMA);
  88. break;
  89. case LBRACE:
  90. JSONObject object = new JSONObject();
  91. value = parseObject(object);
  92. break;
  93. case LBRACKET:
  94. Collection items = new JSONArray();
  95. parseArray(items);
  96. value = items;
  97. break;
  98. case NULL:
  99. value = null;
  100. lexer.nextToken(JSONToken.LITERAL_STRING);
  101. break;
  102. case RBRACKET:
  103. lexer.nextToken(JSONToken.COMMA);
  104. return;
  105. default:
  106. value = parse();
  107. break;
  108. }
  109. array.add(value);
  110. if (lexer.token() == JSONToken.COMMA) {
  111. lexer.nextToken(JSONToken.LITERAL_STRING);
  112. continue;
  113. }
  114. }
  115. }
  116. public Object parse() {
  117. return parse(null);
  118. }
  119. public Object parse(Object fieldName) {
  120. final JSONLexer lexer = getLexer();
  121. switch (lexer.token()) {
  122. case SET:
  123. lexer.nextToken();
  124. HashSet<Object> set = new HashSet<Object>();
  125. parseArray(set, fieldName);
  126. return set;
  127. case TREE_SET:
  128. lexer.nextToken();
  129. TreeSet<Object> treeSet = new TreeSet<Object>();
  130. parseArray(treeSet, fieldName);
  131. return treeSet;
  132. case LBRACKET:
  133. JSONArray array = new JSONArray();
  134. parseArray(array, fieldName);
  135. return array;
  136. case LBRACE:
  137. JSONObject object = new JSONObject();
  138. return parseObject(object, fieldName);
  139. case LITERAL_INT:
  140. Number intValue = lexer.integerValue();
  141. lexer.nextToken();
  142. return intValue;
  143. case LITERAL_FLOAT:
  144. Object value = lexer.decimalValue(isEnabled(Feature.UseBigDecimal));
  145. lexer.nextToken();
  146. return value;
  147. case LITERAL_STRING:
  148. String stringLiteral = lexer.stringVal();
  149. lexer.nextToken(JSONToken.COMMA);
  150. if (lexer.isEnabled(Feature.AllowISO8601DateFormat)) {
  151. JSONScanner iso8601Lexer = new JSONScanner(stringLiteral);
  152. if (iso8601Lexer.scanISO8601DateIfMatch()) {
  153. return iso8601Lexer.getCalendar().getTime();
  154. }
  155. }
  156. return stringLiteral;
  157. case NULL:
  158. lexer.nextToken();
  159. return null;
  160. case TRUE:
  161. lexer.nextToken();
  162. return Boolean.TRUE;
  163. case FALSE:
  164. lexer.nextToken();
  165. return Boolean.FALSE;
  166. case NEW:
  167. lexer.nextToken(JSONToken.IDENTIFIER);
  168. if (lexer.token() != JSONToken.IDENTIFIER) {
  169. throw new JSONException("syntax error");
  170. }
  171. lexer.nextToken(JSONToken.LPAREN);
  172. accept(JSONToken.LPAREN);
  173. long time = ((Number) lexer.integerValue()).longValue();
  174. accept(JSONToken.LITERAL_INT);
  175. accept(JSONToken.RPAREN);
  176. return new Date(time);
  177. case EOF:
  178. if (lexer.isBlankInput()) {
  179. return null;
  180. }
  181. default:
  182. throw new JSONException("TODO " + JSONToken.name(lexer.token()) + " " + lexer.stringVal());
  183. }
  184. }
  185. public void config(Feature feature, boolean state) {
  186. getLexer().config(feature, state);
  187. }
  188. public boolean isEnabled(Feature feature) {
  189. return getLexer().isEnabled(feature);
  190. }
  191. public abstract JSONLexer getLexer();
  192. public final void accept(final int token) {
  193. final JSONLexer lexer = getLexer();
  194. if (lexer.token() == token) {
  195. lexer.nextToken();
  196. } else {
  197. throw new JSONException("syntax error, expect " + JSONToken.name(token) + ", actual "
  198. + JSONToken.name(lexer.token()));
  199. }
  200. }
  201. public void close() {
  202. final JSONLexer lexer = getLexer();
  203. if (isEnabled(Feature.AutoCloseSource)) {
  204. if (!lexer.isEOF()) {
  205. throw new JSONException("not close json text, token : " + JSONToken.name(lexer.token()));
  206. }
  207. }
  208. }
  209. }