JAVA WEB2——Servlet

JAVA WEB2——Servlet

Servlet(Server Applet)是Java Servlet的简称,称为小服务程序或服务连接器,是Java语言编写 的服务器端程序,换句话说,Servlet就是运行在服务器上的Java类。 Servlet用来完成B/S架构下客户端请求的响应处理,也就是交互式地浏览和生成数据,生成动态Web内容

1、第一个servlet程序(servlet)

1.1、实现Servlet

public class HelloServlet implements Servlet {
    @Override
    public void init(ServletConfig servletConfig) throws ServletException {
        System.out.println("servlet初始化");
    }

    @Override
    public ServletConfig getServletConfig() {
        return null;
    }

    @Override
    public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {
        System.out.println("servlet被访问了");
    }

    @Override
    public String getServletInfo() {
        return null;
    }

    @Override
    public void destroy() {
        System.out.println("servlet销毁");
    }
}
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
         version="4.0">
    <servlet>
        <servlet-name>hello</servlet-name>
        <servlet-class>HelloServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>hello</servlet-name>
        <url-pattern>/hello</url-pattern>
    </servlet-mapping>
</web-app>

1.2、继承GenericServlet

public class HelloServlet extends GenericServlet {

    @Override
    public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {
        System.out.println("servlet被访问了");
    }
}

1.3、继承HttpServlet

public class HelloServlet extends HttpServlet {
    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        System.out.println("servlet被访问了");
    }
}

1.4、Servlet注解

@WebServlet("/RuoyrServlet")
public class RuoyrServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("post");
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("get");
    }
}

2、Servlet的生命周期

创建(init): 用户第一次访问servlet创建servlet的实例.

销毁(destroy): 当项目从服务器移除,或服务器关闭的时候

3、请求参数的获取

方法声明 功能介绍
String getParameter(String name) 以字符串形式返回请求参数的值,如果该参数不存在,则返回空值
String[] getParameterValues( String name) 返回一个字符串对象数组,其中包含给定请求参数所具有的所有 值,如果该参数不存在,则返回空值
Enumeration getParameterNames() 返回包含此请求中包含的参数名称的字符串对象的枚举。如果请 求没有参数,则方法返回空枚举
Map getParameterMap() 返回请求参数的键值对,一个键可以对应多个值
String getRemoteAddr() 返回发送请求的客户端或最后一个代理的IP地址
int getRemotePort() 返回发送请求的客户端或最后一个代理的端口号
String getRequestURI() 返回此请求的资源路径信息
StringBuffer getRequestURL() 返回此请求的完整路径信息
String getMethod() 返回发出此请求的HTTP方法的名称,例如GET、POST
String getQueryString() 返回路径后面请求中附带的参数
String getServletPath() 返回此请求中调用servlet的路径部分

4、响应消息

@WebServlet("/RuoyrServlet")
public class RuoyrServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("post");
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("get");
        response.setCharacterEncoding("UTF8");
        response.setContentType("text/html;charset=utf-8");
        PrintWriter writer = response.getWriter();
        writer.write("我已收到请求");
    }
}

5、请求乱码处理

public class RuoyrServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("post");
        System.out.println(request.getParameter("name"));
        System.out.println(new String(request.getParameter("name").getBytes("ISO-8859-1"),"UTF8"));
        response.setCharacterEncoding("UTF8");
        response.setContentType("text/html;charset=utf-8");
        PrintWriter writer = response.getWriter();
        writer.write("我已收到请求");
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("get");
    }
}

6、ServletConfig、ServletContext

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
         version="4.0">
    <servlet>
        <servlet-name>hello</servlet-name>
        <servlet-class>HelloServlet</servlet-class>
        <init-param>
            <param-name>usernaame</param-name>
            <param-value>admin</param-value>
        </init-param>
    </servlet>
    <servlet-mapping>
        <servlet-name>hello</servlet-name>
        <url-pattern>/hello</url-pattern>
    </servlet-mapping>
    <context-param>
        <param-name>username</param-name>
        <param-value>ruoye</param-value>
    </context-param>
</web-app>
public class HelloServlet implements Servlet {

    @Override
    public void init(ServletConfig servletConfig) throws ServletException {
        System.out.println(servletConfig.getServletName());
        System.out.println(servletConfig.getInitParameter("username"));
        ServletContext servletContext = servletConfig.getServletContext();
        Enumeration<String> attributeNames = servletContext.getAttributeNames();
        while (attributeNames.hasMoreElements()){
            System.out.println(attributeNames.nextElement());
        }
    }

    @Override
    public ServletConfig getServletConfig() {
        return null;
    }

    @Override
    public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {

    }

    @Override
    public String getServletInfo() {
        return null;
    }

    @Override
    public void destroy() {

    }
}

7、重定向与请求转发

7.1、重定向

首先客户浏览器发送http请求,当web服务器接受后发送302状态码响应及对应新的location给客 户浏览器,客户浏览器发现是302响应,则自动再发送一个新的http请求,请求url是新的location 地址,服务器根据此请求寻找资源并发送给客户

启动向我借钱,我没有,我让启动去找洲洲借钱

  • 重定向之后,浏览器地址栏的URL会发生改变

  • 重定向过程中会将前面Request对象销毁,然后创建一个新的Request对象

  • 重定向的URL可以是其它项目工程

@WebServlet("/RuoyrServlet")
public class RuoyrServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("post");
        response.sendRedirect(request.getContextPath()+"/WinkToServlet");
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("get");
        this.doPost(request,response);
    }
}
@WebServlet("/WinkToServlet")
public class WinkToServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("我是重定向post");
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("我是重定向get");
    }
}

7.2、请求转发

一个Web组件(Servlet/JSP)将未完成的处理通过容器转交给另外一个Web组件继续处理,转发 的各个组件会共享Request和Response对象

启动向我借钱,我没有,我去找洲洲借钱给启动

  • 转发之后浏览器地址栏的URL不会发生改变
  • 转发过程*享Request对象
  • 转发的URL不可以是其它项目工程
@WebServlet("/RuoyrServlet")
public class RuoyrServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("post");
        RequestDispatcher requestDispatcher = request.getRequestDispatcher("/WinkToServlet");
        requestDispatcher.forward(request,response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("get");
        this.doPost(request,response);
    }
}
@WebServlet("/WinkToServlet")
public class WinkToServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("我是请求转发post");
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("我是请求转发get");
    }
}

7.3、重定向与转发的区别

JAVA WEB2——Servlet

8、Servlet多线程访问问题

  • 服务器在收到请求之后,会启动一个线程来进行相应的请求处理
  • 默认情况下,服务器为每个Servlet只创建一个对象实例。当多个请求访问同一个Servlet时,会有 多个线程访问同一个Servlet对象,此时就可能发生线程安全问题
  • 多线程并发逻辑,需要使用synchronized对代码加锁处理,但尽量避免使用

9、Cookie

  • Cookie本意为”饼干“的含义,在这里表示客户端以“名-值”形式进行保存的一种技术
  • 浏览器向服务器发送请求时,服务器将数据以Set-Cookie消息头的方式响应给浏览器,然后浏览器 会将这些数据以文本文件的方式保存起来
  • 当浏览器再次访问服务器时,会将这些数据以Cookie消息头的方式发送给服务器

9.1、cookie的使用

@WebServlet("/RuoyrServlet")
public class RuoyrServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) {
        //从请求中获取cookie
        Cookie[] cookies = request.getCookies();
        for (Cookie cookie : cookies) {
            System.out.println(cookie.getName()+"==="+cookie.getValue());
        }
        System.out.println("post");
        //创建cookie
        Cookie cookie = new Cookie("name", "zhangsan");
        //最大存活时间,单位为秒
        cookie.setMaxAge(60*60*24);
        //让响应携带cookie
        response.addCookie(cookie);

    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("get");
        this.doPost(request,response);
    }
}

9.2、cookie的生命周期

默认情况下,浏览器会将Cookie信息保存在内存中,只要浏览器关闭,Cookie信息就会消失,可以设置cookie存活时间(设为-1立即失效)

//最大存活时间,单位为秒
cookie.setMaxAge(60*60*24);

9.3、cookie路径问题

  • 浏览器在访问服务器时,会比较Cookie的路径与请求路径是否匹配,只有匹配的Cookie才会发送 给服务器
  • Cookie的默认路径等于添加这个Cookie信息时的组件路径,例如:/项目名/目录/add.do请求添加 了一个Cookie信息,则该Cookie的路径是 /项目名/目录

9.4、cookie的特点

  • 将状态数据保存在浏览器端,不安全
  • 保存数据量有限制,大约4KB左右
  • 只能保存字符串信息
  • 可以通过浏览器设置为禁止使用

10、Session

  • Session本意为"会话"的含义,是用来维护一个客户端和服务器关联的一种技术
  • 浏览器访问服务器时,服务器会为每一个浏览器都在服务器端的内存中分配一个空间,用于创建一 个Session对象,该对象有一个id属性且该值唯一,我们称为SessionId,并且服务器会将这个 SessionId以Cookie方式发送给浏览器存储
  • 浏览器再次访问服务器时会将SessionId发送给服务器,服务器可以依据SessionId查找相对应的 Session对象

10.1、session的使用

@WebServlet("/RuoyrServlet")
public class RuoyrServlet extends HttpServlet {
    protected void doPost(HttpServletRequest request, HttpServletResponse response) {
        HttpSession session = request.getSession();
        System.out.println(session.isNew());
        System.out.println(session.getId());
        session.setAttribute("name","zhangsan");
        //创建cookie
        Cookie cookie = new Cookie("JSESSIONID", session.getId());
        //最大存活时间,单位为秒
        cookie.setMaxAge(60*60*24);
        //让响应携带cookie
        response.addCookie(cookie);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("get");
        this.doPost(request,response);
    }
}

10.2、session的生命周期

  • 为了节省服务器内存空间资源,服务器会将空闲时间过长的Session对象自动清除掉,服务器默认 的超时限制一般是30分钟
  • 使用javax.servlet.http.HttpSession接口的成员方法实现失效实现的获取和设置
方法声明 功能介绍
int getMaxInactiveInterval() 获取失效时间
void setMaxInactiveInterval(int interval) 设置失效时间

可以配置web.xml文件修改失效时间(单位分钟)

<session-config>
    <session-timeout>60</session-timeout>
</session-config>

10.3、session的特点

  • 数据比较安全
  • 能够保存的数据类型丰富,而Cookie只能保存字符串
  • 能够保存更多的数据,而Cookie大约保存4KB
  • 数据保存在服务器端会占用服务器的内存空间,如果存储信息过多、用户量过大,会严重影响服务器的性能
上一篇:Keepalived和HAProxy


下一篇:麒麟V10系统-系统激活点击按钮无响应