一、HTTP協議:
(一)、 請求消息:客戶端發送給服務器端的數據
- 數據格式:
- 請求行
- 請求頭
- 請求空行
- 請求體
(二)、 響應消息:服務器端發送給客戶端的數據
數據格式:
1. 響應行
-
組成:協議/版本 響應狀態碼 狀態碼描述
-
響應狀態碼:服務器告訴客戶端瀏覽器本次請求和響應的一個狀態。
(1)、 狀態碼都是3位數字
(2)、 分類:
①、 1xx:服務器就收客戶端消息,但沒有接受完成,等待一段時間後,發送1xx多狀態碼
②、 2xx:成功。代表:200
③、 3xx:重定向。代表:302(重定向),304(訪問緩存)
④、 4xx:客戶端錯誤。
* 代表:
* 404(請求路徑沒有對應的資源)
* 405:請求方式沒有對應的doXxx【doGet或doPost】方法
⑤、 5xx:服務器端錯誤。代表:500(服務器內部出現異常)
2. 響應頭:
- 格式:
頭名稱: 值
- 常見的響應頭:
(1)、 Content-Type:服務器告訴客戶端本次響應體數據格式以及編碼格式Content-Type: text/html;charset=UTF-8
==(2)、 Content-disposition:服務器告訴客戶端以什麼格式打開響應體數據
* 值:
*in-line:默認值,在當前頁面內打開
*attachment;filename=xxx:以附件形式打開響應體。文件下載
3. 響應空行
4. 響應體:傳輸的數據
* 響應字符串格式
HTTP/1.1 200 OK
Content-Type: text/html;charset=UTF-8
Content-Length: 101
Date: Wed, 06 Jun 2018 07:08:42 GMT
<html>
<head>
<title>$Title$</title>
</head>
<body>
hello , response
</body>
</html>
二、Response對象響應消息
(一)、功能:設置響應消息
1. 設置響應行
- 格式:
HTTP/1.1 200 ok
- 設置狀態碼:
setStatus(int sc)
2. 設置響應頭:==setHeader(String name, String value) ==
3. 設置響應體:
- 使用步驟:
-
獲取輸出流
-
字符輸出流:
PrintWriter getWriter()
-
字節輸出流:
ServletOutputStream getOutputStream()
-
-
使用輸出流,將數據輸出到客戶端瀏覽器
-
(二)、案例:
1. 完成重定向
- 重定向:資源跳轉的方式
- 代碼實現:訪問ResponseDemo1資源時,跳轉到ResponseDemo2資源。
package cn.itcast.web.servlet;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
/**
* 重定向
*/
@WebServlet("/ResponseDemo1")
public class ResponseDemo1 extends HttpServlet {
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
System.out.println("demo1.....");
//訪問/ResponseDemo1,會自動跳轉到/ResponseDemo2資源
//1.設置狀態碼爲302
response.setStatus(302);
//2.設置響應頭location
response.setHeader("location","/LoginCase/ResponseDemo2");
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
this.doPost(request, response);
}
}
package cn.itcast.web.servlet;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@WebServlet("/ResponseDemo2")
public class ResponseDemo2 extends HttpServlet {
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
System.out.println("demo2.....");
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
this.doPost(request, response);
}
}
在Response中,有一個簡單的重定向方法,只需要將填寫跳轉路徑的字符串就可以。
//簡單的重定向方法
response.sendRedirect("/day15/responseDemo2");
- 重定向的特點:redirect
①、 地址欄發生變化【當我們在地址欄中輸入並訪問http://localhost:8080/LoginCase/ResponseDemo1後,地址欄變成http://localhost:8080/LoginCase/ResponseDemo2】
②、 重定向可以訪問其他站點(服務器)的資源
③、 重定向是兩次請求。不能使用request對象來共享數據 - 轉發的特點:forward
①、 轉發地址欄路徑不變
②、 轉發只能訪問當前服務器下的資源
③、 轉發是一次請求,可以使用request對象來共享數據
2.路徑寫法:
- 相對路徑:通過相對路徑不可以確定唯一資源
(1)、 如:./index.html
(2)、 不以/開頭,以 . 開頭路徑
(3)、 規則:找到當前資源和目標資源之間的相對位置關係
①、./:當前目錄
②、../:後退一級目錄
- 絕對路徑:通過絕對路徑可以確定唯一資源
(1)、 如:http://localhost:8080/LoginCase/ResponseDemo2
(2)、 以/開頭的路徑
(3)、 規則:判斷定義的路徑是給誰用的?判斷請求將來從哪兒發出
①、 給客戶端瀏覽器使用:需要加虛擬目錄(項目的訪問路徑)
②、 建議虛擬目錄動態獲取:request.getContextPath()
③、 < a > , < form > 重定向…
④、給服務器使用:不需要加虛擬目錄
⑤、 轉發路徑request.getRequestDispatcher("/ResponseDemo2").forward(request,response);
2. 服務器輸出字符數據到瀏覽器
(1)、步驟:
①、 獲取字符輸出流
②、 輸出數據
//1.獲取字符輸出流
PrintWriter pw = response.getWriter();
//2.輸出數據
pw.write("<h1>hello response</h1>");
(4)、注意、亂碼問題:
①、 PrintWriter pw = response.getWriter();
獲取的流的默認編碼是ISO-8859-1
②、 設置該流的默認編碼
③、 告訴瀏覽器響應體使用的編碼
response.setHeader("content-type","text/html;charset=utf-8");
//簡單的形式,設置編碼,是在獲取流之前設置
response.setContentType("text/html;charset=utf-8");
3. 服務器輸出字節數據到瀏覽器
步驟:
①、 獲取字節輸出流
②、 輸出數據
response.setContentType("text/html;charset=utf-8");
//1.獲取字節輸出流
ServletOutputStream sos = response.getOutputStream();
//2.輸出數據
sos.write("你好".getBytes("utf-8"));
4. 驗證碼
(1). 本質:圖片
(2). 目的:防止惡意表單註冊
import javax.imageio.ImageIO;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.util.Random;
@WebServlet("/CheckCodeServlet")
public class CheckCodeServlet extends HttpServlet {
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
int width = 100;
int height = 50;
//1.創建一對象,在內存中圖片(驗證碼圖片對象)
BufferedImage image = new BufferedImage(width,height,BufferedImage.TYPE_INT_RGB);
//2.美化圖片
//2.1填充背景色
Graphics g = image.getGraphics();//畫筆對象
g.setColor(Color.PINK);//設置畫筆顏色
g.fillRect(0,0,width,height);
//2.2畫邊框
g.setColor(Color.BLUE);
g.drawRect(0,0,width-1,height-1);
String str = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
//生成隨機角標
Random ran = new Random();
for (int i = 1; i <= 4; i++) {
int index = ran.nextInt(str.length());
//獲取字符
char ch = str.charAt(index);
//2.3寫驗證碼
g.drawString(ch+"",width/5*i,height/2);
}
//2.4畫干擾線
g.setColor(Color.GREEN);
//隨機生成座標點
for (int i = 1; i <= 10; i++) {
int x1 = ran.nextInt(width);
int x2 = ran.nextInt(width);
int y1 = ran.nextInt(height);
int y2 = ran.nextInt(height);
g.drawLine(x1,x2,y1,y2);
}
//3.將圖片輸出到頁面展示
ImageIO.write(image, "jpg", response.getOutputStream());
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
this.doPost(request, response);
}
}
在服務器上訪問其資源時,效果顯示如下:
實現通過點擊驗證碼來切換驗證碼圖片內容
分析:
點擊超鏈接或者圖片,需要換一張
1.給超鏈接和圖片綁定單擊事件
2.重新設置圖片src屬性值
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>驗證碼</title>
<script>
window.onload = function(){
//1.獲取圖片對象
var img = document.getElementById("checkCode");
//2.綁定單擊事件
img.onclick = function () {
//加時間戳
var date = new Date().getTime();
img.src = "/LoginCase/CheckCodeServlet?"+date;
}
}
</script>
</head>
<body>
<img id="checkCode" src="/LoginCase/CheckCodeServlet"/>
<a id="change" href="">看不清換一張?</a>
</body>
</html>