一文搞定Servlet的基础知识

Java Servlet 是运行在服务器的程序,是客户端的请求和服务器的数据库之间的中间层,它的主要任务为:

  • 读取客户端的请求数据;
  • 访问数据库处理数据;
  • 发送响应数据到客户端;

1.HTTP协议基础

超文本传输协议(HyperText Transfer Protocol)——是客户端和服务器交互的一种通讯格式,它是TCP/IP协议的一个应用层协议。

例如:在浏览器输入一个地址或点击链接,浏览器会打开一个新的网页。

原理:浏览器得到一个链接,会向服务器发送一段文本(请求),告诉服务器请求打开某一网页;服务器接收到请求,会返回另一段文本(响应)给浏览器,浏览器接收解析后显示在界面。

不同版本的HTTP

  1. HTTP1.0协议:客户端和服务器建立连接后,只能获得一个Wed资源(获得即断开);
  2. HTTP1.1:客户端和服务器建立连接后,在一个连接上可获取多个资源(保持连接);

1.1 HTTP请求

浏览器向服务器请求某个Wed资源时,称为浏览器向服务器发送一个HTTP请求。一个完整的HTTP请求应包含三部分内容:

  • 请求行:请求方法 请求URI HTTP/版本号;
  • 多个消息头:描述客户端请求哪台主机,以及客户端的环境信息等内容;
  • 一个空行
GET和POST的区别
  1. 请求内容不同

    (1)GET方式
    GET /resource?key=value&key2=value2 HTTP/1.1
    消息头
    空行
    
    (2)POST方式
    POST /resource HTTP/1.1
    消息头
    空行
    请求实体(key=value)
    
  2. 用途不同

    GET POST
    链接/地址栏访问 form表单访问
    查询数据 提交数据
    提交数据容量有限制,通常不能超过1K 向服务器发送数据量无限制
    提交速度比POST方式快

常见请求头

Accept: text/html,image/* 【浏览器告诉服务器,它支持的数据类型】
Accept-Charset: ISO-8859-1 【浏览器告诉服务器,它支持哪种字符集】
Accept-Encoding: gzip,compress 【浏览器告诉服务器,它支持的压缩格式】
Accept-Language: en-us,zh-cn 【浏览器告诉服务器,它的语言环境】
Host: www.it315.org:80【浏览器告诉服务器,它的想访问哪台主机】
If-Modified-Since: Tue, 11 Jul 2000 18:23:51 GMT【浏览器告诉服务器,缓存数据的时间】
Referer: http://www.it315.org/index.jsp【浏览器告诉服务器,客户机是从那个页面来的---反盗链】
8.User-Agent: Mozilla/4.0 (compatible; MSIE 5.5; Windows NT 5.0)【浏览器告诉服务器,浏览器的内核是什么】
Cookie【浏览器告诉服务器,带来的Cookie是什么】
Connection: close/Keep-Alive 【浏览器告诉服务器,请求完后是断开链接还是保持链接】
Date: Tue, 11 Jul 2000 18:23:51 GMT【浏览器告诉服务器,请求的时间】

1.2 HTTP响应

服务器接收到浏览器的请求处理后,向浏览器回送数据称为HTTP响应

一个完整HTTP相应包含四个部分:

  • 状态行: HTTP/版本号 状态码 状态描述
  • 多个消息头
  • 一个空行
  • 实体内容
状态码

状态码用于表示服务器对请求的处理结果。它用一个三位的十进制数表示。响应状态码分为五类

状态码 描述
100~199 表示成功接收请求,要求客户端继续提交下一次请求才能完成整个处理结果
200~299 表示请求接收并已完成整个处理过程,常用200
300~399 未完成请求,客户端需进一步细化请求。例如,请求资源已经移动一个新地址。常用302、307和304
400~499 客户端的请求有错误,常用404
500~599 服务器端出现错误,常用500

常用响应头

Location: http://www.it315.org/index.jsp 【服务器告诉浏览器要跳转到哪个页面】
Server:apache tomcat【服务器告诉浏览器,服务器的型号是什么】
Content-Encoding: gzip 【服务器告诉浏览器数据压缩的格式】
Content-Length: 80 【服务器告诉浏览器回送数据的长度】
Content-Language: zh-cn 【服务器告诉浏览器,服务器的语言环境】
Content-Type: text/html; charset=GB2312 【服务器告诉浏览器,回送数据的类型】
Last-Modified: Tue, 11 Jul 2000 18:23:51 GMT【服务器告诉浏览器该资源上次更新时间】
Refresh: 1;url=http://www.it315.org【服务器告诉浏览器要定时刷新】
Content-Disposition: attachment; filename=aaa.zip【服务器告诉浏览器以下载方式打开数据】
Transfer-Encoding: chunked 【服务器告诉浏览器数据以分块方式回送】
Set-Cookie:SS=Q0=5Lb_nQ; path=/search【服务器告诉浏览器要保存Cookie】
Expires: -1【服务器告诉浏览器不要设置缓存】
Cache-Control: no-cache 【服务器告诉浏览器不要设置缓存】
Pragma: no-cache 【服务器告诉浏览器不要设置缓存】
Connection: close/Keep-Alive 【服务器告诉浏览器连接方式】
Date: Tue, 11 Jul 2000 18:23:51 GMT【服务器告诉浏览器回送数据的时间】

2.Servlet生命周期

Servlet 的方法:

  • init() 初始化Servlet
  • destory() 销毁Servlet
  • service() Servelt被访问时执行的方法
  • ServletConfig() Servlet配置
  • getServletInfo() Servlet信息

Servlet生命周期分为5个步骤

  1. 加载Servlet。服务器第一次访问Servlet时,Tomcat负责创建Servlet的实例;
  2. 初始化。Servlet被实例化后,Tomcat会调用 init()方法初始化对象;
  3. 处理服务。请求访问Servlet是,会调用 service() 处理请求;
  4. 销毁。当服务器关闭或自动调用Servlet的 destory() 方法,让Servlet实例释放所占资源的状态。一个Servlet长时间不被调用,会被Tomcat自动销毁。
  5. 卸载。Servlet调用完 destory() 方法后,等待垃圾回收的状态。此时可以重新调用 init() 方法进行初始化操作

Servlet的工作流程

Servlet的工作流程.png

2.1 Servlet的URI映射配置

  • 配置方式一:精准配置

    /别名

    注意:“ / ”是必须声明的,别名不可以为中文;可以配置多个 url-pattern

  • 配置方式二:模糊配置

    *.后缀名

    注意: 所有以指定的后缀名结尾的请求都会调用该 servlet 进行处理;* 表示任意个数的任意字符

    作用:进行模块化开发的划分等

  • 配置方式三:拦截所有请求

    /*

    注意:会拦截所有类型的请求,包括静态资源请求(CSS、JS、图片等)和 JSP 请求。

  • 配置方式四:

    /one/*

    注意:会拦截处理所有servlet的别名以 one 开头的路径的请求;

    一般域名后接的是虚拟项目名,而不是项目名。

注意:

  1. 一个 servlet 可以配置多个 url-pattern ,但不同的 servlet 不允许配置相同的 url-pattern
  2. 如果配置了相同的 url-pattern ,在服务器启动的时候就会报错——服务器启动的时候会将部署的项目中的 Wed.xml 文件加载进内存 ;

3.Servlet是单例的

什么是Servlet是单例的?

服务器在接收到浏览器的请求后,会开辟一个线程来处理客户端的此次请求,在线程中调用对应的 servlet 对象进行处理;

服务器在处理不同的浏览器的请求时,如果对每个请求都创建一个 servlet 对象来进行处理,会消耗大量内存。因此,服务器在处理不同请求只会创建一个 servlet 的实例化对象(该对象是线程共享的)。即Servlet一旦被创建,只存在一个对象,保留在内存中,直到服务器关闭

每次访问请求对象和响应对象都是新的

对于每次访问请求,Servlet引擎都会创建一个新的 HttpServletRequest 请求对象和 HttpServletResponse 响应对象,然后将两个对象作为参数传递给 Service() 方法,该方法在根据请求方式分别调用 doXXX()方法

线程安全问题

当多个用户访问Servlet时,服务器会为每个用户创建一个线程。当多个用户并发访问Servlet共享资源时,就会出现线程安全问题;

原则:

  1. 如果一个变量需要多个用户共享,则应当在访问该变量时,加同步机制 synchronized(对象){}
  2. 如果一个变量不需要共享,则直接在 doGet()doPost() 定义,则不存在线程安全问题;

4.启动时加载Servlet

在服务器启动时完成 servlet 的加载和初始化创建;

为什么要启动时加载

Servlet 对象是第一次被访问的时候被创建的,并调用执行 init 方法。假设在 init 方法中做了一些比较耗时的操作,那第一个访问的用户访问就会花费较长的时间;

什么是启动时加载

通过配置将 Servlet 的实例化过程放在服务器启动时


        myservlet
        lai.firstServlet.MyFirstServlet
        1

5.doGet()、doPost()以及service()方法的区别

不管是 get 方式还是 post 方式的请求,如果 Servlet 类中有service() 方法,则优先调用 Service 方法;

doGet():在没有 service 方法的情况下, get 方式的请求所调用处理请求的方法;

doPost():在没有 service 方法的情况下, post 方式的请求所调用处理请求的方法;

6.ServletConfig对象

读取wed.XML配置文件的初始化参数。

//使用Servlet对象中的 getServletConfig()获取该对象
ServletConfig sc = new XxxServlet().getServletCOnfig()

//通过ServletCOnfig对象获取配置文件中Servlet参数
String value = sc.getInitParamter("key")

7.ServletContext对象

定义 Servlet 用于与其 Servlet 容器进行通信的一组方法。它是服务器中的一个域对象被所有 Servlet 共享,可以处理不同 Servlet 之间的数据传输、通讯

7.1 Servlet之间实现通讯

//(1)创建或获取ServletContext对象,无则创建,有则获取
ServletContext scon = XxxServlet.getServletContext();

//(2)设置或修改域中属性
scon.setAttribute(key,value);

//(3)获取域中属性(根据key)
Ooject o = scon.getAttribute(key);

7.2 ServletContext对象获取配置信息

使用 wed.xml 配置文件,可以为 ServletContext 对象设置参数信息,此参数可以被服务器下的 Servlet 调用。


    key
    value

通过在 wed.xml 文件配置好参数后,可以在 Servlet 中调用,获取方式如下:

ServletContext scon = XxxServlet.getServletContext();

//获取值
String value = scon.getInitParamter("key");

8. Request和Response对象

当客户端向服务器发送一个请求,服务器会为该请求创建一个 HttpServletRequest 对象和 HttpServletResponse 对象。

HttpServletRequest对象封装了读取 HTTP 请求的方法,包含获取请求方法,获取请求URI、获取请求头等;

序号 方法 & 描述
1 Cookie[] getCookies() 返回一个数组,包含客户端发送该请求的所有的 Cookie 对象。
2 Enumeration getAttributeNames() 返回一个枚举,包含提供给该请求可用的属性名称。
3 Enumeration getHeaderNames() 返回一个枚举,包含在该请求中包含的所有的头名。
4 Enumeration getParameterNames() 返回一个 String 对象的枚举,包含在该请求中包含的参数的名称。
5 HttpSession getSession() 返回与该请求关联的当前 session 会话,或者如果请求没有 session 会话,则创建一个。
6 HttpSession getSession(boolean create) 返回与该请求关联的当前 HttpSession,或者如果没有当前会话,且创建是真的,则返回一个新的 session 会话。
7 Locale getLocale() 基于 Accept-Language 头,返回客户端接受内容的首选的区域设置。
8 Object getAttribute(String name) 以对象形式返回已命名属性的值,如果没有给定名称的属性存在,则返回 null。
9 ServletInputStream getInputStream() 使用 ServletInputStream,以二进制数据形式检索请求的主体。
10 String getAuthType() 返回用于保护 Servlet 的身份验证方案的名称,例如,"BASIC" 或 "SSL",如果JSP没有受到保护则返回 null。
11 String getCharacterEncoding() 返回请求主体中使用的字符编码的名称。
12 String getContentType() 返回请求主体的 MIME 类型,如果不知道类型则返回 null。
13 String getContextPath() 返回指示请求上下文的请求 URI 部分。
14 String getHeader(String name) 以字符串形式返回指定的请求头的值。
15 String getMethod() 返回请求的 HTTP 方法的名称,例如,GET、POST 或 PUT。
16 String getParameter(String name) 以字符串形式返回请求参数的值,或者如果参数不存在则返回 null。
17 String getPathInfo() 当请求发出时,返回与客户端发送的 URL 相关的任何额外的路径信息。
18 String getProtocol() 返回请求协议的名称和版本。
19 String getQueryString() 返回包含在路径后的请求 URL 中的查询字符串。
20 String getRemoteAddr() 返回发送请求的客户端的互联网协议(IP)地址。
21 String getRemoteHost() 返回发送请求的客户端的完全限定名称。
22 String getRemoteUser() 如果用户已通过身份验证,则返回发出请求的登录用户,或者如果用户未通过身份验证,则返回 null。
23 String getRequestURI() 从协议名称直到 HTTP 请求的第一行的查询字符串中,返回该请求的 URL 的一部分。
24 String getRequestedSessionId() 返回由客户端指定的 session 会话 ID。
25 String getServletPath() 返回调用 JSP 的请求的 URL 的一部分。
26 String[] getParameterValues(String name) 返回一个字符串对象的数组,包含所有给定的请求参数的值,如果参数不存在则返回 null。
27 boolean isSecure() 返回一个布尔值,指示请求是否使用安全通道,如 HTTPS。
28 int getContentLength() 以字节为单位返回请求主体的长度,并提供输入流,或者如果长度未知则返回 -1。
29 int getIntHeader(String name) 返回指定的请求头的值为一个 int 值。
30 int getServerPort() 返回接收到这个请求的端口号。
31 int getParameterMap() 将参数封装成 Map 类型。

HttpServletResponse对象封装了设置 HTTP 响应报头的方法。

序号 方法 & 描述
1 String encodeRedirectURL(String url) 为 sendRedirect 方法中使用的指定的 URL 进行编码,或者如果编码不是必需的,则返回 URL 未改变。
2 String encodeURL(String url) 对包含 session 会话 ID 的指定 URL 进行编码,或者如果编码不是必需的,则返回 URL 未改变。
3 boolean containsHeader(String name) 返回一个布尔值,指示是否已经设置已命名的响应报头。
4 boolean isCommitted() 返回一个布尔值,指示响应是否已经提交。
5 void addCookie(Cookie cookie) 把指定的 cookie 添加到响应。
6 void addDateHeader(String name, long date) 添加一个带有给定的名称和日期值的响应报头。
7 void addHeader(String name, String value) 添加一个带有给定的名称和值的响应报头。
8 void addIntHeader(String name, int value) 添加一个带有给定的名称和整数值的响应报头。
9 void flushBuffer() 强制任何在缓冲区中的内容被写入到客户端。
10 void reset() 清除缓冲区中存在的任何数据,包括状态码和头。
11 void resetBuffer() 清除响应中基础缓冲区的内容,不清除状态码和头。
12 void sendError(int sc) 使用指定的状态码发送错误响应到客户端,并清除缓冲区。
13 void sendError(int sc, String msg) 使用指定的状态发送错误响应到客户端。
14 void sendRedirect(String location) 使用指定的重定向位置 URL 发送临时重定向响应到客户端。
15 void setBufferSize(int size) 为响应主体设置首选的缓冲区大小。
16 void setCharacterEncoding(String charset) 设置被发送到客户端的响应的字符编码(MIME 字符集)例如,UTF-8。
17 void setContentLength(int len) 设置在 HTTP Servlet 响应中的内容主体的长度,该方法设置 HTTP Content-Length 头。
18 void setContentType(String type) 如果响应还未被提交,设置被发送到客户端的响应的内容类型。
19 void setDateHeader(String name, long date) 设置一个带有给定的名称和日期值的响应报头。
20 void setHeader(String name, String value) 设置一个带有给定的名称和值的响应报头。
21 void setIntHeader(String name, int value) 设置一个带有给定的名称和整数值的响应报头。
22 void setLocale(Locale loc) 如果响应还未被提交,设置响应的区域。
23 void setStatus(int sc) 为该响应设置状态码。

9.重定向和请求转发

9.1 重定向

什么是重定向? ——当浏览器向服务器发送一个请求,服务器通知浏览器跳转请求另一个页面的过程

重定向的实现过程 ——重定向过程中,浏览器会发送两次请求,第一次是浏览器根据链接或网址主动请求,第二次是服务器通知浏览器再次发送请求。前者,响应返回302状态码和跳转地址;后者,返回200状态和响应内容

//设置状态码为302
//HttpServletResponse将常用的状态码风状态成静态常量,直接调用使用就可以了
response.setStatus(HttpServletResponse.SC_MOVED_TEMPORARILY);

//设置跳转地址
response.setHeader("Location","跳转的地址");
//------------------------------------------
resp.sendRedirect("/请求JSP or Servlet")

其实,sendRedirect() 方法就是对 setStatus() 和 setHeader() 的封装

9.2 请求转发

请求转发也可以实现页面的转发。实现方式如下:

request.getRequestDispatcher("/请求JSP or Servlet").forward(request,response);

请求转发是服务器进行跳转的。一次请求实现多个页面或 servlet 的跳转;这多个页面或 servlet 的跳转共用同一个 request 和 response ,因此,请求转发可以通过 request 和 ServletContext作为数据流转的载体。

需注意:请求转发前不可向浏览器写入数据内容,Tomcat后台会产生 IllegalStateException 异常。

//在请求转发之前,向浏览器写入数据
ServletOutputStream outputStream = resp.getOutputStream();
outputStream.write("hello world".getBytes());
outputStream.close();

//请求转发
req.getRequestDispatcher("/display.jsp").forward(req,resp);

异常结果

请求转发时异常.png

9.3 请求转发和重定向的区别

请求转发 重定向
由服务器进行跳转,浏览器地址栏不发生变化 由浏览器进行跳转,浏览器地址栏发生改变
跳转中只有一次请求,且共用同一个request和response对象 有两次请求,无法共用同一个request和response对象
req.getRequestDispatcher("/资源").forward(req,resp); resp.sendRedirect("/项目/资源");
只能跳转当前项目下的资源 可以跳转任何资源
可以传递各种类型数据,包括对象 只能传递字符串
执行到跳转语句时立即跳转 整个页面执行完再执行跳转动作

10.会话技术

指用户打开一个浏览器,访问一个网站,只要不关闭该浏览器,不管该用户点击多少个超链接,访问多少资源,直到用户关闭浏览器,整个该过程称为一次会话。

场景应用:登录界面的自动登录;商场的推荐喜欢商品等

会话跟踪技术有 Cookie 和 Session 。

10.1 Cookie

Ⅰ 什么是Cookie
  • 网页之间的交互是基于 HTTP 协议传出数据,而HTTP协议是无状态(即一旦数据提交完,浏览器和服务器的连接就关闭,再次交互会重新建立新的连接)
  • 服务器无法确认用户信息。W3C提出:给每个用户发一个通行证,无论客户访问时都携带通行证,服务器以此确认用户信息;
  • Cookie 的流程:浏览器访问服务器,如果服务器需要记录该用户的状态,就使用 response 向浏览器发送一个 Cookie,浏览器将 Cookie保存起来;当浏览器再次访问服务器时,浏览器会把请求地址连同 Cookie 一同交给服务器;
Ⅱ Cookie API

Cookie类用于创建一个Cookie对象
response接口中定义addCookie方法,用于在响应头中添加一个相应的 Set-Cookie头字段
request接口中定义getCookie方法,用于获取客户端提交的Cookie

常用Cookie方法

Cookie常用方法.png
Ⅲ 设置有效期

Cookie 文件通过 setMaxAge 方法设置有效期。

  • 当 MaxAge 为正数时,浏览器会将 Cookie 写到磁盘中保存;无论关闭浏览器或电脑,Cookie 在有效时间内都有效
  • 当 MaxAge 为负数时,Cookie 是临时性的,仅在本浏览器内有效,关闭浏览器 Cookie 就失效,也不会写到磁盘中;
  • 如果 MaxAge 为 0,则表示 删除 Cookie
Ⅳ Cookie的修改

如要修改原有 Cookie 的值,则创建一个名称相同的、新的 Cookie,并添加到浏览器中,则会覆盖原有 Cookie;需注意:新创建的 Cookie 中出value、MaxAge之外的所有属性均要与原 Cookie 相同;否则浏览器会视为不同的 Cookie

Ⅴ 不可夸域名性

Cookie是不可跨域名的。即,访问 baidu 网站产生的 Cookie,不会在访问 Google 时被携带;浏览器判断一个网站能否操作另一个网站的 Cookie 的依据是域名。

但是,Cookie 的 demain属性决定运行访问 Cookie 的域名。可以通过 Cookie.setDomain("域名");方法规定 Cookie 能够被哪些域名的网页访问

除此之外,Cookie 中的 path 属性决定允许访问 Cookie 的路径

  • 一般,Cookie 发布后,整个网页的资源都可以使用;
  • 如果想让指定的资源才能获取 Cookie,则使用 setPath() 方法来指定访问 Cookie 的资源路径;
Ⅵ 传递中文编码问题

创建 Cookie 时存入中文会产生乱码。原因是:中文属于Unicode字符,占4个或三个字符,英文为 ASCII字符,占2个字符;

解决

//在存入中文数据时,先将中文进行编码
Cookie c = new Cookie("name",URLEncode.encode("value",charset));

//中文解码
URLEncode.decode(Cookie.getValue(),charset);

10.2 Session

Session是另一种记录浏览器状态的机制。与Cookie不同的是,Cookie 保存在浏览器,Session 保存在服务器中。用户使用浏览器访问服务器时,服务器把用户的信息以某种形式记录在服务器中。

Session 比 Cookie 更方便,Session可以解决 Cookie 解决不了的事情【Session 可以存储对象,Cookie 只能存储字符串】。

常用方法

Session常用方法.png
Ⅰ域对象
  • Session也是一个域对象。只要 Session 对象没有被销毁,servlet 之间就可以通过 Session 对象实现通讯
  • 一般来讲,当存进去的是用户级别的数据就用 Session。只要浏览器不关闭,希望数据还在,就使用 Session 来保存
Ⅱ 生命周期
  1. Session 在用户第一次访问服务器 Servlet、JSP等动态资源时被自动创建,Session 对象保存在内存里;
  2. 访问 HTML、IMAGE 等静态资源,Session对象不会被创建;
  3. Session生成后,只要有用户继续访问,服务器就会更新 Session 的最后访问时间(无论是否对 Session 进行读写);
  4. 服务器会将长时间没有活跃的 Session 从内存中删除,即 Session 的超时时间;

设置Session有效期

Session 的默认失效时间为30分钟。可以通过以下方式修改 Session 有限期:

  1. 在Tomcat/conf/web.xml文件中设置时间长度,对所有WEB应用都有效;

    
     **
    
    
  2. 在项目目录下的 web.xml文件中设置,对单个WEB应用有效;若与上述方式冲突,以此为准;

    
     **
    
    
  3. 通过方法 setMaxInactiveInterval() 方法设置;

    //设置Session最长超时时间,单位为秒
    httoSession.setMaxInactiveInterval(**);
    

Session 有效期指的是不活动时间,即在一段时间内不访问资源或网页即 Session 对象失效;而 Cookie 有效期则以创建时间起计算,无论用户是否访问;

Ⅲ Session原理

HTTP 是无状态的,Session 不能依据 HTTP 连接来判断是否为同一个用户。于是,服务器向用户浏览器发送了一个名为 JESSIONID 的Cookie,它的值是 Session 的 id 值,也就是说,Session 依据 Cookie 来识别是否为同一个用户

当用户在访问某个 Servlet 时,服务器创建一个 Session对象,并颁发一个 Cookie 给用户浏览器。用户用相同浏览器访问时,服务器根据 Cookie 中 JESSIONID 值来判断哪个 Session;

Ⅳ 禁用Cookie后,Session的使用

当浏览器禁用Cookie之后,那么我们的jsessionid就不能在浏览器中保存,那么后面的请求中就不会将 jsessionid 发送到服务器,服务器这面就找不到数据。解决方案如下:

  1. 在url后手动的拼接上 jsessionid

    传递格式如 /path/Servlet;jsessionid=sessionid

  2. 使用响应对象中的 encodeURL(String path) 实现 jsessionid 的自动拼接 String path = resp.encodeURL("path/Servlet");

10.3 Session和Cookie的区别

Session Cookie
相当于容器,可以存储任意类型数据 只能存储字符串,对非ASCII字符串需要进行编码
存储在服务器,客户端不可见 存储在浏览器,客户端可见
基于一次会话,关闭浏览器即失效 设置Maxage为正数时,在磁盘中保存,直至时间到期
并发访问用户很多时,会占用服务器大量内存 保存在客户端,不会占用服务器资源
禁用 Cookie ,可通过 URL 地址重写进行会话跟踪 禁用Cookie,即无法使用
只在当前域名内有效 可设置domain属性实现跨域名

参考文章

  • 菜鸟教程-Servlet
  • java3y - GitHub
    可关注大佬微信公众号:java3y

你可能感兴趣的:(一文搞定Servlet的基础知识)