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

特定设备蜂窝网络下POST JSON至EC2实例超时问题求助

排查部分设备蜂窝网络下无法发送JSON的问题

以下Kotlin代码在WiFi及多数设备蜂窝网络环境下可正常向EC2实例发送JSON,但部分设备使用蜂窝网络时完全无法发送数据,无错误码返回,仅在重连WiFi时出现超时;受影响用户每次生成的相似JSON对象,在蜂窝网络下均发送失败。

private suspend fun sendJsonFile(file: File) {
    val url = URL(EC2_URL)
    val urlConnection = url.openConnection() as HttpURLConnection
    try {
        sendJsonFileLog = "Preparing to send file: ${file.name}"
        // Set timeouts for connection and read operations
        urlConnection.connectTimeout = 50000
        urlConnection.readTimeout = 100000
        urlConnection.requestMethod = "POST"
        urlConnection.setRequestProperty("Content-Type", "application/json")
        urlConnection.setRequestProperty("Content-Encoding", "gzip")
        urlConnection.doOutput = true

        // Read file and compress JSON data
        val jsonInputString = file.readText()
        val byteArrayOutputStream = ByteArrayOutputStream()
        GZIPOutputStream(byteArrayOutputStream).use { gzipOutputStream ->
            gzipOutputStream.write(jsonInputString.toByteArray())
        }
        val compressedData = byteArrayOutputStream.toByteArray()
        sendJsonFileLog = "JSON data compressed"

        // Send compressed JSON data
        urlConnection.outputStream.use { os ->
            os.write(compressedData)
            os.flush()
        }
        sendJsonFileLog = "Compressed data sent"

        // Handle HTTP response codes
        val responseCode = urlConnection.responseCode
        sendJsonFileLog += " - Response code: $responseCode"
        if (responseCode == HttpURLConnection.HTTP_OK) {
            file.delete()
            sendJsonFileLog += " - File deleted."
            updateList()
        } else {
            handleHttpError(responseCode, urlConnection.responseMessage)
        }
    } catch (e: IOException) {
        sendJsonFileLog = "Network error: ${e.localizedMessage}"
        handleNetworkError(e)
    } catch (e: Exception) {
        sendJsonFileLog = "Unexpected error: ${e.localizedMessage}"
        handleUnexpectedError(e)
    } finally {
        urlConnection.disconnect()
        sendJsonFileLog += " - Connection closed."
    }
}

可能的原因及排查步骤

  • 运营商蜂窝网络的APN/代理限制
    部分运营商的蜂窝网络会拦截特定格式的HTTP请求,比如对Content-Encoding: gzip的POST请求有过滤,或者APN设置中默认启用了代理导致请求被吞。可以让用户:

    • 检查设备APN设置,切换为运营商默认APN,关闭手动代理
    • 尝试切换4G/5G网络模式,测试是否能发送成功
  • 超时设置未覆盖蜂窝网络的慢连接场景
    当前connectTimeout=50000ms、readTimeout=100000ms,但部分蜂窝网络建立连接或传输数据的时间更长,导致请求卡在建立连接阶段,未触发超时逻辑。建议临时调大超时时间(比如connectTimeout=60000ms、readTimeout=120000ms),观察是否会出现明确的超时错误,而非无响应。

  • Gzip压缩的兼容性问题
    代码中使用GZIP压缩JSON,但部分蜂窝网络的中间网关可能无法正确解析压缩后的数据流,直接丢弃请求。可以临时注释掉压缩逻辑,直接发送未压缩的JSON:

    // 注释压缩相关代码,直接发送原JSON
    val compressedData = jsonInputString.toByteArray()
    sendJsonFileLog = "Using uncompressed JSON data"
    

    如果发送成功,说明是压缩相关的问题,可能需要调整压缩方式(比如确保GZIP流正确关闭,或添加Content-Length头)。

  • HttpURLConnection的兼容性缺陷
    Android系统的HttpURLConnection在部分设备和网络环境下存在兼容性问题,比如无法正确处理蜂窝网络下的TCP连接复用、分块编码等。建议替换为OkHttp库,它对各种网络环境的兼容性更好:

    // 示例:用OkHttp实现发送压缩JSON
    private suspend fun sendJsonFileWithOkHttp(file: File) {
        val client = OkHttpClient.Builder()
            .connectTimeout(60, TimeUnit.SECONDS)
            .readTimeout(120, TimeUnit.SECONDS)
            .build()
    
        val jsonInputString = file.readText()
        val compressedData = ByteArrayOutputStream().use { baos ->
            GZIPOutputStream(baos).use { it.write(jsonInputString.toByteArray()) }
            baos.toByteArray()
        }
    
        val request = Request.Builder()
            .url(EC2_URL)
            .post(RequestBody.create(MediaType.parse("application/json"), compressedData))
            .header("Content-Encoding", "gzip")
            .build()
    
        try {
            client.newCall(request).execute().use { response ->
                sendJsonFileLog = "Response code: ${response.code()}"
                if (response.isSuccessful) {
                    file.delete()
                    sendJsonFileLog += " - File deleted."
                    updateList()
                } else {
                    handleHttpError(response.code(), response.message())
                }
            }
        } catch (e: IOException) {
            sendJsonFileLog = "Network error: ${e.localizedMessage}"
            handleNetworkError(e)
        }
    }
    
  • JSON内容的特殊性触发拦截
    用户每次生成的相似JSON可能包含特定关键词、特殊字符或大小刚好触发运营商的安全策略拦截。可以尝试修改JSON内容(比如简化内容、替换敏感字符),测试是否能发送成功;如果能,说明是内容本身的问题,需要调整JSON结构或内容。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.24 11:41:22