目录

1、简介

2、页面动态刷新验证码图片

 3、页面下载图片

        3.1、如图,在resources文件夹下放一张图片资源

        3.2、运行项目,查看图片资源在服务器中的绝对地址,以便获取地址和图片名称

       3.3、编写类,完成逻辑功能

         3.4、注册类

        3.5、运行结果(访问路径后图片自动下载)

4、重定向


1、简介

        在servlet类中,几乎所有的业务处理方法都有两个参数----req和resp,以都Get()方法为例,它的两个参数就是req和resp。不难想象,req参数与浏览器向服务器发送请求有关,而resp与服务器向浏览器响应东西有关。这篇文章将要介绍的就是resp这个参数,并通过实现:1)实现页面动态刷新验证码图片;2)页面下载图片;3)重定向。 这三个功能来简单介绍resp参数

protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException{};

2、页面动态刷新验证码图片

        这个功能我们想要实现页面动态刷数字-字母新验证码的操作。

        首先分析一下要实现这个功能需要的几个步骤:1)在内存中创建一张空白的图片;2)获取关于这张图片的画笔;3)为画笔选取一个颜色,并为图片涂上背景颜色;4)为画笔选取一个颜色,在图片上绘制出验证码字符串;5)将绘制好验证码字符串的图片在浏览器页面上显示出来;6)设置响应头,让浏览器页面定时刷新,并且不缓存当前页面文档。

        首先是获取验证码字符串,方法如下

private String makeAString(){
        Random rnd = new Random();
        String val = "";
        for (int i = 0; i <6 ; i++) {
            String charOrNum = rnd.nextInt(2)%2 == 0 ? "char" : "num";
            if("char".equalsIgnoreCase(charOrNum)){
                int temp = rnd.nextInt(2)%2 == 0 ? 65 : 97;
                val += (char)(temp + rnd.nextInt(26));
            }else if("num".equalsIgnoreCase(charOrNum)){
                val += rnd.nextInt(10);
            }
        }
        return val;
    }

        然后在doGet()方法中实现上述业务逻辑,具体实现如下:

protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//      对resp头进行设置,使浏览器不缓存当前文档内容
        resp.setDateHeader("expries", -1);
        resp.setHeader("Cache-Control", "no-chche");
        resp.setHeader("pragma", "no-cache");
        resp.setHeader("refresh", "5");
//        resp.setContentType();
//      在内存中创建一张图片
        BufferedImage img = new BufferedImage(80, 20, BufferedImage.TYPE_INT_RGB);
//      获得关于图片的画笔
        Graphics graphics = img.getGraphics();
//      为画笔选取一个颜色,用于填充图片的背景
        graphics.setColor(Color.green);
        graphics.fillRect(0, 0, 80, 20);
//      为画笔选取一个颜色,用于绘制验证码字符串
        graphics.setColor(Color.gray);
        graphics.setFont(new Font(null, Font.BOLD, 20));
        String string = makeAString();
        graphics.drawString(string, 0, 20);
//        System.out.println(string);
//      把图片显示在浏览器页面上
        ImageIO.write(img, "png", resp.getOutputStream());

    }

        在web.xml文件中注册类,并指明访问路径

<servlet>
    <servlet-name>resp</servlet-name>
    <servlet-class>ResponseServlet</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>resp</servlet-name>
    <url-pattern>/resp</url-pattern>
  </servlet-mapping>

运行结果如下:(图片每五秒会动态刷新

RESP使用教程_验证码

 3、页面下载图片

        这个功能我想要实现 当我访问一个路径的时候,浏览器页面会弹出一个图片下载的窗口。想要实现这个功能,我们需要:1)准备一张图片;2)获得图片在服务器中的路径;3)获取图片名称;4)设置响应头,以支持图片下载; 5)获得这张图片的数据流; 6)通过响应输出流将这张图片显示在浏览器页面上

        3.1、如图,在resources文件夹下放一张图片资源

RESP使用教程_服务器_02

        3.2、运行项目,查看图片资源在服务器中的绝对地址,以便获取地址和图片名称

RESP使用教程_验证码_03

       3.3、编写类,完成逻辑功能

protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//      获取图片路径和图片名称
        String path = "E:\\code\\kuang\\javaweb-test\\javaweb-servlet-01\\out\\artifacts\\response_war_exploded\\WEB-INF\\classes\\虎牙.png";
        String name = path.substring(path.lastIndexOf("\\")+1);

//      设置resp响应头,下载图片
        resp.setHeader("content-disposition", "attachment;filename="+ URLEncoder.encode(name, "UTF-8"));
//      获得图片文件的输入流
        FileInputStream fileIn = new FileInputStream(path);
//      获得resp输出到浏览器页面上的输出流
        ServletOutputStream os = resp.getOutputStream();
//      设置一个缓冲区,将图片文件输出流通过缓冲区输入到resp的输出流上
        byte[] buffer = new byte[1024];
        int len;
        while ((len = fileIn.read(buffer)) > 0){
            os.write(buffer, 0, len);
            os.flush();
        }
//      关闭输入输出流
        os.close();
        fileIn.close();
    }

         3.4、注册类

<servlet>
    <servlet-name>resp</servlet-name>
    <servlet-class>ResponseServlet</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>resp</servlet-name>
    <url-pattern>/resp</url-pattern>
  </servlet-mapping>

        3.5、运行结果(访问路径后图片自动下载)

RESP使用教程_RESP使用教程_04

4、重定向

        重定向就是浏览器在向服务器发送了一个请求之后,服务器的当前程序处理方法还没有完全处理完成这个请求的功能,需要其它的程序协助完成。于是服务器告诉浏览器接下来需要访问的程序,浏览器再次发送一个请求到服务器,以完成功能。

        也就是说,重定向中浏览器发送了两次请求,而且地址栏也会发生改变。

        实现RedirectServlet类如下(重定向到/img路径的页面):

public class RedirectServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        resp.sendRedirect("/response_war_exploded/img");
        System.out.println("这是RedirectServlet");
    }
}

配置映射路径

<servlet>
    <servlet-name>red</servlet-name>
    <servlet-class>RedirectServlet</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>red</servlet-name>
    <url-pattern>/red</url-pattern>
  </servlet-mapping>

运行结果(输入/red路径后,重定向到/img路径):

RESP使用教程_验证码_05

RESP使用教程_RESP使用教程_06

RESP使用教程_服务器_07

总的来说,重定向就是服务器告诉浏览器接下来需要访问的页面路径,浏览器实际上发出了两次请求,并且一般不会去发出到 scr/main/webapp/WEB-INF目录下资源访问的重定向。接下来一片讲req参数的时候会讲到请求转发,它和重定向有相似的地方,讲完后我还会发一篇比较详细对比重定向和转发的文章。这里我们关注一下重定向的地址(/response_war_exploded/img):/当前项目路径/目的路径,这里和请求转发也有区别。