【问题标题】:Volley JsonObjectRequest Post request not workingVolley JsonObjectRequest Post 请求不起作用
【发布时间】:2013-11-19 05:01:30
【问题描述】:

我正在使用 android Volley 发出请求。所以我使用这个代码。我不明白一件事。我在我的服务器中检查 params 始终为空。我认为 getParams() 不起作用。我应该怎么做才能解决这个问题。

 RequestQueue queue = MyVolley.getRequestQueue();
        JsonObjectRequest jsObjRequest = new JsonObjectRequest(Request.Method.POST,SPHERE_URL,null,
                new Response.Listener<JSONObject>() {
                    @Override
                    public void onResponse(JSONObject response) {
                        System.out.println(response);
                        hideProgressDialog();
                    }
                },
                new Response.ErrorListener() {
                    @Override
                    public void onErrorResponse(VolleyError error) {
                      hideProgressDialog();
                    }
                }) {
            protected Map<String, String> getParams() throws AuthFailureError {
                Map<String, String> params = new HashMap<String, String>();
                params.put("id","1");
                params.put("name", "myname");
                return params;
            };
        };
        queue.add(jsObjRequest);

【问题讨论】:

  • 谢谢你的问题。我也遇到了 JsonObjectRequest 的问题。所以,我只是使用普通的 StringRequest。然后它就起作用了。这似乎是凌空错误。请问你是怎么解决的?
  • 当然可以。你必须创建你的 CustomJsonObjectRequest 就像在这里stackoverflow.com/questions/19837820/…
  • 因为构造函数的第三个参数为空。
  • @njzk2:我认为 pmb 正在尝试发送带有 url 编码参数的 POST 请求,而不是 JSON 正文,这是第三个参数的用途。 LOG_TAG 的答案似乎是最恰当的:一个接受参数并仍然允许 JSON 响应的自定义类。

标签: android android-volley


【解决方案1】:

尝试使用这个帮助类

import java.io.UnsupportedEncodingException;
import java.util.Map;    
import org.json.JSONException;
import org.json.JSONObject;    
import com.android.volley.NetworkResponse;
import com.android.volley.ParseError;
import com.android.volley.Request;
import com.android.volley.Response;
import com.android.volley.Response.ErrorListener;
import com.android.volley.Response.Listener;
import com.android.volley.toolbox.HttpHeaderParser;

public class CustomRequest extends Request<JSONObject> {

    private Listener<JSONObject> listener;
    private Map<String, String> params;

    public CustomRequest(String url, Map<String, String> params,
            Listener<JSONObject> reponseListener, ErrorListener errorListener) {
        super(Method.GET, url, errorListener);
        this.listener = reponseListener;
        this.params = params;
    }

    public CustomRequest(int method, String url, Map<String, String> params,
            Listener<JSONObject> reponseListener, ErrorListener errorListener) {
        super(method, url, errorListener);
        this.listener = reponseListener;
        this.params = params;
    }

    protected Map<String, String> getParams()
            throws com.android.volley.AuthFailureError {
        return params;
    };

    @Override
    protected Response<JSONObject> parseNetworkResponse(NetworkResponse response) {
        try {
            String jsonString = new String(response.data,
                    HttpHeaderParser.parseCharset(response.headers));
            return Response.success(new JSONObject(jsonString),
                    HttpHeaderParser.parseCacheHeaders(response));
        } catch (UnsupportedEncodingException e) {
            return Response.error(new ParseError(e));
        } catch (JSONException je) {
            return Response.error(new ParseError(je));
        }
    }

    @Override
    protected void deliverResponse(JSONObject response) {
        // TODO Auto-generated method stub
        listener.onResponse(response);
    }
}

在活动/片段中使用这个

RequestQueue requestQueue = Volley.newRequestQueue(getActivity());
CustomRequest jsObjRequest = new CustomRequest(Method.POST, url, params, this.createRequestSuccessListener(), this.createRequestErrorListener());

requestQueue.add(jsObjRequest);

【讨论】:

  • 谢谢它的工作原理!为什么在 JsonObjectRequest 中覆盖 getParams() 不起作用?是 Volley 错误吗?
  • 这不是错误,getParams() 不会调用,因为 JsonObjectRequest 扩展了 JsonRequest,它直接调用 getBody() 将构造函数的第二个参数(调用 requestBody)编码为 contentType,这就是它的原因忽略你的 getParam() 方法。
  • @LOG_TAG this.createRequestSuccessListener(), this.createRequestErrorListener());没看懂,请解释一下。
  • @Droider 这些是创建正确响应处理对象的方法。出于可读性的目的,它们很可能被制作成单独的方法。您也可以使用 new 关键字就地创建对象,但根据这些对象的代码大小,可能难以一目了然。
  • 我遇到了很多问题,这很好用:D 谢谢
【解决方案2】:

您可以创建自定义JSONObjectReuqest 并覆盖getParams 方法,或者您可以在构造函数中将它们作为JSONObject 提供以放入请求正文中。

像这样(我编辑了你的代码):

JSONObject obj = new JSONObject();
obj.put("id", "1");
obj.put("name", "myname");

RequestQueue queue = MyVolley.getRequestQueue();
JsonObjectRequest jsObjRequest = new JsonObjectRequest(Request.Method.POST,SPHERE_URL,obj,
    new Response.Listener<JSONObject>() {
        @Override
        public void onResponse(JSONObject response) {
             System.out.println(response);
             hideProgressDialog();
        }
    },
    new Response.ErrorListener() {
        @Override
        public void onErrorResponse(VolleyError error) {
             hideProgressDialog();
        }
    });
queue.add(jsObjRequest);

【讨论】:

  • 又好又快!但是如果你需要 x-www-urlencoded 是由 volley 完成的吗?
  • 我不确定,但您可以轻松测试它。
  • 您确定不会调用 getParams 吗?相反,代码显示它是由 getBody() 和 getPostParams() 调用的,而您在这里说自己相反:stackoverflow.com/questions/18484647/…
  • 你说得对,我在这些方法之间搞混了(睡眠不足)。我编辑了我的答案。
  • 尝试使用 POST 和 GET 方法。两者都不起作用。我想不通。
【解决方案3】:

对我来说很简单!几周前我收到了:

这用于getBody() 方法,而不是getParams() 用于发布请求。

这是我的:

    @Override
/**
 * Returns the raw POST or PUT body to be sent.
 *
 * @throws AuthFailureError in the event of auth failure
 */
public byte[] getBody() throws AuthFailureError {
    //        Map<String, String> params = getParams();
    Map<String, String> params = new HashMap<String, String>();
    params.put("id","1");
    params.put("name", "myname");
    if (params != null && params.size() > 0) {
        return encodeParameters(params, getParamsEncoding());
    }
    return null;

}

(我假设您想发布您在 getParams 中编写的参数)

我在构造函数中为请求提供了参数,但是由于您正在动态创建请求,因此您可以在 getBody() 方法的覆盖中对它们进行硬编码。

这就是我的代码的样子:

    Bundle param = new Bundle();
    param.putString(HttpUtils.HTTP_CALL_TAG_KEY, tag);
    param.putString(HttpUtils.HTTP_CALL_PATH_KEY, url);
    param.putString(HttpUtils.HTTP_CALL_PARAM_KEY, params);

    switch (type) {
    case RequestType.POST:
        param.putInt(HttpUtils.HTTP_CALL_TYPE_KEY, RequestType.POST);
        SCMainActivity.mRequestQueue.add(new SCRequestPOST(Method.POST, url, this, tag, receiver, params));

如果你想要更多,最后一个字符串 params 来自:

param = JsonUtils.XWWWUrlEncoder.encode(new JSONObject(paramasJObj)).toString();

paramasJObj 是这样的:{"id"="1","name"="myname"} 通常的 JSON 字符串。

【讨论】:

  • 我不明白如何在这里传递参数。字符串 s = 新字符串(参数)。这是什么?
  • 它只是一个带有我的参数的字符串。我在构造函数中发送它。我再给你看一些。
  • 感谢@poutrathor,如果您能告诉我如何在 getParams() 方法中发送该参数。
  • 啊。因此,您想将它们用作参数。出于好奇,您会向服务器发布什么内容?
  • 我的目标是我必须像在getParams中写的那样发送参数,我不能发送jsonObject。
【解决方案4】:

当您使用 JsonObject 请求时,您需要在初始化中传递链接后立即传递参数,看看这段代码:

        HashMap<String, String> params = new HashMap<>();
        params.put("user", "something" );
        params.put("some_params", "something" );

    JsonObjectRequest request = new JsonObjectRequest(Request.Method.POST, "request_URL", new JSONObject(params), new Response.Listener<JSONObject>() {
        @Override
        public void onResponse(JSONObject response) {

           // Some code 

        }
    }, new Response.ErrorListener() {
        @Override
        public void onErrorResponse(VolleyError error) {
            //handle errors
        }
    });


}

【讨论】:

    【解决方案5】:

    您需要做的就是覆盖 Request 类中的 getParams 方法。我遇到了同样的问题,我搜索了答案,但找不到合适的答案。问题与获取请求不同,服务器重定向的发布参数可能会被丢弃。例如,阅读this。所以,不要冒险让您的请求被网络服务器重定向。如果您的目标是 http://example/myapp ,请提及您的服务的确切地址,即 http://example.com/myapp/index.php
    Volley 还可以,而且效果很好,问题出在其他地方。

    【讨论】:

      【解决方案6】:

      覆盖函数 getParams 工作正常。您使用 POST 方法并将 jBody 设置为空。这就是为什么它不起作用。如果要发送空 jBody,可以使用 GET 方法。 我已经覆盖了 getParams 方法,它可以与 GET 方法(和 null jBody)一起使用,也可以与 POST 方法(和 jBody != null)一起使用

      还有所有的例子here

      【讨论】:

        【解决方案7】:

        我曾经遇到过同样的问题,空的 POST 数组是由于请求的重定向(在您的服务器端)引起的,请修复 URL,使其在到达服务器时不必重定向。例如,如果使用服务器端应用程序上的 .htaccess 文件强制使用 https,请确保您的客户端请求具有“https://”前缀。通常当重定向发生时,POST 数组会丢失。我希望这会有所帮助!

        【讨论】:

          【解决方案8】:

          可以尝试使用 Volley Json Request and Response ith Java Code 进行调用。

          public void callLogin(String sMethodToCall, String sUserId, String sPass) {
                  RequestQueue requestQueue = Volley.newRequestQueue(getApplicationContext());
          
                  JsonObjectRequest jsonObjectRequest = new JsonObjectRequest(
                          Request.Method.POST, ConstantValues.ROOT_URL_LOCAL + sMethodToCall.toString().trim(), addJsonParams(sUserId, sPass),
          //                JsonObjectRequest jsonObjectRequest = new JsonObjectRequest(Request.Method.POST, url, object,
                          new Response.Listener<JSONObject>() {
                              @Override
                              public void onResponse(JSONObject response) {
                                  Log.d("onResponse", response.toString());
                                  Toast.makeText(VolleyMethods.this, response.toString(), Toast.LENGTH_LONG).show(); // Test
          
                                  parseResponse(response);
          //                        msgResponse.setText(response.toString());
          //                        hideProgressDialog();
                              }
                          },
                          new Response.ErrorListener() {
          
                              @Override
                              public void onErrorResponse(VolleyError error) {
                                  VolleyLog.d("onErrorResponse", "Error: " + error.getMessage());
                                  Toast.makeText(VolleyMethods.this, error.toString(), Toast.LENGTH_LONG).show();
          //                hideProgressDialog();
                              }
                          }) {
          
                      /**
                       * Passing some request headers
                       */
                      @Override
                      public Map<String, String> getHeaders() throws AuthFailureError {
                          HashMap<String, String> headers = new HashMap<String, String>();
                          headers.put("Content-Type", "application/json; charset=utf-8");
                          return headers;
                      }
          
          
                  };
          
                  requestQueue.add(jsonObjectRequest);
              }
          
              public JSONObject addJsonParams(String sUserId, String sPass) {
                  JSONObject jsonobject = new JSONObject();
                  try {
          //            {"id":,"login":"secretary","password":"password"}
          
                      ///***//
                      Log.d("addJsonParams", "addJsonParams");
          
          //            JSONObject jsonobject = new JSONObject();
          
          //            JSONObject jsonobject_one = new JSONObject();
          //
          //            jsonobject_one.put("type", "event_and_offer");
          //            jsonobject_one.put("devicetype", "I");
          //
          //            JSONObject jsonobject_TWO = new JSONObject();
          //            jsonobject_TWO.put("value", "event");
          //            JSONObject jsonobject = new JSONObject();
          //
          //            jsonobject.put("requestinfo", jsonobject_TWO);
          //            jsonobject.put("request", jsonobject_one);
          
                      jsonobject.put("id", "");
                      jsonobject.put("login", sUserId); // sUserId
                      jsonobject.put("password", sPass); // sPass
          
          
          //            js.put("data", jsonobject.toString());
          
                  } catch (JSONException e) {
                      e.printStackTrace();
                  }
          
                  return jsonobject;
              }
          
              public void parseResponse(JSONObject response) {
          
                  Boolean bIsSuccess = false; // Write according to your logic this is demo.
                  try {
                      JSONObject jObject = new JSONObject(String.valueOf(response));
                      bIsSuccess = jObject.getBoolean("success");
          
          
                  } catch (JSONException e) {
                      e.printStackTrace();
                      Toast.makeText(VolleyMethods.this, "" + e.toString(), Toast.LENGTH_LONG).show(); // Test
                  }
          
              }
          

          【讨论】:

            【解决方案9】:



            构建gradle(应用程序)
            dependencies {
                implementation fileTree(dir: "libs", include: ["*.jar"])
                implementation "org.jetbrains.kotlin:kotlin-stdlib:$kotlin_version"
                implementation 'androidx.core:core-ktx:1.1.0'
                implementation 'androidx.appcompat:appcompat:1.1.0-alpha01'
                implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
                testImplementation 'junit:junit:4.12'
                androidTestImplementation 'androidx.test.ext:junit:1.1.1'
                androidTestImplementation 'androidx.test.espresso:espresso-core:3.2.0'
                implementation 'com.android.volley:volley:1.1.1'
            }
            

            安卓清单
            <uses-permission android:name="android.permission.INTERNET" />
            <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
            

            主活动
            当您使用 JsonObjectRequest 时,必须发送 jsonobject 并接收 jsonobject,否则您将收到错误,因为它只接受 jsonobject。
            import com.android.volley.Request
            import com.android.volley.Response
            import com.android.volley.toolbox.JsonObjectRequest
            import com.android.volley.toolbox.Volley
            
            fun peticion(){
                val jsonObject = JSONObject()
                jsonObject.put("user", "jairo")
                jsonObject.put("password", "1234")
                val queue = Volley.newRequestQueue(this)
                val url = "http://192.168.0.3/get_user.php"
                // GET: JsonObjectRequest( url, null,
                // POST: JsonObjectRequest( url, jsonObject,
                val jsonObjectRequest = JsonObjectRequest( url, jsonObject,
                    Response.Listener { response ->
                        // Check if the object 'msm' does not exist
                        if(response.isNull("msm")){
                            println("Name: "+response.getString("nombre1"))
                        }
                        else{
                            // If the object 'msm' exists we print it
                            println("msm: "+response.getString("msm"))
                        }
                    },
                    Response.ErrorListener { error ->
                        error.printStackTrace()
                        println(error.toString())
                    }
                )
                queue.add(jsonObjectRequest)
            }
            

            文件 php get_user.php
            <?php
                header("Access-Control-Allow-Origin: *");
                header("Access-Control-Allow-Headers: *");
                // we receive the parameters
                $json = file_get_contents('php://input');
                $params = json_decode($json);
                error_reporting(0);
                require_once 'conexion.php';
            
                $mysqli=getConex();
                $user=$params->user;
                $password=$params->password;
                $res=array();
                $verifica_usuario=mysqli_query($mysqli,"SELECT * FROM usuarios WHERE usuario='$user' and clave='$password'");
                if(mysqli_num_rows($verifica_usuario)>0){
                    $query="SELECT * FROM usuarios WHERE usuario='$user'";
                    $result=$mysqli->query($query);
                    while($row = $result->fetch_array(MYSQLI_ASSOC)){
                        $res=$row;
                    }
                }
                else{
                    $res=array('msm'=>"Incorrect user or password");
                }
                $jsonstring = json_encode($res);
                header('Content-Type: application/json');
                echo $jsonstring;
            ?>
            

            文件 php 连接
            <?php
                function getConex(){
                    $servidor="localhost";
                    $usuario="root";
                    $pass="";  
                    $base="db";
                    
                    $mysqli = mysqli_connect($servidor,$usuario,$pass,$base);
                    if (mysqli_connect_errno($mysqli)){
                        echo "Fallo al conectar a MySQL: " . mysqli_connect_error();
                    }
                    $mysqli->set_charset('utf8');
                    return $mysqli;
                }
            ?>
            

            【讨论】:

            • 你能解释一下这段代码吗?目前还不清楚这是如何解决问题的。
            猜你喜欢
            • 2019-01-26
            • 2021-08-31
            • 2015-06-09
            • 1970-01-01
            • 2015-08-10
            • 2015-07-03
            • 1970-01-01
            • 2021-06-21
            相关资源
            最近更新 更多