httpClient訪問網路,httpclient.execute(httpGet)方法不執行問題
阿新 • • 發佈:2019-01-23
最近在維護專案過程中遇到了一個比較奇葩的問題,軟體在別的手機上都是OK的,就是在HTC手機上的時候,會遇到軟體沒有完全退出,然後再次點選軟體,進不去的問題
首先說一下這個Bug產生的原因,因為每次 我們軟體進入的時候都去請求GuidePage,看看是否需要升級,如果需要升級的話就要去請求引導介面,然後設定給Viewpager。那麼
問題就產生在請求網路的時候,Bug復現;1,如果系統完全退出,就是在點選退出應用的時候呼叫System.exit(0)這個方法的時候,第二次進入軟體的時候是沒有問題的;問題在
於,沒有完全退出應用,適當的保留一些服務的時候,再次進入就會進不去。根據log日誌,分析出問題產生的原因就是在訪問引導介面介面的時候,httpclient的execute方法沒有
執行,觀察自己封裝的訪問網路框架,發現連結都已經釋放,httpclient也釋放了,還是沒能解決問題。最後確定問題在於訪問網路的執行緒阻塞了。長時間不能相應。設定的連結超
時當然也是沒有用的。下面就來說一下我的解決方案吧
在執行execute方法的時候,另外開啟一個執行緒去執行,然後捕獲異常,判斷執行緒是否阻塞,然後讓執行緒沉睡2秒鐘,呼叫thread.interrupt();打斷狀態,這樣就能解決這個bug了public static String sendGetCommand(Context context, String url, String retDataType) { String result = null; url = url.replaceAll(" ", "%20"); try { httpRequest = new HttpGet(url); // if(url.toLowerCase().startsWith("https")) { if (httpClient == null) { httpClient = HttpsSSLSocketFactory.createMyHttpClient( CONNECT_TIMEOUT, SO_TIMEOUT); } } /* * else { HttpParams httpParameters = new BasicHttpParams(); // Set * the timeout in milliseconds until a connection is established. // * The default value is zero, that means the timeout is not used. * HttpConnectionParams.setConnectionTimeout(httpParameters, * CONNECT_TIMEOUT); // Set the default socket timeout (SO_TIMEOUT) * // in milliseconds which is the timeout for waiting for data. * HttpConnectionParams.setSoTimeout(httpParameters, SO_TIMEOUT); if * (httpClient == null) { httpClient = new * DefaultHttpClient(httpParameters); } } */ if(httpClient != null){ Thread thread = new Thread(){ @Override public void run() { try { response = httpClient.execute(httpRequest); }catch(IllegalArgumentException ec){ response = null; interrupted(); } catch (ClientProtocolException e) { response = null; interrupted(); e.printStackTrace(); } catch (IOException e) { response = null; interrupted(); e.printStackTrace(); } } }; thread.start(); try { Thread.sleep(1000*2); if(response == null){ thread.interrupt(); } } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } } int statusCode = response.getStatusLine().getStatusCode(); System.out.println(statusCode); if (response.getStatusLine().getStatusCode() == 200) { if (retDataType != null) result = EntityUtils.toString(response.getEntity(), retDataType); else result = EntityUtils.toString(response.getEntity(), HTTP.UTF_8); } } catch (UnsupportedEncodingException e) { e.printStackTrace(); } catch (ClientProtocolException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } catch (IllegalArgumentException e) { e.printStackTrace(); } catch (ParseException e) { e.printStackTrace(); }finally{ httpClient.getConnectionManager().closeExpiredConnections(); } return result; }