Cookie 其实是存储在客户端上的文本信息,并保留了各类跟踪的信息。
Cookie工做步骤:
(1)客户端请求服务器,若是服务器须要记录该用户的状态,就是用 response 向客户端浏览器颁发一个 Cookie。
(2)客户端浏览器会把 Cookie 保存下来。
(3)当浏览器再请求该网站时,浏览器把该请求的网址连同 Cookie 一同提交给服务器。服务器检查该 Cookie,以此来辨认用户状态。
注:Cookie功能须要浏览器的支持,若是浏览器不支持Cookie或者Cookie禁用了,Cookie功能就会失效。
Java中把Cookie封装成了javax.servlet.http.Cookie类。
Cookies 一般设置在 HTTP 头信息中(虽然 JavaScript 也能够直接在浏览器上设置一个 Cookie)。设置 Cookie 的 Servlet 会发送以下的头信息:
HTTP/1.1 200 OK
Date: Fri, 04 Feb 2000 21:03:38 GMT
Server: Apache/1.3.9 (UNIX) PHP/4.0b3
Set-Cookie: name=xyz; expires=Friday, 04-Feb-07 22:03:38 GMT;
path=/; domain=w3cschool.cc
Connection: close
Content-Type: text/html
|
正如您所看到的,Set-Cookie 头包含了一个名称值对、一个 GMT 日期、一个路径和一个域。名称和值会被 URL 编码。expires 字段是一个指令,告诉浏览器在给定的时间和日期以后"忘记"该 Cookie。
若是浏览器被配置为存储 Cookies,它将会保留此信息直到到期日期。若是用户的浏览器指向任何匹配该 Cookie 的路径和域的页面,它会从新发送 Cookie 到服务器。浏览器的头信息可能以下所示:
GET / HTTP/1.0
Connection: Keep-Alive
User-Agent: Mozilla/4.6 (X11; I; Linux 2.2.6-15apmac ppc)
Host: zink.demon.co.uk:1126
Accept: image/gif, */*
Accept-Encoding: gzip
Accept-Language: en
Accept-Charset: iso-8859-1,*,utf-8
Cookie: name=xyz
|
方法
|
功能
|
public void setDomain(String pattern)
|
该方法设置 cookie 适用的域。
|
public String getDomain()
|
该方法获取 cookie 适用的域。
|
public void setMaxAge(int expiry)
|
该方法设置 cookie 过时的时间(以秒为单位)。若是不这样设置,cookie 只会在当前 session 会话中持续有效。
|
public int getMaxAge()
|
该方法返回 cookie 的最大生存周期(以秒为单位),默认状况下,-1 表示 cookie 将持续下去,直到浏览器关闭。
|
public String getName()
|
该方法返回 cookie 的名称。名称在建立后不能改变。
|
public void setValue(String newValue)
|
该方法设置与 cookie 关联的值。
|
public String getValue()
|
该方法获取与 cookie 关联的值。
|
public void setPath(String uri)
|
该方法设置 cookie 适用的路径。若是您不指定路径,与当前页面相同目录下的(包括子目录下的)全部 URL 都会返回 cookie。
|
public String getPath()
|
该方法获取 cookie 适用的路径。
|
public void setSecure(boolean flag)
|
该方法设置布尔值,向浏览器指示,只会在HTTPS和SSL等安全协议中传输此类Cookie。
|
public void setComment(String purpose)
|
该方法规定了描述 cookie 目的的注释。该注释在浏览器向用户呈现 cookie 时很是有用。
|
public String getComment()
|
该方法返回了描述 cookie 目的的注释,若是 cookie 没有注释则返回 null。
|
Cookie的maxAge决定着Cookie的有效期,单位为秒。
若是maxAge为0,则表示删除该Cookie;若是为负数,表示该Cookie仅在本浏览器中以及本窗口打开的子窗口内有效,关闭窗口后该Cookie即失效。
Cookie中提供getMaxAge()和setMaxAge(int expiry)方法来读写maxAge属性。
Cookie是不能够跨域名的。域名www.google.com颁发的Cookie不会被提交到域名www.baidu.com去。这是由Cookie的隐私安全机制决定的。隐私安全机制可以禁止网站非法获取其余网站的Cookie。
正常状况下,同一个一级域名的两个二级域名之间也不能互相使用Cookie。若是想让某域名下的子域名也可使用该Cookie,须要设置Cookie的domain参数。
Java中使用setDomain(String domain)和getDomain()方法来设置、获取domain。
Path属性决定容许访问Cookie的路径。
Java中使用setPath(String uri)和getPath()方法来设置、获取path。
HTTP协议不只是无状态的,并且是不安全的。
使用HTTP协议的数据不通过任何加密就直接在网络上传播,有被截获的可能。若是不但愿Cookie在HTTP等非安全协议中传输,能够设置Cookie的secure属性为true。浏览器只会在HTTPS和SSL等安全协议中传输此类Cookie。
Java中使用setSecure(boolean flag)和getSecure ()方法来设置、获取Secure。
经过 Servlet 添加 Cookies 包括三个步骤:
(1)建立一个 Cookie 对象:您能够调用带有 cookie 名称和 cookie 值的 Cookie 构造函数,cookie 名称和 cookie 值都是字符串。
(2)设置最大生存周期:您可使用 setMaxAge 方法来指定 cookie 可以保持有效的时间(以秒为单位)。
(3)发送 Cookie 到 HTTP 响应头:您可使用 response.addCookie 来添加 HTTP 响应头中的 Cookies。
AddCookieDemo.java
package notes.javaee.servlet.cookie;
// 导入必需的 java 库
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
// 扩展 HttpServlet 类
@WebServlet("/servlet/cookie/addCookieDemo")
public class AddCookieDemo extends HttpServlet {
private static final long serialVersionUID = 1L;
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
Cookie cookieName = new Cookie("name", request.getParameter("name"));
Cookie cookieAge = new Cookie("age", request.getParameter("age"));
// 为两个Cookie设置有效期
cookieName.setMaxAge(30);
cookieAge.setMaxAge(30);
// 在响应头中添加两个 Cookies
response.addCookie(cookieName);
response.addCookie(cookieAge);
// 设置响应内容类型
response.setContentType("text/html");
response.setCharacterEncoding("utf-8");
PrintWriter out = response.getWriter();
String title = "设置 Cookies 实例";
String docType = "<!doctype html public \"-//w3c//dtd html 4.0 " +
"transitional//en\">\n";
out.println(docType +
"<html>\n" +
"<head><title>" + title + "</title></head>\n" +
"<body bgcolor=\"#f0f0f0\">\n" +
"<h1 align=\"center\">" + title + "</h1>\n" +
"<ul>\n" +
" <li><b>名字</b>:"
+ request.getParameter("name") + "\n" +
" <li><b>年龄</b>:"
+ request.getParameter("age") + "\n" +
"</ul>\n" +
"</body></html>");
}
}
|
ShowCookieDemo.html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>显示Cookie</title>
</head>
<body>
<form action="/ServletNotes/servlet/cookie/showCookieDemo"method="GET">
名字:<input type="text" name="name">
<br />
年龄:<input type="text" name="age"/>
<input type="submit"value="提交" />
</form>
</body>
</html>
|
访问http://localhost:8080/ServletNotes/ShowCookieDemo.html,提交输入文本后,能够看到cookie内容。
要读取 Cookies,您须要经过调用 HttpServletRequest的getCookies()方法建立一个 javax.servlet.http.Cookie对象的数组。而后循环遍历数组,并使用 getName() 和 getValue() 方法来访问每一个 cookie 和关联的值。
ReadCookies.java
package notes.javaee.servlet.cookie;
// 导入必需的 java 库
import java.io.*;
import javax.servlet.*;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.*;
// 扩展 HttpServlet 类
@WebServlet("/servlet/cookie/readCookies")
public class ReadCookies extends HttpServlet {
public void doGet(HttpServletRequest request,
HttpServletResponse response)
throws ServletException, IOException {
Cookie cookie = null;
Cookie[] cookies = null;
// 获取与该域相关的 Cookies 的数组
cookies = request.getCookies();
// 设置响应内容类型
response.setContentType("text/html;charset=UTF-8");
PrintWriter out = response.getWriter();
String title = "Reading Cookies Example";
String docType = "<!doctype html public \"-//w3c//dtd html 4.0 " +
"transitional//en\">\n";
out.println(docType +
"<html>\n" +
"<head><title>" + title + "</title></head>\n" +
"<body bgcolor=\"#f0f0f0\">\n");
if (cookies != null) {
out.println("<h2>查找 Cookies 名称和值</h2>");
for (int i = 0; i < cookies.length; i++) {
cookie = cookies[i];
out.print("名称:" + cookie.getName() + ",");
out.print("值:" + cookie.getValue() + " <br/>");
}
} else {
out.println("<h2>未找到 Cookies</h2>");
}
out.println("</body>");
out.println("</html>");
}
}
|
Java中并无提供直接删除Cookie的方法,若是想要删除一个Cookie,直接将这个Cookie的有效期设为0就能够了。步骤以下:
(1)读取一个现有的 cookie,并把它存储在 Cookie 对象中。
(2)使用 setMaxAge() 方法设置 cookie 的年龄为零,来删除现有的 cookie。
(3)把这个 cookie 添加到响应头。
DeleteCookieDemo.java
package notes.javaee.servlet.cookie;
// 导入必需的 java 库
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
// 扩展 HttpServlet 类
@WebServlet("/servlet/cookie/deleteCookieDemo")
public class DeleteCookieDemoextends HttpServlet {
private static final long serialVersionUID = 1L;
public void doGet(HttpServletRequest request,
HttpServletResponse response)
throws ServletException, IOException {
Cookie cookie = null;
Cookie[] cookies = null;
// 获取与该域相关的 Cookies 的数组
cookies = request.getCookies();
// 设置响应内容类型
response.setContentType("text/html");
response.setCharacterEncoding("utf-8");
PrintWriter out = response.getWriter();
String title = "Delete Cookies Example";
String docType = "<!doctype html public \"-//w3c//dtd html 4.0 " +
"transitional//en\">\n";
out.println(docType +
"<html>\n" +
"<head><title>" + title + "</title></head>\n" +
"<body bgcolor=\"#f0f0f0\">\n");
if (cookies != null) {
out.println("<h2>Cookies 名称和值</h2>");
for (int i = 0; i < cookies.length; i++) {
cookie = cookies[i];
if ((cookie.getName()).compareTo("name") == 0) {
cookie.setMaxAge(0);
response.addCookie(cookie);
out.print("已删除的 cookie:" + cookie.getName() + "<br/>");
}
out.print("名称:" + cookie.getName() + ",");
out.print("值:" + cookie.getValue() + " <br/>");
}
} else {
out.println(
"<h2 class=\"tutheader\">No cookies founds</h2>");
}
out.println("</body>");
out.println("</html>");
}
} |