Java Implementation of the HTTP packet reading process

Source: Internet
Author: User

In the previous two articles, "GET Implementation of HTTP request packets" and "HTTP request packet Java Implementation" have explained the request connection content of the HTTP packet. This article will continue to provide some additional information to explain how to read the HTTP packet.

The following is a SocketRequest class designed by myself to read the HTTP protocol package 。

 
 
  1. Public class SocketRequest
  2. {// Read data from the InputStream of the specified Socket
  3. Private InputStreaminput;
  4. Private Stringuri;
  5. Private StringBufferrequest = new StringBuffer (); // used to save all content
  6. Private intCONTENT_LENGTH = 0; // The Data Length of the actual package content
  7. Private boolean bePost = false;
  8. Private boolean beHttpResponse = false;
  9. Private boolean beChucked = false;
  10. Private boolean beGet = false;
  11. Private bytecrlf13 = (byte) 13; // 'R'
  12. Private bytecrlf10 = (byte) 10; // 'n'
  13. Public SocketRequest (InputStream input ){
  14. This. input = input ;}
  15. Public SocketRequest (Socket socket ){
  16. This. input = socket. getInputStream ();}
  17. Public void ReadData ()
  18. {// Parse the InputStream data
  19. ReadHeader (); // Header
  20. If (beChucked) // It is Chucked
  21. {Int ChuckSize = 0;
  22. While (ChuckSize = getChuckSize ()> 0) // multiple Chucked
  23. {ReadLenData (ChuckSize + 2); // read the fixed-length data}
  24. ReadLenData (2); // the last two digits}
  25. If (CONTENT_LENGTH> 0)
  26. {ReadLenData (CONTENT_LENGTH); // read the fixed-length data}
  27. Uri = ""; // parseUri (new String (request ));}
  28. Private void readLenData (int size) // read the fixed-length data
  29. {Int readed = 0; // read count
  30. Try {
  31. Int available = 0; // input. available (); // readable
  32. If (available> (size-readed) available = size-readed;
  33. While (readed <size)
  34. {While (available = 0) {// wait until data is readable
  35. Available = input. available (); // readable}
  36. If (available> (size-readed) available = size-readed; // size-readed -- remaining number
  37. If (available> 2048) available = 2048; // size-readed -- remaining number
  38. Byte [] buffer = new byte [available];
  39. Int reading = input. read (buffer );
  40. Request = request. append (new String (buffer, 0, reading); // Add byte Arrays
  41. Readed + = reading; // read characters
  42. } Catch (IOException e) {System. out. println ("Read readLenData Error! ");}}
  43. Private voidReadHeader () // read the header and obtain the size
  44. {Byte [] crlf = new byte [1];
  45. IntcrlfNum = 0; // The number of line breaks connected to the carriage return. crlfNum = 4 indicates the end of the header.
  46. Try {while (input. read (crlf )! =-1) // read the header
  47. {If (crlf [0] = crlf13 | crlf [0] = crlf10)
  48. {CrlfNum ++ ;}
  49. Else
  50. {CrlfNum = 0;} // clear if not
  51. Request = request. append (new String (crlf,); // Add the byte array
  52. If (crlfNum = 4) break ;}}
  53. Catch (IOException e) {System. out. println ("Read Http Header Error! ");
  54. Return ;}
  55. String tempStr = (new String (request). toUpperCase (); // here I only process the GET and POST Methods
  56. StringstrMethod = tempStr. substring (0, 4 );
  57. If (strMethod. equals ("GET") // before
  58. {BeGet = true ;}
  59. Else if (strMethod. equals ("POST "))
  60. {BePost = true;
  61. GetContentlen_Chucked (tempStr );}
  62. Else {System. out. println ("unsupported HTTP packet type");} // other types are not currently supported
  63. }
  64. Private void getContentlen_Chucked (String tempStr) // obtain the CONTENT-LENGTH or whether it is CHUNKED
  65. {String ss1 = "CONTENT-LENGTH :";
  66. String ss2 = new String ("TRANSFER-ENCODING: CHUNKED ");
  67. Int clIndex = tempStr. indexOf (ss1 );
  68. Int chuckIndex = tempStr. indexOf (ss2); // CHUNKED type
  69. Byte requst [] = tempStr. getBytes ();
  70. If (clIndex! =-1)
  71. {// Starting from clIndex + 1 to rn
  72. StringBuffer sb = new StringBuffer ();
  73. For (int I = (clIndex + 16); I ++)
  74. {If (requst [I]! = (Byte) 13 & requst [I]! = (Byte) 10)
  75. {Sb. append (char) requst [I]);}
  76. Else
  77. Break ;}
  78. CONTENT_LENGTH = Integer. parseInt (sb. toString (); // the size of the formal HTML file
  79. // System. out. println ("CONTENT_LENGTH =" + CONTENT_LENGTH );}
  80. If (chuckIndex! =-1) beChucked = true ;}
  81. Private intgetChuckSize () // Chuck size {
  82. Byte [] crlf = new byte [1];
  83. StringBuffersb1 = new StringBuffer ();
  84. IntcrlfNum = 0; // The number of line breaks connected to the carriage return. crlfNum = 4 indicates the end of the header.
  85. Try {while (input. read (crlf )! =-1) // read the header {
  86. If (crlf [0] = crlf13 | crlf [0] = crlf10)
  87. {CrlfNum ++ ;}
  88. Else
  89. {CrlfNum = 0;} // clear if not
  90. Sb1.append (char) crlf [0]);
  91. Request = request. append (new String (crlf,); // Add the byte array
  92. If (crlfNum = 2) break ;}
  93. } Catch (IOException e ){
  94. System. out. println ("Read Http Package Error! ");
  95. Return 0 ;}
  96. Return Integer. parseInt (sb1.toString (). trim (), 16); // 16.
  97. } // Use this method to filter whether the HTTP protocol package is sent to the target server
  98. Private String parseUri (String requestString ){
  99. Int index1, index2;
  100. Index1 = requestString. indexOf ('');
  101. If (index1! =-1 ){
  102. Index2 = requestString. indexOf ('', index1 + 1 );
  103. If (index2> index1)
  104. Return requestString. substring (index1 + 1, index2 );}
  105. Return null ;}
  106. Public String getData (){
  107. Return request. toString ();}}

Use this class:

 
 
  1. SocketRequest request = new SocketRequest (socket); // The socket is the Socket instance returned by ServerSocket. accept ().
  2. Request. ReadData (); // read data
  3. Request. getData ();

Why should I use this powerful power to read data? Especially when the Socket connection sends data, latency often occurs due to network reasons, when the server starts receiving data, it is possible that only part of the data can be obtained from InputStream. Otherwise, incomplete data or incorrect data may be obtained 。

There are multiple methods to read bytes from InputStream:

Commonly used int read () and int read (byte [] B). When read (byte []) is used, programmers often make mistakes because in the network environment, the amount of data read is not necessarily equal to the size of the parameter 。

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.