zoukankan      html  css  js  c++  java
  • [Java拾遗四]JavaWeb基础之Servlet_Request&&Response

    [Java拾遗四]JavaWeb基础之Servlet_Request&&Response

     

    今天来回顾下之前学过Servle的Resquest以及Response的知识.
    1,Request和Response技术:

        rr的作用:
            request是请求,封装用户的请求信息.若想获取请求信息,找request就行了
            response是响应,封装服务器的响应信息,若想往页面写东西,找response就可以了
        rr的体系结构:
            request
            在servlet中有一个service(ServletRequest,ServletResponse)  抽象方法
            在HttpServlet中实现了service(ServletRequest,ServletResponse)
            并且重载了service(HttpServletRequest,HttpServletResponse)
            
            request的实现类 org.apache.catalina.connector.RequestFacade
            response的实现类 org.apache.catalina.connector.ResponseFacade
            
            request的体系
                ServletRequest(接口)
                    |
                    |
                HttpServletRequest(接口)
                    |
                    |
                RequestFacade(类 tomcat)
                
           response的体系
               ServletResponse(接口)
                    |
                    |
                HttpServletResponse(接口)
                    |
                    |
                ResponseFacade(类 tomcat)
    2,Response
       (1)作用:响应
            http响应的格式:
                响应行 响应头 响应体
        (2)简单介绍api
            操作响应行:
                响应行的格式:
                    协议/版本 状态码 状态码说明
                    HTTP/1.1 200 OK
                常用的方法:
                    setStatus(int)
                    sendError(int)
                    sendError(int,msg)
            操作响应头:
                响应头的格式:
                    key:name
                    key:name1,name2  --多个值的时候用逗号隔开
                常用的方法:
                    setHeader(string,string)
                    setIntHeader(string,int)
                    addHeader(string,string)
                    setDateHeader(string,long)
            操作响应体:
                响应题就是展示的内容
                    getOutputStream()
                    getWriter()
        (3)详解api
           a, 状态码:
                1xx:正在请求中
                2xx:完成请求响应
                    200:成功完成
                3xx:还需浏览器进一步操作
                    302:还需跳转
                    304:浏览器去读缓存
                4xx:用户请求错误
                    404:路径不存在
                5xx:服务器错误:
                    500:服务器错误

            常用方法:
                对于非错误的状态码
                    setStatus(int):例如 setStatus(304)
                对于的错误的状态码
                    sendError(int)
                    sendError(int,msg):返回错误的信息
            b,操作响应头:
                响应头的格式:
                    key:name
                    key:name1,name2  --多个值的时候用逗号隔开
                常用方法:
                    setHeader(String key,String name):给响应设置指定的头信息
                    addHeader(String key,String name1):若存在则追加,反之则设置
                    
                    setIntHeader(String key,int value):给响应设置指定的头信息(int类型的)
                    addIntHeader(String key,int value):若存在则追加,反之则设置
                    
                    setDateHeader(String key,Long long):给相应头设置毫秒值的
            案例:
                重定向:
                    302:还需要跳转
                    需要用到location
                    代码实现:
                        setStatus(302);
                        setHeader("location","跳转的路径");
                    开发中时使用
                        sendRedirect(跳转的路径);
                刷新:
                    response.setHeader("refresh","3;url=跳转的路径");
                    
                重定向和刷新最后的效果是一样的,同样是发送了两次请求
    代码案例:
    使用location跳转:

    public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        response.setStatus(302);
        //设置跳转路径
        response.setHeader("location","/dayaugmentum10/loca2");
    }

    使用refresh跳转:

    public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        response.setHeader("refresh", "3;url=/augmentum/1.html");
    }


       c,操作响应体:
            常用的方法:
            ServletOutputStream getOutputStream():字节流
            PrintWriter getWriter():字符流
            
            通过流对象.println(任意内容);
        字符乱码的处理
            设置响应信息的编码格式
                response.setCharacterEncoding("utf-8"):
            
            设置响应信息的编码格式并且通知浏览器用什么编码打开
                response.setHeader("content-type","text/html;charset=utf-8");
                开发中使用
                response.setContentType("text/html;charset=utf-8"); ☆
                
            在页面添加
            <meta http-equiv="Content-Type" content="text/html;charset=utf-8">
        注意事项(针对流)
            字节流和字符流是互斥的.
            tomcat会帮我们关闭流
        验证码:
            作用:防止恶意暴力破解密码

     验证码模版


    3,Request
        请求.若想获取请求信息,找我就可以了
        请求的格式:
            请求行 请求头 请求体
        (1)api简介
            a,请求行
                格式:请求方式 资源路径 协议/版本
                例如:GET /augmentum/1.html HTTP/1.1
                常用方法:
                    getMethod()
                    getRequestURI()
                    getProtocol()
                    getQueryString()
           b, 请求头
                格式:
                    key:name1[,name2]
                常用方法:
                    String getHeader(key)
                    Enumeration getHeaders(key)
                    Enumeration getHeaderNames();
                    
                    getIntHeaders(key)
           c, 请求体
                只有post才有请求体,存放就是post请求的参数
                例如 username=tom&password=123&hobby=eat&hobby=sleep
                常用方法:
                    String getParameter(key)
                    Enumeration getParameterNames()
                    Map<String,String[]> getParameterMap();
                    String[] getParameterValues(key);
                
        (2)api详解
            a,请求行:
                常用方法:
                    getMethod():获取请求的方式
                    getRequestURI():获取的从项目名开始到请求参数参数之前(?)
                    getProtocol():获取协议和版本
                    getQueryString():以字符串的形式获取请求参数
                    结果:    
                        GET
                        /augmentum/row
                        HTTP/1.1
                        login=tom&password=123

                        GET /augmentum/form.html HTTP/1.
                常见的请求方式:post和get
                    区别:
                      1.get请求的参数会出现在地址栏上,post不会,post相对安全
                      2.get请求参数的大小有限制,post理论上没有.
                      3.只有post有请求体.
                获取用户信息:
                    getRemoteAddr():获取用户ip
                    getRequestURL():获取请求路径(带协议的路径 URL)
                    getContextPath():获取项目名
                    结果: 
                        192.168.40.1xx
                        http://192.168.40.97/augmentum/row
                        /augmentum

    复制代码
     1 public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
     2     /*//获取请求方式
     3     String method = request.getMethod();
     4     System.out.println(method);
     5     //获取请求资源路径
     6     String uri = request.getRequestURI();
     7     System.out.println(uri);
     8     //获取协议版本
     9     String pro = request.getProtocol();
    10     System.out.println(pro);
    11     //获取get请求的请求参数
    12     String s = request.getQueryString();
    13     System.out.println(s);*/
    14     
    15     //获取用户ip
    16     String addr = request.getRemoteAddr();
    17     System.out.println(addr);
    18     //获取请求路径
    19     String url = request.getRequestURL().toString();
    20     System.out.println(url);
    21     //获取项目名
    22     String contextPath = request.getContextPath();
    23     System.out.println(contextPath);
    24 }
    复制代码

            b,请求头:
                格式:
                    key:name1[,name2]
                常用方法:
                    String getHeader(key):获取指定的头信息
                    int getIntHeader(key):
                    long getDateHeader(key):
                    Enumeration getHeaders(key):以Enumeration形式获取指定头的信息
                    Enumeration getHeaderNames();返回所有的请求头的名称
                防盗链
                    使用的 referer请求头

    复制代码
        String referer = request.getHeader("referer");
        if (referer==null) {
            System.out.println("地址栏来的 可以访问");
        }else if(referer.startsWith("http://localhost/augmentum")){
            System.out.println("站内访问");
        }else{
            System.out.println("站外访问");
        }
    }
    复制代码

            c,请求体:
                只有post请求才有,用来存放请求参数.
                get请求和post通用的方法:
                获取用户参数:
                    String getParameter(key):获取指定的参数信息
                    String[] getParameterValues(key):以string[]的格式返回指定的参数信息
                    
                    Map<String,String[]> getParameterMap();以map的形式返回所有的参数
                    Enumeration getParameterNames();以Enumeration形式返回所有的参数名称
                    
                    例如:
                        姓名:tom
                        爱好:[drink, sleep]
                        ----------------------
                        username:[tom]
                        password:[1234]
                        hobby:[drink, sleep]
                        ----------------------
                        username:[tom]
                        password:[1234]
                        hobby:[drink, sleep]

    复制代码
    public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        //获取姓名
        String username = request.getParameter("username");
        System.out.println("姓名:"+username);
        //获取爱好
        String[] hobby=request.getParameterValues("hobby");
        System.out.println("爱好:"+Arrays.toString(hobby));
        //获取所有
        System.out.println("----------------------");
        Map<String,String[]> map=request.getParameterMap();
        for (String name : map.keySet()) {
            System.out.println(name+":"+Arrays.toString(map.get(name)));
        }
        System.out.println("----------------------");
        //获取所有的参数名称
        Enumeration<String> params = request.getParameterNames();
        while(params.hasMoreElements()){
            
            String name = params.nextElement();
            System.out.println(name+":"+Arrays.toString(request.getParameterValues(name)));
        }
    }
    复制代码

           d,域对象:
                request:
                    一次请求中,响应之前.
                    请求串,请求链
                    request.getRequestDispatcher("转发路径").forward(request,response)
                    服务器内部跳转
                    客户端的路径:   /工程名/编写的路径
                    服务器的内部路径:   /编写的路径
                常用方法:
                    xxxAttribute()
                    setAttribute(String,Object);
                    Object getAttribute(String)
                    removeAttribute()
               

        请求转发与重定向的区别
           1.请求转发是服务器内部跳转,地址栏不会发生改变
            重定向地址栏会发生改变。

            2.请求转发,只有一次请求,一次响应.
            重定向,有两次请求,两次响应。

            3.请求转发存在request域,可以共享数据.
            重定向不存在request域。

            4.请求转发只能在服务器的内部跳转,简单说,只能访问本站内资源。
            重定向可以访问站外资源,也可以访问站内资源.

            5.请求转发是由request 发起的 . request.getRequestDispatcher().forward()
            重定向是由response 发起的  response.sendRedirect();

            6.请求转发与重定向时路径写法不一样.
            重定向要跳转的路径是从浏览器在次发起的,是浏览器端路径,写法: /工程名/资源
            请求转发是服务器内部跳转,这时它与浏览器无关 写法:/资源
    可用如下图来表示: 
    reqAndResp

    请求的中文乱码:
        浏览器地址栏使用utf-8编码
        tomcat7使用的iso8859-1编码
        
        参数使用utf-8编码,tomcat使用iso-8859-1进行解码出现了乱码.
        解决的思路:
            把接受的参数先iso-8859-1编码,然后使用utf-8进行解码
            对于post请求和get请求可以通过
                new String(name.getBytes("iso8859-1"),"utf-8");
            对于post请求还可以使用
                request.setCharacterEncoding("utf-8"); 
            
            乱码解决过程        
            String s="赵四";
            String s1=URLEncoder.encode(s,"utf-8");
            String s2=URLDecoder.decode(s1, "iso8859-1");
            System.out.println(s2);
            
            //先使用iso8859-1编码
            String s3 = URLEncoder.encode(s2, "iso8859-1");
            //使用utf-8解码
            String s4 = URLDecoder.decode(s3, "utf-8");
            System.out.println(s4);

  • 相关阅读:
    理解Promise函数中的resolve和reject
    一行代码 去除滚动条
    django开发前准备工作
    居中select中的option选项
    setTimeout中第一个参数
    利用es6解构赋值快速提取JSON数据;
    需要删除远程分支,刚好有正在别的分支做的事情
    vue项目处理dpr和多屏幕适配问题
    使用mockjs模拟后端返回的json数据;
    移动端页面中点击input输入框的时候弹出的键盘将输入框挡住的问题
  • 原文地址:https://www.cnblogs.com/du-0210/p/8426864.html
Copyright © 2011-2022 走看看