我正在创建一个API,它将接收HTTP请求并返回JSON报告。我一直在用Java(使用HTTPUrlConnection)和Python(使用请求)测试请求。 API是用Java Spark编写的。我正在使用Python进行一些测试,因为请求更容易使用。我使用的Python代码是为了深入了解我尝试做的事情,因为它可行。
我的请求的一些参数作为JSON对象的字符串表示形式传递。我发现的是,当JSON对象字符串传递给我的API并进行解析时,对象的处理方式会有所不同,具体取决于它来自何处,特别是当有问题的数据是int时。
在Python中:
report_dict = {
"client_name": "Wayne_Enterprises",
"client_id": 123,
"report_type": "test_report",
"timestamp_generated": "2015-08-11T11:00:00Z",
"report_data": {"revenue": 40000}
}
response = requests.post(myurl, data=json.dumps(report_dict))
在Java中:
JSONObject testData = new JSONObject();
JSONObject content = new JSONObject();
content.put("revenue", 40000);
testData.put("client_name","Wayne_Enterprises");
testData.put("client_id",123);
testData.put("report_type","test_report");
testData.put("timestamp_generated","2015-08-11T11:00:00Z");
testData.put("report_data",content.toString());
URL url = new URL("http","127.0.0.1",8080,"/reports/");
HttpURLConnection connection = (HttpURLConnection)url.openConnection();
connection.setRequestMethod("POST");
connection.setUseCaches(false);
connection.setDoOutput(true);
System.out.println(testData.toString());
DataOutputStream wr = new DataOutputStream (connection.getOutputStream());
wr.writeBytes(testData.toString());
wr.close();
JSON字符串在API中处理如下:
120> JSONParser parser = new JSONParser();
121> JSONObject report = (JSONObject) parser.parse(request.body());
122> String reportType = (String) report.get("report_type");
123> String clientName = (String) report.get("client_name");
124> int clientId = (int)(long) report.get("client_id");
125> JSONObject data = (JSONObject)parser.parse((String)report.get("report_data"));
126> String dateStr = (String) report.get("timestamp_generated");
当我在Python中运行测试时,数据已成功发布。但是,当我运行java测试时,当我设置clientID int时,我得到一个ClassCast异常:java.lang.String cannot be cast to java.lang.long
。嗯,这很容易解决。所以这条线现在变成了:
int clientId = (int)(long) Long.parseLong((String) report.get("client_id"));
这不仅是丑陋的,而且会产生相反的问题。现在我已经无法将java.lang.Long强制转换为java.lang.String!
我在Java中创建对象时出错了吗?或者我是否错误地处理了请求?
编辑: 我正在使用org.json.simple
字符串输出: 爪哇
{"report_data":"{\"revenue\":123}","timestamp_generated":"2000-01-01T12:00:00Z","report_type":"api_testing","client_name":"Wayne_Enterprises","client_id":123}
的Python
{'client_name': 'test_client', 'report_data': '{"revenue": 4000}', 'report_type': 'transparency', 'client_id': 123, 'timestamp_generated': '2015-07-29T11:00:00Z'}
堆栈追踪:
java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Long
at com.simplerelevance.Main.lambda$init$1(Main.java:124)
at com.simplerelevance.Main$$Lambda$2/449105069.handle(Unknown Source)
at spark.SparkBase$1.handle(SparkBase.java:311)
at spark.webserver.MatcherFilter.doFilter(MatcherFilter.java:159)
at spark.servlet.SparkFilter.doFilter(SparkFilter.java:131)
at org.eclipse.jetty.servlet.ServletHandler$CachedChain.doFilter(Servlet
Handler.java:1652)
at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java
:585)
at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.j
ava:143)
at org.eclipse.jetty.security.SecurityHandler.handle(SecurityHandler.jav
a:577)
at org.eclipse.jetty.server.session.SessionHandler.doHandle(SessionHandl
er.java:223)
at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandl
er.java:1127)
at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:
515)
at org.eclipse.jetty.server.session.SessionHandler.doScope(SessionHandle
r.java:185)
at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandle
r.java:1061)
at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.j
ava:141)
at org.eclipse.jetty.server.handler.ContextHandlerCollection.handle(Cont
extHandlerCollection.java:215)
at org.eclipse.jetty.server.handler.HandlerCollection.handle(HandlerColl
ection.java:110)
at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper
.java:97)
at org.eclipse.jetty.server.Server.handle(Server.java:497)
at org.eclipse.jetty.server.HttpChannel.handle(HttpChannel.java:310)
at org.eclipse.jetty.server.HttpConnection.onFillable(HttpConnection.jav
a:257)
at org.eclipse.jetty.io.AbstractConnection$2.run(AbstractConnection.java
:540)
at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPoo
l.java:635)
at org.eclipse.jetty.util.thread.QueuedThreadPool$3.run(QueuedThreadPool
.java:555)
at java.lang.Thread.run(Thread.java:745)
答案 0 :(得分:2)
为什么不使用:
int clientId = (int) report.getLong("client_id");
getLong根据密钥返回长整数。然后你从长期转换为int。
或者,您可以在Java中更改clientId的声明以键入long,而不是int。然后不需要铸造。
答案 1 :(得分:1)
report.get("client_id”);
会为您提供String
个对象,该对象不能只投放到long
或int
。请改用report.getLong
或report.getInt
。