You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Volley框架中JsonObjectRequest无法获取数据求助

问题分析与解决方案

核心问题排查

你的代码存在几个关键问题,直接导致Volley请求无响应:

  1. Volley与AsyncTask冗余嵌套
    Volley本身是异步网络框架,内部已实现线程调度管理,完全不需要用AsyncTask包裹请求。将Volley请求放在doInBackground中会干扰其正常线程逻辑,导致请求无法执行。

  2. 错误的重试策略配置
    你设置了DefaultRetryPolicy(0, ...),第一个参数是请求超时时间(毫秒),设为0会让请求立即超时,根本无法发起有效网络请求。

  3. ProgressDialog管理混乱
    onResponse和onPostExecute中都有关闭对话框的逻辑,且onPostExecute用Timer强制30秒关闭,会导致请求还在处理时就被强制终止,同时掩盖真实请求状态。

  4. 错误日志信息不足
    onErrorResponse仅打印error.getMessage(),很多Volley错误的详细堆栈信息需要通过VolleyLog.getStackTraceString(error)才能查看,不利于排查问题。


修正后的代码

public class OutputActivity extends AppCompatActivity {
    GridView listView;
    VolleyListViewAdapter adapter;
    private List<CommonBean> volleyList = new ArrayList<>();
    private ProgressDialog mProcessingDialog;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_output);
        listView = findViewById(R.id.ListView);
        adapter = new VolleyListViewAdapter(OutputActivity.this, volleyList);
        listView.setAdapter(adapter);
        // 直接发起Volley请求,无需AsyncTask
        fetchProductList();
    }

    private void fetchProductList() {
        mProcessingDialog = new ProgressDialog(OutputActivity.this);
        mProcessingDialog.setTitle("Please Wait..");
        mProcessingDialog.setMessage("Loading");
        mProcessingDialog.setIndeterminate(false);
        mProcessingDialog.setCancelable(false);
        mProcessingDialog.show();

        String url = "https://api.fnpplus.com/productapi/api/rest/v1.2/productList?catalogId=india";
        JsonObjectRequest jsonObjReq = new JsonObjectRequest(Request.Method.GET,
                url,
                null, // GET请求无需请求体,传null即可
                new Response.Listener<JSONObject>() {
                    @Override
                    public void onResponse(JSONObject response) {
                        Log.d("rlog", response.toString());
                        try {
                            // response本身就是JSONObject,无需重复解析
                            JSONObject dataObj = response.getJSONObject("data");
                            JSONArray productArray = dataObj.getJSONArray("productResults");
                            Log.d("rlog", productArray.toString());

                            volleyList.clear(); // 清空旧数据,避免重复添加
                            for (int i = 0; i < productArray.length(); i++) {
                                JSONObject obj = productArray.getJSONObject(i);
                                CommonBean commonBean = new CommonBean();
                                commonBean.setTextView1(obj.optString("productName"));

                                JSONObject priceObj = obj.getJSONObject("price");
                                Log.d("rlog1", priceObj.toString());
                                commonBean.setTextView2(priceObj.optString("price"));
                                Log.d("rlog12", priceObj.optString("price"));

                                JSONObject imageObj = obj.getJSONObject("productImage");
                                Log.d("rlog1", imageObj.toString());
                                commonBean.setImageView(imageObj.optString("path"));
                                Log.d("rlog12", imageObj.optString("path"));

                                volleyList.add(commonBean);
                            }
                            adapter.notifyDataSetChanged();
                        } catch (Exception e) {
                            e.printStackTrace();
                            Toast.makeText(OutputActivity.this, "数据解析失败", Toast.LENGTH_SHORT).show();
                        } finally {
                            // 无论成功失败都关闭对话框
                            if (mProcessingDialog != null && mProcessingDialog.isShowing()) {
                                mProcessingDialog.dismiss();
                            }
                        }
                    }
                }, new Response.ErrorListener() {
            @Override
            public void onErrorResponse(VolleyError error) {
                // 打印详细错误堆栈
                VolleyLog.d("rlog", "Error: " + VolleyLog.getStackTraceString(error));
                Toast.makeText(OutputActivity.this, "请求失败,请检查网络", Toast.LENGTH_SHORT).show();
                if (mProcessingDialog != null && mProcessingDialog.isShowing()) {
                    mProcessingDialog.dismiss();
                }
            }
        });

        // 设置合理重试策略:5秒超时,最多重试1次
        jsonObjReq.setRetryPolicy(new DefaultRetryPolicy(
                5000,
                DefaultRetryPolicy.DEFAULT_MAX_RETRIES,
                DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));

        RequestQueue requestQueue = Volley.newRequestQueue(OutputActivity.this);
        requestQueue.add(jsonObjReq);
    }
}

额外优化建议

  • 变量命名规范:避免用ListView作为GridView的变量名,改用listView这类符合Java规范的名称,避免混淆。
  • 数据去重:每次请求前清空volleyList,防止多次请求导致数据重复显示。
  • 用户友好提示:在异常处理块添加Toast提示,让用户直观了解错误状态。
  • Volley版本迁移:建议使用官方维护的Volley库(com.android.volley:volley:1.2.1),第三方维护版本可能存在兼容性问题。

内容的提问来源于stack exchange,提问作者Abm

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.11 22:20:29