如何用Volley构建Map<String, List<>>结构并发送JSON格式POST请求
问题描述
需要发送如下格式的JSON数据:
{"date": "2022-11-15", "number": "2222", "user": "Faisal", "report_note": "Test", "detail": [{ "desc": "", "usable": 0, "condition": "GOOD", "numbering": "CRT-0002", "numbering_id": "2", "code": "F" }, { "desc": "", "usable": 0, "condition": "GOOD", "numbering": "CRT-0001", "numbering_id": "1", "code": "F" } ] }
需求:
- 能够接收服务器返回的JSON响应(已实现)
- 随请求向服务器发送上述格式的JSON数据
我编写了如下代码,但无法正确发送包含数组的JSON请求:
private void createPackagingReturn() { String url = "some/url"; Map<String, String> params = new HashMap<>(); params.put("date", date); params.put("number", number); params.put("user", name); params.put("report_note", report); params.put("detail", json); JsonObjectRequest jsonObjectRequest = new JsonObjectRequest(Request.Method.POST, url,new JSONObject(params), new Response.Listener<JSONObject>() { @Override public void onResponse(JSONObject response) { //Toast.makeText(getApplicationContext(),"Response :" + response.toString(), Toast.LENGTH_LONG).show(); title = "Information"; message = response.toString(); alertMessageError(title,message); System.out.println(response); try { JSONObject jObj = new JSONObject(response.toString()); String status = jObj.getString("status"); if (status.equals("ok")) { //String message = jObj.getString("message"); title = "Success"; message = "ok"; alertMessage(title,message); } else { title = "Error"; message = "error"; //alertMessageError(title,message); } } catch (JSONException e) { e.printStackTrace(); } } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError error) { System.out.println(error.getLocalizedMessage()); } }){ @Override public Map<String,String> getHeaders() throws AuthFailureError { String bearer = "bearer ".concat(jwt); Map<String,String> headersSys = super.getHeaders(); Map<String,String> headers = new HashMap<>(); headersSys.remove("Authorization"); headers.put("Accept", "application/json"); headers.put("Authorization", bearer); headers.putAll(headersSys); return headers; } }; RequestQueue requestQueue = Volley.newRequestQueue(getApplicationContext()); requestQueue.add(jsonObjectRequest); }
项目已引入GSON库,请帮忙修改代码,实现正确发送带上述JSON数据的JsonObjectRequest POST请求。
解决方案
方法一:使用GSON序列化实体类(推荐)
这种方式更易维护,避免手动拼接JSON出错。
- 创建对应JSON结构的实体类
public class PackagingReturn { private String date; private String number; private String user; private String report_note; private List<Detail> detail; // 生成getter、setter方法,或用Lombok简化代码 public static class Detail { private String desc; private int usable; private String condition; private String numbering; private String numbering_id; private String code; // 生成getter、setter方法 } }
- 修改请求方法
private void createPackagingReturn() { String url = "some/url"; // 组装数据到实体类 PackagingReturn packagingReturn = new PackagingReturn(); packagingReturn.setDate(date); packagingReturn.setNumber(number); packagingReturn.setUser(name); packagingReturn.setReport_note(report); List<PackagingReturn.Detail> detailList = new ArrayList<>(); // 添加第一个detail数据 PackagingReturn.Detail detail1 = new PackagingReturn.Detail(); detail1.setDesc(""); detail1.setUsable(0); detail1.setCondition("GOOD"); detail1.setNumbering("CRT-0002"); detail1.setNumbering_id("2"); detail1.setCode("F"); detailList.add(detail1); // 添加第二个detail数据 PackagingReturn.Detail detail2 = new PackagingReturn.Detail(); detail2.setDesc(""); detail2.setUsable(0); detail2.setCondition("GOOD"); detail2.setNumbering("CRT-0001"); detail2.setNumbering_id("1"); detail2.setCode("F"); detailList.add(detail2); packagingReturn.setDetail(detailList); // 用GSON将实体类转为JSONObject Gson gson = new Gson(); String jsonString = gson.toJson(packagingReturn); JSONObject requestBody = null; try { requestBody = new JSONObject(jsonString); } catch (JSONException e) { e.printStackTrace(); } // 创建并发送请求 JsonObjectRequest jsonObjectRequest = new JsonObjectRequest(Request.Method.POST, url, requestBody, response -> { try { String status = response.getString("status"); if ("ok".equals(status)) { title = "Success"; message = "ok"; alertMessage(title, message); } else { title = "Error"; message = "error"; alertMessageError(title, message); } } catch (JSONException e) { e.printStackTrace(); title = "Information"; message = response.toString(); alertMessageError(title, message); } System.out.println(response); }, error -> System.out.println(error.getLocalizedMessage()) ){ @Override public Map<String,String> getHeaders() throws AuthFailureError { String bearer = "bearer ".concat(jwt); Map<String,String> headersSys = super.getHeaders(); Map<String,String> headers = new HashMap<>(); headersSys.remove("Authorization"); headers.put("Accept", "application/json"); headers.put("Authorization", bearer); headers.putAll(headersSys); return headers; } }; RequestQueue requestQueue = Volley.newRequestQueue(getApplicationContext()); requestQueue.add(jsonObjectRequest); }
方法二:直接构建JSONObject(快速修改)
如果不想创建实体类,可手动构建包含数组的请求体:
private void createPackagingReturn() { String url = "some/url"; try { // 构建detail数组 JSONArray detailArray = new JSONArray(); JSONObject detail1 = new JSONObject(); detail1.put("desc", ""); detail1.put("usable", 0); detail1.put("condition", "GOOD"); detail1.put("numbering", "CRT-0002"); detail1.put("numbering_id", "2"); detail1.put("code", "F"); detailArray.put(detail1); JSONObject detail2 = new JSONObject(); detail2.put("desc", ""); detail2.put("usable", 0); detail2.put("condition", "GOOD"); detail2.put("numbering", "CRT-0001"); detail2.put("numbering_id", "1"); detail2.put("code", "F"); detailArray.put(detail2); // 构建完整请求体 JSONObject requestBody = new JSONObject(); requestBody.put("date", date); requestBody.put("number", number); requestBody.put("user", name); requestBody.put("report_note", report); requestBody.put("detail", detailArray); // 创建并发送请求 JsonObjectRequest jsonObjectRequest = new JsonObjectRequest(Request.Method.POST, url, requestBody, response -> { try { String status = response.getString("status"); if ("ok".equals(status)) { title = "Success"; message = "ok"; alertMessage(title, message); } else { title = "Error"; message = "error"; alertMessageError(title, message); } } catch (JSONException e) { e.printStackTrace(); title = "Information"; message = response.toString(); alertMessageError(title, message); } System.out.println(response); }, error -> System.out.println(error.getLocalizedMessage()) ){ @Override public Map<String,String> getHeaders() throws AuthFailureError { String bearer = "bearer ".concat(jwt); Map<String,String> headersSys = super.getHeaders(); Map<String,String> headers = new HashMap<>(); headersSys.remove("Authorization"); headers.put("Accept", "application/json"); headers.put("Authorization", bearer); headers.putAll(headersSys); return headers; } }; RequestQueue requestQueue = Volley.newRequestQueue(getApplicationContext()); requestQueue.add(jsonObjectRequest); } catch (JSONException e) { e.printStackTrace(); } }
原代码问题说明
原代码用HashMap<String, String>存储参数时,detail被当作字符串传入,而非JSON数组,导致服务器收到的detail类型不符合预期。上述两种方法均可正确构建包含数组的JSON请求体,解决该问题。
内容的提问来源于stack exchange,提问作者KangIcal
相关产品推荐
相关产品推荐

