【问题标题】:How to send a POST request using volley with string body?如何使用带有字符串正文的 volley 发送 POST 请求?
【发布时间】:2021-05-19 17:46:54
【问题描述】:

我正在开发一个与我编写的 RESTful Web 服务通信的 Android 应用程序。将Volley 用于GET 方法非常棒且简单,但我无法将手指放在POST 方法上。

我想发送一个POST 请求,请求正文中包含String,并检索Web 服务的原始响应(如200 ok500 server error)。

我能找到的只是StringRequest,它不允许发送数据(正文),而且它还限制我接收解析的String 响应。 我还遇到了JsonObjectRequest,它接受数据(正文)但检索已解析的JSONObject 响应。

我决定编写自己的实现,但我找不到从 Web 服务接收原始响应的方法。我该怎么做?

【问题讨论】:

    标签: android web-services rest android-volley


    【解决方案1】:

    你可以参考下面的代码(当然你可以自定义获取更多的网络响应细节):

    try {
        RequestQueue requestQueue = Volley.newRequestQueue(this);
        String URL = "http://...";
        JSONObject jsonBody = new JSONObject();
        jsonBody.put("Title", "Android Volley Demo");
        jsonBody.put("Author", "BNK");
        final String requestBody = jsonBody.toString();
    
        StringRequest stringRequest = new StringRequest(Request.Method.POST, URL, new Response.Listener<String>() {
            @Override
            public void onResponse(String response) {
                Log.i("VOLLEY", response);
            }
        }, new Response.ErrorListener() {
            @Override
            public void onErrorResponse(VolleyError error) {
                Log.e("VOLLEY", error.toString());
            }
        }) {
            @Override
            public String getBodyContentType() {
                return "application/json; charset=utf-8";
            }
    
            @Override
            public byte[] getBody() throws AuthFailureError {
                try {
                    return requestBody == null ? null : requestBody.getBytes("utf-8");
                } catch (UnsupportedEncodingException uee) {
                    VolleyLog.wtf("Unsupported Encoding while trying to get the bytes of %s using %s", requestBody, "utf-8");
                    return null;
                }
            }
    
            @Override
            protected Response<String> parseNetworkResponse(NetworkResponse response) {
                String responseString = "";
                if (response != null) {
                    responseString = String.valueOf(response.statusCode);
                    // can get more details such as response.headers
                }
                return Response.success(responseString, HttpHeaderParser.parseCacheHeaders(response));
            }
        };
    
        requestQueue.add(stringRequest);
    } catch (JSONException e) {
        e.printStackTrace();
    }
    

    【讨论】:

    • 对我来说效果很好。很棒的分享!
    • 它有效,但必须删除 bodyContentType 和 parseNetworkResponse 方法
    • @kondal, parseNetworkResponse 用于 OP 的要求 (and retrieve the raw response of the web service)
    • @user31231234124 是的,正如我在上面评论的那样,这是 OP 的第二个要求 :)
    • 要在 PHP 脚本中访问 POSTed 数据,您可以使用:$raw_data = file_get_contents("php://input"); $json_data = json_decode($raw_data); $title = $json_data-&gt;Title; $author = $json_data-&gt;Author;
    【解决方案2】:

    我喜欢this 之一,但它是问题中要求的sending JSON not string,在此处重新发布代码,以防原来的 github 被删除或更改,并且发现这个对某人有用。

    public static void postNewComment(Context context,final UserAccount userAccount,final String comment,final int blogId,final int postId){
        mPostCommentResponse.requestStarted();
        RequestQueue queue = Volley.newRequestQueue(context);
        StringRequest sr = new StringRequest(Request.Method.POST,"http://api.someservice.com/post/comment", new Response.Listener<String>() {
            @Override
            public void onResponse(String response) {
                mPostCommentResponse.requestCompleted();
            }
        }, new Response.ErrorListener() {
            @Override
            public void onErrorResponse(VolleyError error) {
                mPostCommentResponse.requestEndedWithError(error);
            }
        }){
            @Override
            protected Map<String,String> getParams(){
                Map<String,String> params = new HashMap<String, String>();
                params.put("user",userAccount.getUsername());
                params.put("pass",userAccount.getPassword());
                params.put("comment", Uri.encode(comment));
                params.put("comment_post_ID",String.valueOf(postId));
                params.put("blogId",String.valueOf(blogId));
    
                return params;
            }
    
            @Override
            public Map<String, String> getHeaders() throws AuthFailureError {
                Map<String,String> params = new HashMap<String, String>();
                params.put("Content-Type","application/x-www-form-urlencoded");
                return params;
            }
        };
        queue.add(sr);
    }
    
    public interface PostCommentResponseListener {
        public void requestStarted();
        public void requestCompleted();
        public void requestEndedWithError(VolleyError error);
    }
    

    【讨论】:

    • 什么是“mPostCommentResponse”?
    • @ParthaChakraborty mPostCommentResponse 自定义回调,用于将响应返回到活动或片段。
    • 如果是发送json,为什么设置application/x-www-form-urlencoded
    • 我看了一段关于这段代码的视频。建议你也看看。 www.youtube.com/watch?v=_Ziyi4RkcNE
    【解决方案3】:
    Name = editTextName.getText().toString().trim();
    Email = editTextEmail.getText().toString().trim();
    Phone = editTextMobile.getText().toString().trim();
    
    
    JSONArray jsonArray = new JSONArray();
    jsonArray.put(Name);
    jsonArray.put(Email);
    jsonArray.put(Phone);
    final String mRequestBody = jsonArray.toString();
    
    StringRequest stringRequest = new StringRequest(Request.Method.PUT, OTP_Url, new Response.Listener<String>() {
        @Override
        public void onResponse(String response) {
            Log.v("LOG_VOLLEY", response);
    
        }
    }, new Response.ErrorListener() {
        @Override
        public void onErrorResponse(VolleyError error) {
            Log.e("LOG_VOLLEY", error.toString());
        }
    }) {
        @Override
        public String getBodyContentType() {
            return "application/json; charset=utf-8";
        }
    
        @Override
        public byte[] getBody() throws AuthFailureError {
            try {
                return mRequestBody == null ? null : mRequestBody.getBytes("utf-8");
            } catch (UnsupportedEncodingException uee) {
                VolleyLog.wtf("Unsupported Encoding while trying to get the bytes of %s using %s", mRequestBody, "utf-8");
                return null;
            }
        }
    
    };
    stringRequest.setShouldCache(false);
    VollySupport.getmInstance(RegisterActivity.this).addToRequestque(stringRequest);
    

    【讨论】:

    • 这是一个很长的答案,应该附有详细的解释。这是做什么的?
    • @Sanjeev Pal,非常感谢,很好的答案,它非常适合 Http setEntity 替换
    【解决方案4】:
    StringRequest stringRequest = new StringRequest(Request.Method.POST, URL, new Response.Listener<String>() {
            @Override
            public void onResponse(String response) {
                Log.e("Rest response",response);
            }
        }, new Response.ErrorListener() {
            @Override
            public void onErrorResponse(VolleyError error) {
                Log.e("Rest response",error.toString());
            }
        }){
            @Override
            protected Map<String,String> getParams(){
                Map<String,String> params = new HashMap<String,String>();
                params.put("name","xyz");
                return params;
            }
    
            @Override
            public Map<String,String> getHeaders() throws AuthFailureError {
                Map<String,String> params = new HashMap<String,String>();
                params.put("content-type","application/fesf");
                return params;
            }
    
        };
    
        requestQueue.add(stringRequest);
    

    【讨论】:

      【解决方案5】:

      我为 Volley Request 创建了一个函数。你只需要传递参数:

      public void callvolly(final String username, final String password){
          RequestQueue MyRequestQueue = Volley.newRequestQueue(this);
          String url = "http://your_url.com/abc.php"; // <----enter your post url here
          StringRequest MyStringRequest = new StringRequest(Request.Method.POST, url, new Response.Listener<String>() {
              @Override
              public void onResponse(String response) {
                  //This code is executed if the server responds, whether or not the response contains data.
                  //The String 'response' contains the server's response.
              }
          }, new Response.ErrorListener() { //Create an error listener to handle errors appropriately.
              @Override
              public void onErrorResponse(VolleyError error) {
                  //This code is executed if there is an error.
              }
          }) {
              protected Map<String, String> getParams() {
                  Map<String, String> MyData = new HashMap<String, String>();
                  MyData.put("username", username);             
                  MyData.put("password", password);                
                  return MyData;
              }
          };
      
      
          MyRequestQueue.add(MyStringRequest);
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-06-06
        • 1970-01-01
        • 1970-01-01
        • 2013-08-05
        相关资源
        最近更新 更多