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

Android应用向PHP服务器发送JSON数据失败求助

问题分析与解决方案

看起来你遇到的情况确实有点挠头——Android端明明返回了HTTP_OK,但PHP服务器就是没接收到JSON数据。我帮你梳理下两端代码里的问题点,以及对应的修复方案:

一、Android端代码的问题与修复

你的Android代码里有几个细节处理不当,可能导致数据没有正确发送到服务器:

  1. 数据流操作顺序错误
    你在写入数据到bufferedWriter之前,先调用了outputStream.flush();,这时候输出流是空的,flush没有意义,反而可能干扰后续数据的提交。正确顺序应该是先写入数据,再刷新缓冲。

  2. 内容长度计算未指定编码
    setFixedLengthStreamingMode使用params[1].getBytes().length时,默认会采用平台编码(不一定是UTF-8),但你请求头指定的是Content-Type: application/json,这会导致长度计算不匹配,服务器可能截断或无法识别数据。

  3. 资源未正确回收
    当前关闭流的逻辑放在响应码判断之后,如果提前return(比如收到HTTP_OK就返回true),流和连接都不会被关闭,既可能造成资源泄漏,也可能影响数据的完整发送。

修改后的Android代码:

@Override
protected Boolean doInBackground(String... params) {
    HttpURLConnection httpURLConnection = null;
    OutputStream outputStream = null;
    BufferedWriter bufferedWriter = null;
    try {
        URL url = new URL(params[0]);
        httpURLConnection = (HttpURLConnection) url.openConnection();
        httpURLConnection.setDoInput(true);
        httpURLConnection.setDoOutput(true);
        httpURLConnection.setRequestMethod("POST");
        
        // 指定UTF-8编码计算内容长度,和请求头保持一致
        byte[] postData = params[1].getBytes("UTF-8");
        httpURLConnection.setFixedLengthStreamingMode(postData.length);
        httpURLConnection.setRequestProperty("Content-Type", "application/json; charset=UTF-8");
        httpURLConnection.connect();

        outputStream = new BufferedOutputStream(httpURLConnection.getOutputStream());
        bufferedWriter = new BufferedWriter(new OutputStreamWriter(outputStream, "UTF-8"));
        
        // 先写入数据,再依次刷新缓冲和输出流
        bufferedWriter.write(params[1]);
        bufferedWriter.flush();
        outputStream.flush();

        int httpResponse = httpURLConnection.getResponseCode();
        Log.d("TAG", "Response Code: " + httpResponse);
        if (httpResponse == HttpURLConnection.HTTP_OK || httpResponse == HttpURLConnection.HTTP_ACCEPTED) {
            Log.d("TAG", "Data sent successfully");
            return true;
        } else {
            Log.d("TAG", "Unexpected response code: " + httpResponse);
            return false;
        }
    } catch (IOException e) {
        e.printStackTrace();
        return false;
    } finally {
        // 在finally块中确保所有资源被关闭,避免泄漏
        try {
            if (bufferedWriter != null) bufferedWriter.close();
            if (outputStream != null) outputStream.close();
            if (httpURLConnection != null) httpURLConnection.disconnect();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

另外,生成JSON数组的代码还有个隐藏bug:你在循环里重复使用同一个JSONObject对象,会导致所有数组元素都是最后一条记录的数据。把对象创建放到循环内部即可:

JSONArray jsonArray = new JSONArray();
for (Record record : list) {
    try {
        // 每次循环创建新的JSONObject,避免数据覆盖
        JSONObject jsonObject = new JSONObject();
        jsonObject.put("firstName", record.getFirstName());
        jsonObject.put("lastName", record.getLastName());
        jsonObject.put("age", String.valueOf(record.getAge()));
        jsonObject.put("sex", record.getSex());
        jsonObject.put("comment", record.getComment());
        jsonArray.put(jsonObject);
    } catch (JSONException e) {
        e.printStackTrace();
    }
}

二、PHP端代码的问题与修复

即使数据正确发送,你的PHP脚本也可能因为以下问题无法处理:

  1. 缺少JSON解析错误处理
    如果file_get_contents('php://input')读取失败,或者JSON格式错误,json_decode会返回null,但你的代码直接跳过逻辑,没有任何错误提示,根本不知道问题出在哪。

  2. SQL语句存在语法错误与注入风险
    字符串类型的字段(比如firstName、lastName)没有用单引号包裹,会直接导致SQL语法错误;同时直接拼接用户输入到SQL里,存在严重的SQL注入风险。

  3. 缺少调试信息
    没有打印接收到的原始数据,无法确认服务器是否真的收到了JSON。

修改后的PHP代码:

<?php
echo "PHP script started<br>";
// 打印接收到的原始数据,方便调试
$jsonInput = file_get_contents('php://input');
echo "Received input: " . $jsonInput . "<br>";

// 检查JSON解析是否成功
$objs = json_decode($jsonInput);
if (json_last_error() !== JSON_ERROR_NONE) {
    echo "JSON parse error: " . json_last_error_msg() . "<br>";
    exit;
}

// 确认解析结果是数组
if (is_array($objs)) {
    $servername = "localhost";
    $username = "root";
    $password = "";
    $dbname = "Synch";

    // 创建数据库连接
    $conn = new mysqli($servername, $username, $password, $dbname);
    if ($conn->connect_error) {
        die("Connection failed: " . $conn->connect_error);
    }

    // 使用预处理语句防止SQL注入,同时解决字符串字段的语法问题
    $sql = "INSERT INTO Synchdata (firstName, lastName, age, sex, comment) VALUES (?, ?, ?, ?, ?)";
    $stmt = $conn->prepare($sql);
    if (!$stmt) {
        echo "Prepare statement error: " . $conn->error . "<br>";
        $conn->close();
        exit;
    }

    // 绑定参数(s表示字符串,若age是整数类型可改为i)
    $stmt->bind_param("sssss", $firstName, $lastName, $age, $sex, $comment);

    foreach ($objs as $obj) {
        $firstName = $obj->firstName;
        $lastName = $obj->lastName;
        $age = $obj->age;
        $sex = $obj->sex;
        $comment = $obj->comment;

        echo "Processing record: " . $firstName . " " . $lastName . "<br>";

        if ($stmt->execute()) {
            echo "New record created successfully<br>";
        } else {
            echo "Error: " . $stmt->error . "<br>";
        }
    }

    $stmt->close();
    $conn->close();
} else {
    echo "Invalid JSON format: expected an array<br>";
}
?>

三、调试小技巧

  1. 直接访问PHP脚本的URL,确认能输出PHP script started,验证服务器配置正常。
  2. 发送请求后查看PHP页面的输出,确认Received input是否显示了你发送的JSON数据。
  3. 查看Android端Logcat的日志,确认响应码和数据发送的流程是否正常。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.15 08:03:43