詳解HttpURLConnection

jopen 8年前發布 | 10K 次閱讀 Java開發

請求響應流程

詳解HttpURLConnection - 白志華的個人空間

設置連接參數的方法

  • setAllowUserInteraction

  • setDoInput

  • setDoOutput

  • setIfModifiedSince

  • setUseCaches

  • setDefaultAllowUserInteraction

  • setDefaultUseCaches

設置請求頭或響應頭

HTTP請求允許一個key帶多個用逗號分開的values,但是HttpURLConnection只提供了單個操作的方法:

  • setRequestProperty(key,value)

  • addRequestProperty(key,value)

setRequestProperty和addRequestProperty的區別就是,setRequestProperty會覆蓋已經存在的key的所有values,有清零重新賦值的作用。而addRequestProperty則是在原來key的基礎上繼續添加其他value。

發送URL請求

建立實際連接之后,就是發送請求,把請求參數傳到服務器,這就需要使用outputStream把請求參數傳給服務器:

  • getOutputStream 

獲取響應

請求發送成功之后,即可獲取響應的狀態碼,如果成功既可以讀取響應中的數據,獲取這些數據的方法包括:

  • getContent

  • getHeaderField

  • getInputStream 

對于大部分請求來說,getInputStream和getContent是用的最多的。

相應的信息頭用以下方法獲取:

  • getContentEncoding

  • getContentLength

  • getContentType

  • getDate

  • getExpiration

  • getLastModifed 

HttpURLConnection

任何網絡連接都需要經過socket才能連接,HttpURLConnection不需要設置socket,所以,HttpURLConnection并不是底層的連接,而是在底層連接上的一個請求。這就是為什么HttpURLConneciton只是一個抽象類,自身不能被實例化的原因。HttpURLConnection只能通過URL.openConnection()方法創建具體的實例。

雖然底層的網絡連接可以被多個HttpURLConnection實例共享,但每一個HttpURLConnection實例只能發送一個請求。請求結束之后,應該調用HttpURLConnection實例的InputStream或OutputStream的close()方法以釋放請求的網絡資源,不過這種方式對于持久化連接沒用。對于持久化連接,得用disconnect()方法關閉底層連接的socket。

創建HttpURLConnection

URL url = new URL("http://localhost:8080/xxx.do");  
   
URLConnection rulConnection = url.openConnection();// 此處的urlConnection對象實際上是根據URL的  
// 請求協議(此處是http)生成的URLConnection類  
// 的子類HttpURLConnection,故此處最好將其轉化  
// 為HttpURLConnection類型的對象,以便用到  
// HttpURLConnection更多的API.如下:  
   
HttpURLConnection httpUrlConnection = (HttpURLConnection) rulConnection;

設置HttpURLConnection參數

// 設定請求的方法為"POST",默認是GET  
httpUrlConnection.setRequestMethod("POST");  
  
// 設置是否向httpUrlConnection輸出,因為這個是post請求,參數要放在  
// http正文內,因此需要設為true, 默認情況下是false;  
httpUrlConnection.setDoOutput(true);  
   
// 設置是否從httpUrlConnection讀入,默認情況下是true;  
httpUrlConnection.setDoInput(true);  
   
// Post 請求不能使用緩存  
httpUrlConnection.setUseCaches(false);  
   
// 設定傳送的內容類型是可序列化的java對象  
// (如果不設此項,在傳送序列化對象時,當WEB服務默認的不是這種類型時可能拋java.io.EOFException)  
httpUrlConnection.setRequestProperty("Content-type", "application/x-java-serialized-object");  
 
// 連接,從上述url.openConnection()至此的配置必須要在connect之前完成,  
httpUrlConnection.connect();

 

URLConnection建立連接

// 此處getOutputStream會隱含的進行connect(即:如同調用上面的connect()方法,  
// 所以在開發中不調用上述的connect()也可以)。  
OutputStream outStrm = httpUrlConnection.getOutputStream();
getInputStream()也是同理。

HttpURLConnection發送請求

// 現在通過輸出流對象構建對象輸出流對象,以實現輸出可序列化的對象。  
ObjectOutputStream objOutputStrm = new ObjectOutputStream(outStrm);  
   
// 向對象輸出流寫出數據,這些數據將存到內存緩沖區中  
objOutputStrm.writeObject(new String("我是測試數據"));  
   
// 刷新對象輸出流,將任何字節都寫入潛在的流中(些處為ObjectOutputStream)  
objOutputStm.flush();  
  
// 關閉流對象。此時,不能再向對象輸出流寫入任何數據,先前寫入的數據存在于內存緩沖區中,  
// 在調用下邊的getInputStream()函數時才把準備好的http請求正式發送到服務器  
objOutputStm.close();

 

HttpURLConneciton獲取響應

 // 調用HttpURLConnection連接對象的getInputStream()函數,  

InputStream inStrm = httpConn.getInputStream(); 

設置POST參數

OutputStream os = httpConn.getOutputStream();  
             String param = new String();  
             param = "CorpID=" + CorpID +  
                     "&LoginName=" + LoginName+  
                     "&send_no=" + phoneNumber +  
                     "&msg=" + java.net.URLEncoder.encode(msg,"GBK"); ;  
             os.write(param.getBytes());

 

超時設置,防止 網絡異常的情況下,可能會導致程序僵死而不繼續往下執行

System.setProperty("sun.net.client.defaultConnectTimeout""30000");  

System.setProperty("sun.net.client.defaultReadTimeout""30000");  

 

其中: sun.net.client.defaultConnectTimeout:連接主機的超時時間(單位:毫秒)  

sun.net.client.defaultReadTimeout:從主機讀取數據的超時時間(單位:毫秒)  

  

JDK 1.5以前的版本,只能通過設置這兩個系統屬性來控制網絡超時。在1.5中,還可以使用HttpURLConnection的父類URLConnection的以下兩個方法:  

setConnectTimeout:設置連接主機超時(單位:毫秒)  

setReadTimeout:設置從主機讀取數據超時(單位:毫秒)  

  

例如:  

HttpURLConnection urlCon = (HttpURLConnection)url.openConnection();  

urlCon.setConnectTimeout(30000);  

urlCon.setReadTimeout(30000);  


來自: http://blog.csdn.net/woxueliuyun/article/details/43267365

 本文由用戶 jopen 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!