HttpClient.execute() 阻塞问题

本文探讨了在Android应用中使用HttpPost与PHP后台交互时遇到的阻塞问题,并提出了解决方案,包括通过新建线程及使用StrictMode来避免主线程网络访问导致的阻塞。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

在实现安卓与PHP后台交互过程中,当安卓利用HttpPost去后台获取数据时,代码执行到下面这句就阻塞了:

<span style="font-size:14px;">httpClient.execute(httpPost);</span>

一开始找到资料说是新开一个线程执行上述语句,于是我便利用如下方式尝试了:

<span style="font-size:14px;">new Thread() {
<span style="white-space:pre">	</span>public void run(){
<span style="white-space:pre">		</span>try {
	<span style="white-space:pre">		</span>HttpResponse response = httpClient.execute(httpPost);
	<span style="white-space:pre">	</span>} catch (Exception e) {
		<span style="white-space:pre">	</span>e.printStackTrace();
	<span style="white-space:pre">	</span>}	
	}
}.start();
				</span>

这个的确可以解决 HttpClient.execute() 的阻塞问题,但是在不同的线程中执行代码时,由于代码执行的时间不一样,这便容易产生数据不一致的问题,比如我现在要登录,一开始输入的帐号密码是正确的,但是点击登录之后没响应。接着我又输了个错误的帐号密码然后登录,结果竟然能登录。


因此后来换用了一个办法,即在安卓主线程或者任何一个其他的子线程中加入以下代码,不用另开线程也能解决 HttpClient.execute 的阻塞问题:

<span style="font-size:14px;">StrictMode.setThreadPolicy(new StrictMode.ThreadPolicy.Builder()
        .detectDiskReads()
        .detectDiskWrites()
        .detectNetwork()
        .penaltyLog()
        .build());
        StrictMode.setVmPolicy(new StrictMode.VmPolicy.Builder()
                .detectLeakedSqlLiteObjects()
                .detectLeakedClosableObjects()
                .penaltyLog()
                .penaltyDeath()
                .build());</span>


貌似在安卓4.0开始,谷歌就已经对“在主线程中直接访问网络”等做法进行了限制,也就是为什么我们没用新线程执行execute语句时会造成阻塞。而我们用上面的StrictMode(严苟模式)正是针对此问题的。

at org.apache.http.impl.io.SessionInputBufferImpl.readLine(SessionInputBufferImpl.java:280) at org.apache.http.impl.conn.DefaultHttpResponseParser.parseHead(DefaultHttpResponseParser.java:138) at org.apache.http.impl.conn.DefaultHttpResponseParser.parseHead(DefaultHttpResponseParser.java:56) at org.apache.http.impl.io.AbstractMessageParser.parse(AbstractMessageParser.java:259) at org.apache.http.impl.DefaultBHttpClientConnection.receiveResponseHeader(DefaultBHttpClientConnection.java:163) at org.apache.http.impl.conn.CPoolProxy.receiveResponseHeader(CPoolProxy.java:157) at org.apache.http.protocol.HttpRequestExecutor.doReceiveResponse(HttpRequestExecutor.java:273) at org.apache.http.protocol.HttpRequestExecutor.execute(HttpRequestExecutor.java:125) at org.apache.http.impl.execchain.MainClientExec.execute(MainClientExec.java:272) at org.apache.http.impl.execchain.ProtocolExec.execute(ProtocolExec.java:186) at org.apache.http.impl.execchain.RetryExec.execute(RetryExec.java:89) at org.apache.http.impl.execchain.RedirectExec.execute(RedirectExec.java:110) at org.apache.http.impl.client.InternalHttpClient.doExecute(InternalHttpClient.java:185) at org.apache.http.impl.client.CloseableHttpClient.execute(CloseableHttpClient.java:83) at org.apache.http.impl.client.CloseableHttpClient.execute(CloseableHttpClient.java:108) at com.pg.common.utils.http.HttpClientUtils.doJsonPost(HttpClientUtils.java:228) at com.pg.common.utils.http.HttpClientUtils.doJsonPost(HttpClientUtils.java:189) at com.pg.modules.alarm.heartbeat.HeartBeatTask.run(HeartBeatTask.java:32) at sun.reflect.GeneratedMethodAccessor83.invoke(Unknown Source) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.lang.reflect.Method.invoke(Method.java:498) at org.springframework.scheduling.support.ScheduledMethodRunnable.run(ScheduledMethodRunnable.java:84) at org.springframework.scheduling.support.DelegatingErrorHandlingRunnable.run(DelegatingErrorHandlingRunnable.java:54) at org.springframework.scheduling.concurrent.ReschedulingRunnable.run(ReschedulingRunnable.java:93) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run(FutureTask.java:266) at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.access$201(ScheduledThreadPoolExecutor.java:180) at java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(ScheduledThreadPoolExecutor.java:293) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:750) 2025-04-27 16:11:40.009 [scheduling-1] ERROR com.pg.modules.alarm.heartbeat.HeartBeatTask - Read timed out
05-13
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值