Servlet是基于Java语言的Web服务器编程技术,是Sun公司提出的一种实现动态网页的解决方案。Servlet程序是一个运行在服务器中的特殊Java类,它能够处理来自客户端的请求并生成相应。其实servlet就是继承了HttpServlet、复写了service的Java类。

一、使用

1、创建普通的Java类并继承HttpServlet

2、复写service方法

3、在service方法中书写逻辑代码

4、在webContent下的WEB-INF文件夹下的web.xml文件中配置servlet

二、把tomcat集成到eclipse

Window -> Preferences-->Server-->Runtime Enviroments,点击右侧的Add

选择自己下载的tomcat的版本,Next

选择自己tomcat的路径,finish就好了。


三、第一个servlet

Java类:

package com.servlet;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class MyServlet extends HttpServlet{
    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) 
            throws ServletException, IOException {
        resp.getWriter().write("it is my first servlet");
        System.out.println("it is my first servlet.");
    }
}


Web.xml配置文件:

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd" id="WebApp_ID" version="4.0">
  <!-- 配置Servlet -->
      <!-- 配置servlet类路径 -->
      <servlet>
          <servlet-name>my</servlet-name>
          <servlet-class>com.servlet.MyServlet</servlet-class>
      </servlet>
      <!-- 配置访问方式 -->
      <servlet-mapping>
          <servlet-name>my</servlet-name>
          <url-pattern>/my</url-pattern>
      </servlet-mapping>
</web-app> 

url的组成:

http://localhost:8080/MyServlet/my
服务器地址:端口号/类名/servlet别名

报错:

404:没找到这个类
500:找到了没这个类

eclipse报404


四、servlet的生命周期

1、从第一次调用到服务器关闭

2、如果Servlet在web.xml中配置了load-on-startup,生命周期为从服务器启动到服务器关闭

servlet:

package com.servlet;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class Servletlife extends HttpServlet {
	@Override
	public void init() throws ServletException {
		System.out.println("servlet初始化完成");
	}
	@Override
	protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
		resp.getWriter().write("servlet life");
		System.out.println("servlet life");
	}
	@Override
	public void destroy() {
		System.out.println("俺被销毁了");
	}
}

web.xml:


<servlet>
    <servlet-name>life</servlet-name>
  	<servlet-class>com.servlet.Servletlife</servlet-class>
  	<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
  	<servlet-name>life</servlet-name>
  	<url-pattern>/life</url-pattern>
</servlet-mapping>

五、doGet方法和doPost方法

1、doGet:此方法被本类的service()调用,用来处理一个GET请求;

2、doPost:此方法被本类的service()调用,用来处理一个POST请求;

不管是get方式还是post方式,如果servlet类中有service方法,都会优先调用service方法。

3、Servlet常见错误:

404:资源未找到,未找到项目

500:内部服务器错误,未找到类

405:请求方式不支持,请求方式和servlet中的方法不匹配

六、request对象学习

1、作用

    request对象中封存了当前请求的所有请求信息

2、使用

(1)获取请求行数据

       getMethod()     //获取请求方式

       getRequestURL()   //获取请求URL

       getRequestURI()   //获取URI

       getScheme()       //获取协议

(2)获取请求头数据

       getHeader()    //获取指定的请求头信息

       getHeaderNames()   //获取所有的请求行的键的枚举

(3)获取用户数据

       getParameter()    //获取用户数据

       req.getParameterValues()   返回同键不同值的数据

注意:如果请求数据不存在,不会把错而是返回null

注意:request对象由tomcat服务器创建,并作为实参传递给处理请求的servlet的service方法

package com.servlet;

import java.io.IOException;
import java.util.Enumeration;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;


public class RequestServlet extends HttpServlet {
   @Override
	protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
		//获取请求行数据
		   //获取请求方式
		   		String method = req.getMethod();
		   		System.out.println(method);
		   //获取请求URL
		   		StringBuffer url = req.getRequestURL();
		   		System.out.println(url);
		   	//获取URI
		   		String uri = req.getRequestURI();
		   		System.out.println(uri);
		   //获取协议
		   		String h = req.getScheme();
		   		System.out.println(h);
		   		
		//获取请求头数据
		   		//获取指定的请求头信息
		   		String value = req.getHeader("Accept");
		   		System.out.println(value);
		   		//获取所有的请求行的键的枚举
		   		Enumeration e = req.getHeaderNames();
		   		while(e.hasMoreElements()) {
		   			String name = (String) e.nextElement();
		   			String value2 = req.getHeader(name);
		   			System.out.println(name+":"+value2);
		   		}
		//获取用户数据
		   		String name = req.getParameter("uname");
		   		String pwd = req.getParameter("pwd");
		   		System.out.println(name+":"+pwd);
		   		//返回同键不同值的数据
		   		String[] favs = req.getParameterValues("fav");
		   		if(favs!=null) {
		   			for(String fav:favs) {
		   				System.out.println(fav);
		   			}
		   		}
	}
}

使用的一个jsp来写了一个表单:

<%@ page language="java" contentType="text/html; charset=utf-8"
    pageEncoding="utf-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Insert title here</title>
</head>
<body>
	<form action="request" method="get">
		用户名:<input type="text" name="uname" value=""></br>
		密码:<input type="test" name="pwd" value=""></br>
		爱好: </br>
			<input type="checkbox" name="fav" value="1">唱</br>
			<input type="checkbox" name="fav" value="2">跳</br>
			<input type="checkbox" name="fav" value="3">rap</br>
		<input type="submit" value="登录">
	</form>
</body>
</html>

结果:

 

七、Response对象

       响应处理结果

1、设置响应头

resp.setHeader(String name,String value);   //在响应头添加响应信息,但同键会覆盖

resp.addHeader(String name,String value); //在响应头添加响应信息,同键不会覆盖

2、设置响应编码格式

resp.setContentType("text/html;charset=utf-8");

3、设置值响应状态码

resp.sendError(int num,String msg); //自定义响应状态码

4、设置响应实体

resp.getWriter().write(String str);  //响应具体的数据给浏览器

5、service请求处理响应代码流程:

设置响应编码格式

获取请求数据

处理请求数据

响应处理结果

代码:

package com.servlet;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class ResponseServlet extends HttpServlet {
	@Override
	protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
		//相应处理结果
			//设置响应头
			resp.setHeader("fruit", "banana");
			resp.addHeader("food", "hotpot");
			//设置响应编码格式
			//resp.setContentType("text/plain;charset=utf-8");
			//resp.setContentType("text/xml;charset=utf-8");
			resp.setContentType("text/html;charset=utf-8");
			//设置值响应状态码
			//resp.sendError(404, "sorry");
			//设置响应实体
			resp.getWriter().write("<b>今天天气真好,但是我出不去</b>");
	}
}

效果:

6、Servlet流程总结:

浏览器发起请求到服务器(请求)

服务器接收浏览器的请求,进行解析,创建request对象存储请求数据

服务器调用对应的servlet进行请求处理,并将request对象作为实参传递给servlet的方法

servlet的方法执行进行请求处理

      设置请求编码格式

      设置响应编码格式

      获取请求信息

      处理请求信息
                     创建业务层对象
                     调用业务层对象的方法
       响应处理结果


7、请求转发学习:

作用:实现多个servlet联动操作处理请求,这样避免代码冗余,让servlet的职责更加明确

           req.getRequestDispatcher(要转发的地址).forword(req,resp);

特点:一次请求,浏览器地址不变

注意:请求转发后直接return结束即可

8、request作用域

        一次请求中的所有servlet

作用:解决了一次请求内不同servlet的数据(请求数据+其他数据)共享问题

数据流转:

request.setAttribute(Object name,Object value);

request.getAttribute(Object obj)

9、重定向

       解决了表单重复提交的问题,以及当前servlet无法处理的请求的问题

使用:resp.sendRedirect(String uri)

例:resp.sendRedirect("/login/main"); //login后重定向到main

特点:

两次请求,两个request对象

浏览器地址栏改变

使用时机:

如果请求中有表单数据,而数据有比较重要,不能重复提交,建议使用重定向

如果请求被servlet接收后,无法进行处理,建议使用重定向定位到可以处理的资源


八、Cookie技术

1、作用:

解决了发送的不同请求的数据共享问题

2、使用:

(1)Cookie的创建和存储

      创建Cookie对象

              Cookie c = new Cookie(String name,String value);

      设置Cookie

             设置有效期:c.setMaxAge(int seconds);  //Cookie的有效期

             设置有效路径:c.setPath(String uri);  //该路径下携带Cookie

      响应Cookie信息给客户端

             resp.addCookie(c)

(2)Cookie的获取

              获取Cookie信息数组

                  Cookie[] cks = req.getCookies();

              遍历数组获取Cookie信息,使用for循环即可

                  if(cks!=null){

                          for(Cookie c:cks){

                                String name = c.getName();

                                String value = c.getValue();

                                System.out.println(name+":"+value);

                           }

                     }

注意:

一个Cookie对象存储一条数据。多条数据,可以多建几个Cookie对象存储

package com.servlet;

import java.io.IOException;

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;

public class CookieServlet extends HttpServlet {
	protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
		//设置请求编码格式
		req.setCharacterEncoding("utf-8");
		//设置响应编码格式
		resp.setContentType("text/html;charset=utf-8");
		//获取请求信息
		
		//处理请求信息
		//相应处理结果
			//使用Cookie进行浏览器端的数据存储
				//创建Cookie对象
				Cookie c = new Cookie("food","hotpot");
				Cookie c2 = new Cookie("fruit","banana");
				//设置Cookie
					//设置Cookie有效期(三天)
					c2.setMaxAge(3*24*3600);
				//响应Cookie信息
					resp.addCookie(c);
					resp.addCookie(c2);
		//直接响应
		resp.getWriter().write("Cookie学习");
		
	}
}

3、特点:

浏览器端的数据存储技术

存储的数据声明在服务器端

临时存储:存储在浏览器的运行内存中,浏览器关闭即失效

定时存储:设置了Cookie的有效期,存储在客户端的硬盘中,在有效期内符合路径要求的请求都会附带该信息

默认cookie信息存储好之后,每次请求都会附带,除非设置有效路径

九、session技术

1、原理:

用户第一次访问服务器,服务器会创建一个session对象给此用户,并将该session对象的JSESSIONID使用Cookie技术存储到浏览器中,保证用户的其他请求能够获取到同一个session对象,也保证了不同请求能够获取到共享的数据。

2、特点:

存储在服务器端

服务器进行创建

依赖Cookie技术

一次会话

默认存储时间是30分钟

3、作用:

解决了一个用户不同请求处理的数据共享问题

4、使用:

(1)创建session对象/获取session对象 

      HttpSession hs = req.getSession();

      如果请求中拥有session的标识符也就是JSESSIONID,则返回其对应的session对象

      如果请求中没有session的标识符也就是JSESSIONID,则创建新的session对象,并将其JSESSIONID作为从cookie数据存储到浏览器内存中

      如果session对象是失效的,也会重新创建一个session对象,并将其JSESSIONID存储到浏览器内存中

(2)设置session存储时间

     hs.setMaxInactiveInterval(int seconds);

     注意:在指定的时间内session对象没有被使用则被销毁,如果使用了则重新计时

3)设置session强制失效

     hs.invalidate();

注意:

JSESSIONID存储在了cookie的临时存储空间中,浏览器关闭即失效

使用:

package com.servlet;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

public class SessionServlet extends HttpServlet {
	@Override
	protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
		req.setCharacterEncoding("utf-8");
		resp.setContentType("text/html;charset=utf-8");
		
		//获取请求信息
		String name = "张三";
		//处理请求信息
			//创建session对象
			HttpSession hs = req.getSession();
			//设置session存储时间(5s)
			hs.setMaxInactiveInterval(5);
			System.out.println(hs.getId());
			//设置session强制失效
			hs.invalidate();
		//响应处理结果
		resp.getWriter().write("session学习");
	}
}

5、存储和获取数据:

存储:hs.setAttribute(String name,Object value);

获取:hs.getAttribute(String name);返回的数据类型为Object

注意:存储的动作和取出的动作发生在不同请求中,但是存储要先于取出
使用时机:
       一般用户在登陆web项目时会将用户的个人信息存储到Session中,供该用户的其他请求使用

6、总结:

       session解决了一个用户的不同请求的数据共享问题,只要在JSESSIONID不失效和session对象不失效的情况下。用户的任意请求在处理时都能获取到同一个session对象。

作用域

        一次会话

        在JSESSIONID和SESSION对象不是小的情况下为整个项目内

session失效处理:

        将用户请求中的JSESSIONID和后台获取到的SESSION对象的JSESSIONID精选比对,如果一致则session没有失效,如果不一致则证明session失效了。重定向到登陆页面,让用户重新登陆。

十、ServletContext

1、特点:

服务器创建

用户共享

2、作用域:

整个项目内

3、生命周期:

服务器启动到服务器关闭

4、使用:

(1)获取ServletContext对象

       第一种方法

       ServletContext sc =  (ServletContext) this.getServletContext();

      第二种方法

      ServletContext sc2 =  (ServletContext) this.getServletConfig().getServletContext();

     第三种方法 

     ServletContext sc3 =  (ServletContext) req.getSession().getServletContext();

2)使用ServletContext对象完成数据共享

     数据存储

     sc.setAttribute("str","ServletContext对象学习");

     数据获取

     sc.getAttribute("str")

注意:不同的用户可以给ServletContext对象对象进行数据的存取

          获取的数据不存在返回null

(3)获取项目中web.xml文件中的全局配置数据

     sc.getInitParameter(String name);

    根据键的名字返回web.xml中配置的全局数据的值,返回String类型。如果数据不存在返回null

    sc.getInitParameterNames(); 返回键名的枚举

    配置方式:

   <context-param>

         <param-name>name</param-name>

        <param-value>zhangsan</param-value>

  </context-param>

注意:一组<context-param>标签只能存储一组键值对数据,多组可以声明多个<context-param>进行存储

作用:将静态数据和代码进行解耦

(4)获取项目webroot下的资源的绝对路径

     String path = sc.getRealPath(String path);

     获取的路径为项目根目录,path参数为项目根目录中的路径

(5)获取webroot下的资源的流对象

     InputStream is = sc.getResourceAsStream(String path);

     注意:此种方式只能获取项目根目录下的资源流对象,class文件的流对象需要使用类加载器获取

小结:

request:一次请求中的数据共享

session:用户不同请求中的数据共享

ServletContext:不同用户的数据共享

十一、ServletConfig

         获取在web.xml中给每个servlet单独配置的数据

使用:

获取Servlet Config对象

SercletConfig sc = this.getServletConfig();

获取web.xml中的配置数据

String code = sc.getInitParameter("config");

十二、web.xml:

Web项目下的web.xml文件为局部配置,针对本项目的位置。

Tomcat下的web.xml文件为全局变量,配置公共信息。

加载时机:服务器启动时。

热部署:

    <Context path="/pet" reloadable="true" docBase="绝对路径" />

    放到server.xml的<Host>下

    路径下的文件必须存在,不存在的话就会报错

 

servlet重定向路径总结:

相对路径:从当前请求的路径查找资源的路径。

       相对路径如果servlet的别名中包含目录,则会造成重定向资源查找失败。

绝对路径:第一个/表示服务器根目录

       /虚拟项目名/资源路径

 

servlet请求转发:

/表示根目录

req.getRequestDispatcher("/资源路径").forward(req,resp);

Logo

CSDN联合极客时间,共同打造面向开发者的精品内容学习社区,助力成长!

更多推荐