<img src="1.jpg"/> <img src="2.jpg"/> <img src="3.jpg"/>
一個完整的HTTP請求包含:html
1.一個請求行(GET /aa/index.html HTTP/1.0)java
2.若干個請求頭(告訴服務器客戶端的一些信息)web
3.實體內容(請求的時候須要向服務器傳遞的內容)。瀏覽器
注意:請求行,請求頭,而後後空一行,請求信息(如表單提交數據爲post方式)。緩存
請求行:用於描述客戶端的請求方式,請求的資源名稱,以及使用的HTTP的協議版本號tomcat
GET /aa/index.html HTTP/1.0 服務器
告訴服務器一些客戶端的信息app
Accept:用於告訴服務器,客戶機支持的數據類型(值爲:text/html(文本),image(圖片),/*/(任何類型)webapp
Accept-Charset:客戶機採用的編碼ide
Accept-Encoding:客戶機支持的壓縮格式
Accept-Language:客戶機的語言環境,不一樣國家訪問的內容也是不一樣的,就是經過這個頭實現的,用於實現國際化
Host:告訴服務器,想訪問的主機名
If-Modified-Since:客戶機將這個頭信息發送給服務端,服務端進行比對,告訴客戶機是否去拿緩存,和服務器端返回的Last-Modified值是相等的
If-None-Match:客戶機將這個頭信息發送給服務端,服務端進行比對,告訴客戶機是否去拿緩存,和服務器端返回的Etag值是相等的
Referer:客戶機告訴服務器,他是從哪一個資源來訪問服務器的(防盜鏈),經過檢查該頭是不是從本網站點擊過來的,如不是的,就讓他跳到本網站的首頁來
User-Agen::客戶機告訴服務器,客戶機的軟件環境
Cookie:客戶機經過這個頭向服務器帶點數據
Connection:客戶機的鏈接狀態(close:關閉鏈接 Keep-Alive:不會斷開鏈接)
例子:
這個是我在訪問http://localhost:8080/aa/index.html,能夠看到請求信息。
以上的內容爲多個消息頭,用於描述客戶端請求哪臺主機,以及客戶端的一些環境信息等
請求行中的GET稱之爲請求方式,請求方式:post,get,head,options,delete,trace,put,經常使用的有:get,post,用戶沒有設置,默認狀況下瀏覽器向服務器發送的都是get請求,例如在瀏覽器直接輸地址訪問,點擊連接訪問都是get,用戶如想把請求方式改成post,可經過更改表單form的提交方式實現.無論post或get,都用於向服務器請求某個web資源,這兩種方式的區別主要表如今數據傳遞上:請求方式爲get方式,則能夠再請求的URL地址後以?的形式帶上交給服務器的數據,多個數據之間以&進行分割,同時在URL地址後附帶的參數是有限制的,其數據容量一般不能超過1k,若請求方式爲post方式,則能夠再請求的實體內容中向服務器發送數據,post方式的特色:傳送的數據無限制.
<a href="/2.html?name=jiangwei">2.html</a>
點擊這個連接就是一個get方式,並且攜帶了name字段值
點擊連接是Get方式,並且是在資源地址後面攜帶信息的。
同時再看一下Referer這個請求頭,這個頭表明的是從當前頁面是從哪一個頁面跳轉過來的:
咱們點擊上面的2.html超連接,跳轉到了2.html頁面這時候能夠看到請求頭中的Referer:http://localhost:8080/aa/index.html,代表2.html頁面是從index.html頁面跳轉過來的,這個請求頭的做用仍是很大的,主要用於防盜鏈,好比用戶點擊了一個連接跳轉到一個頁面中,該頁面的網站站長髮現這個用戶不是從指定的頁面中跳轉過來的,因此就會讓頁面跳轉到該網站的首頁,讓用戶從該網站的首頁跳轉到該頁面。
下面在/aa/index.html文件中添加一個表單:
<form action="/2.html" method="post"> <input type="text" name="name"/> <input type="submit"/> </form>在文本框中輸入內容,點擊提交按鈕:
能夠看到這種方式是post方式,並且在請求頭以後空一行,是請求內容信息。
用於描述服務器的基本信息,以及數據的描述,服務器經過這些數據的描述信息,能夠通知客戶端如何處理等一會它會送的數據
Location:這個頭配合302狀態碼使用,用於告訴用戶找誰
response.setStatus(302); response.setHeader("Location","/aa/1.html");
請求重定向,判斷瀏覽器的地址欄的地址是否發生變化,實例是用戶登陸
Server:服務器經過這個頭,告訴瀏覽器的類型
Content-Encoding:服務器經過這個頭,數據的壓縮格式,收費是靠數據出口量算的, 因此爲了省錢和效率高,要進行數據壓縮,jdk中的GZIPOutputStream類,壓縮類流,包裝流和底層流,最好將包裝流關了或者刷新,數據寫入到底層流中去,
response.setHeader("Content-Encoding","gzip"); response.setHeader("Content-length",gzip.length+"");
Content-Length:服務器會送的數據的長度
Content-Type:服務器會送數據的類型,response.getOutputStream().write();服務器會送數據都是二進制,經過這個頭,能夠告訴瀏覽器這個二進制是什麼類型,
InputStream in = this.getServletContext().getResourceAsStream("/1.jpg"); int len = 0; byte buffer[] =new byte[1024]; OutputStream out =response.getOutputStream(); while((len=in.read(buffer))>0){ out.write(buffer,0,len) }
在服務器的目錄下的web.xml中查看各個數據類型的respose.setHeader("content-type","")的寫法.
Refresh:告訴瀏覽器隔多長時間刷新一次,response.setHeader("refresh","3;url=""")控制瀏覽器隔三秒跳到指定的網頁上
Content-Disposition:告訴瀏覽器如下載的方式打開文件
response.setHeader("content-disposition","attachment;filename=1.jpg);
Transfer-Encoding:告訴瀏覽器數據的傳送格式
Last-Modified:服務端文件的最後修改時間,這個值返回給客戶端,客戶機第二次訪問服務器時帶來的If-Modified-Since的值和服務器的值同樣,就拿緩存給客戶,實時更新,
ETag:緩存相關的頭,服務器根據數據的內容生產一個字符串,客戶機第二次訪問服務器時帶來的If-None-Match的值和服務器的值同樣,就拿緩存給客戶,實時更新,
Expires:高速瀏覽器,把會送的資源緩存多少時間,-1或0,則是不緩存的
Pragma:no-cache
Cache-Control:no-cache
Date:控制瀏覽器不要緩存數據,當數據不發生改變時,就要緩存,當實時性要求很高的數據不能緩存.
HTTP /1.1 200 OK :狀態行,用於描述服務器對請求的處理結果
格式:HTTP版本號 狀態碼 緣由敘述
狀態碼用於表示服務器對請求的處理結果,他是一個三位的十進制數,響應狀態碼分爲5類,
100-199:表示接收請求,要求客戶端繼續提交下一次請求才能完成整個處理過程
200-299:表示成功接收請求並已完成整個處理過程,經常使用200
300-399:爲完成請求,客戶需進一步細化請求,例如,請求的資源已經移動一個新地址,經常使用302(你請求我,我叫你去找別人),307和304(拿緩存)
400-499:客戶端的請求有錯誤,經常使用404,403(沒有權限訪問,以前咱們在打開Tomcat Manager頁面的時候遇到過)
500-599:服務器端出現錯誤,經常使用500
在響應頭後面空一行是服務器返回的實體內容:
<HTML>
<BODY>
...........
package com.http.demo; import java.io.ByteArrayOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.zip.GZIPOutputStream; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; public class HttpServletDemo extends HttpServlet { private static final long serialVersionUID = -7234797658264000867L; @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp)throws ServletException, IOException { //測試 try{ //test1(resp);//location響應頭 //test2(resp);//Content-Encoding響應頭 //test3(resp);//Content-Type響應頭 test4(resp);//refresh響應頭 //test5(resp);//content-disposition }catch(Exception e){ e.printStackTrace(); } } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp)throws ServletException, IOException { doGet(req,resp); } //使用響應頭location和302狀態碼實現請求重定向(地址欄中的地址發生改變) public void test1(HttpServletResponse response){ response.setStatus(302); response.setHeader("Location", "/aa/3.html"); } //使用響應頭Content-Encoding實現數據的壓縮輸出 public void test2(HttpServletResponse resp) throws Exception{ //壓縮數據很大的時候壓縮效率纔有體現,若是數據很小的話反而更大 //壓縮資源:提升網頁的訪問性能,電信按照出口流量收錢的。 String data = "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa";//壓縮數據大點還有效果 System.out.println("壓縮前的數據大小:"+data.length()); ByteArrayOutputStream bout = new ByteArrayOutputStream();//底層流 GZIPOutputStream gout = new GZIPOutputStream(bout);//包裝流通常有緩衝,沒有把緩衝區寫滿,不會寫到底層流 gout.write(data.getBytes()); gout.close();//等於刷新操做,將包裝流中的信息刷新 byte gzip[] = bout.toByteArray();//獲得壓縮後的數據 System.out.println("壓縮後的數據大小:"+gzip.length); //通知瀏覽器數據採用壓縮格式 resp.setHeader("Content-Encoding", "gzip"); resp.setHeader("Content-Length", gzip.length+"");//代表長度 resp.getOutputStream().write(gzip);//壓縮數據寫給瀏覽器 } //使用響應頭content-type設置服務器返回給client的數據類型 public void test3(HttpServletResponse resp) throws Exception{ //具體能夠查看tomcat目錄中的web.xml文件 resp.setHeader("Content-Type","image/jpeg"); InputStream ins = this.getServletContext().getResourceAsStream("/1.jpg"); int len = 0; byte[] buffer = new byte[1024]; OutputStream ops = resp.getOutputStream(); while((len = ins.read(buffer))!=-1){ ops.write(buffer, 0, len); } ops.close(); } //使用響應頭refresh實現頁面的定時刷新 public void test4(HttpServletResponse resp) throws Exception{ //股票,聊天室 //填充的值爲:3;url="http://www.baidu.com"表示3s以後跳轉到http://www.baidu.com頁面 //若是沒有http://www.baidu.com的話,只是在該頁面進行刷新 resp.setHeader("refresh", "3;url=\"http://www.baidu.com\""); String data = "aaaaaaaaaaaaaa"; resp.getOutputStream().write(data.getBytes()); } //使用響應頭content-disposition實現客戶機用下載的方式打開數據資源 public void test5(HttpServletResponse resp) throws Exception{ resp.setHeader("content-disposition","attachment;filename=1.jpg"); InputStream ins = this.getServletContext().getResourceAsStream("/1.jpg"); int len = 0; byte[] buffer = new byte[1024]; OutputStream ops = resp.getOutputStream(); while((len = ins.read(buffer))!=-1){ ops.write(buffer, 0, len); } } }
resp.setHeader("refresh", "3");每隔3s刷新該頁面
resp.setHeader("refresh", "3;url=\"http://www.baidu.com\"");這個就是說3s以後跳轉到baidu首頁。