• 【Servlet】4:详解请求对象 HttpServletRequest


    目录

    | 请求对象 HttpServletRequest接口

    HttpServletRequest的基本概述

    请求对象获取 URL & Method

    请求对象获取 参数名

    请求对象获取 参数值

    参数值乱码问题


    本文章属于后端全套笔记的第三部分

    (更新中)【后端入门到入土!】Java+Servlet+JDBC+SSM+SpringBoot+SpringCloud 基础入门_m0_57265007的博客-CSDN博客一篇文章,后端入门到入土。包含 Java基础+高级、MySQL、JDBC、Servlet、SSM、SpringBoot、SpringCloud、项目 的笔记。https://blog.csdn.net/m0_57265007/article/details/127962617?csdn_share_tail=%7B%22type%22%3A%22blog%22%2C%22rType%22%3A%22article%22%2C%22rId%22%3A%22127962617%22%2C%22source%22%3A%22m0_57265007%22%7D

    | 请求对象 HttpServletRequest接口

    HttpServletRequest的基本概述

    HttpServletRequest在哪里使用?

    • 仔细观察就能发现,之前的 doGet 和 doPost 方法的参数列表内为 HttpServletRequest req, HttpServletResponse resp

    • 这两个参数就是我们现在学习的HttpServletRequest和之后要学习的HttpServletRespose

    • 我们再来复习一下Tomcat处理请求的全流程,好方便接下来更清晰地使用它

    当一个请求发送到Tomcat之后,首先经过Service然后会交给Connector,Connector用于接收请求并将接收的请求封装为Request和Response来具体处理,Request和Response封装完之后再交由Container内的Servlet进行处理,Container处理完请求之后再返回给Connector,最后在由Connector通过Socket将处理的结果返回给客户端,这样整个请求的就处理完了!

    HttpServletRequest是什么?

    • HttpServletRequest来自于Servlet规范中,是一个接口

    • 实现类由 HTTP服务器(Tomcat)提供

    • HttpServletRequest的实现类对象被称为请求对象

    作用?

    • HttpServletRequest接口负责在doGet/doPost方法运行时读取Http请求协议包中信息

    • 读取Http请求协议包中【请求行】信息

    • 读取保存在Http请求协议包中【请求头】或【请求体】中请求参数信息

    • 代替浏览器向Http服务器申请资源文件调用


    请求对象获取 URL & Method

    语法

    1. request.getRequestURI(); //获取请求行的URI
    2. request.getRequestURL(); //获取请求行的URL
    3. request.getMethod(); //获取请求行的method(请求方式)

    示例

    • 下面的Servlet的实现类相关web.xml配置已经配好了。

    • 网站部署在Tomcat的别名为web2。该Servlet对象的别名为web1.、

    • 配置完毕、代码写完之后,启动Tomcat,输入URLhttp://localhost:8080/web2/web1 即可访问Servlet

    1. public class MyServlet extends HttpServlet {
    2. @Override
    3. public void init() throws ServletException {
    4. super.init();
    5. System.out.println("MyServlet对象被创建了");
    6. }
    7. @Override
    8. protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    9. //super.doGet(req, resp); 如果你是要彻底覆盖父类的doGet方法,不需要父类提供的功能,就可以删除super.doGet(req,resp);这一句
    10. System.out.println("这是Servlet的doGet方法");
    11. //request.getRequestURI()
    12. System.out.println("获取到请求行的URL:" + req.getRequestURL()); //http://localhost:8080/web2/web1
    13. System.out.println("获取到请求行的URI:" + req.getRequestURI()); ///web2/web1
    14. //request.getMethod()
    15. System.out.println("获取到请求行的method(请求方式):" + req.getMethod()); //?GET
    16. }
    17. }


    请求对象获取 参数名

    语法

    使用 getParameterNames 方法,返回一个 Enumeration 枚举类

    1. Enumeration parameters = request.getParameterNames();
    2. while(parameters.hasMoreElements()){
    3. String parameter = (String)parameters.nextElement(); //得到的是Object,所以要强转为String
    4. }

    示例

    1. public class MyServlet extends HttpServlet {
    2. @Override
    3. public void init() throws ServletException {
    4. super.init();
    5. System.out.println("MyServlet对象被创建了");
    6. }
    7. @Override
    8. protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    9. //...
    10. //request.getParameters
    11. Enumeration parameters = req.getParameterNames();
    12. while(parameters.hasMoreElements()){
    13. System.out.println("参数名:" + (String)parameters.nextElement());//得到的是Object,所以要强转为String
    14. //参数名:name 参数名:age
    15. }
    16. }
    17. }

    请求对象获取 参数值

    语法

    String value = request.getParameter(参数名);

    联系上一小节 获取参数名 的代码,则完整代码如下

    1. Enumeration parameters = request.getParameterNames();
    2. int i = 1;
    3. while(parameters.hasMoreElements()){
    4. String parameterName = (String)parameters.nextElement();//得到的是Object,所以要强转为String
    5. String parameterValue = request.getParameter(parameterName);
    6. System.out.println("参数" + i + ":" + parameterName + " = " + parameterValue);
    7. //name = Klee age = 12
    8. }

    示例

    1. public class MyServlet extends HttpServlet {
    2. @Override
    3. public void init() throws ServletException {
    4. super.init();
    5. System.out.println("MyServlet对象被创建了");
    6. }
    7. @Override
    8. protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    9. //...
    10. //request.getParameters
    11. Enumeration parameters = req.getParameterNames();
    12. int i = 1;
    13. while(parameters.hasMoreElements()){
    14. String parameterName = (String)parameters.nextElement();//得到的是Object,所以要强转为String
    15. String parameterValue = req.getParameter(parameterName);
    16. System.out.println("参数" + i++ + ":" + parameterName + " = " + parameterValue);
    17. //参数1:name = Klee 参数2:age = 12
    18. }
    19. }
    20. }
     

    参数值乱码问题

    为什么来自POST请求获取到的参数值会乱码?

    • 浏览器若以GET方式发送请求,请求参数保存在【请求头】,在Http请求协议包到达Http服务器之后,第一件事就是进行解码请求头二进制内容由Tomcat负责解码,Tomcat9.0默认使用【utf-8】字符集解码请求头,可以解释一切国家文字

    • 浏览器若以POST方式发送请求,请求参数保存在【请求体】,在Http请求协议包到达Http服务器之后,第一件事就是进行解码请求体二进制内容由当前请求对象(request)负责解码。request默认使用[IS0-8859-1]字符集解码请求体,一个东欧语系字符集此时如果请求体参数内容是中文,将无法解码只能得到乱码

    • 需要注意的是,任意版本的Tomcat都存在POST请求乱码问题,仅8.0版本前的Tomcat存在GET请求乱码(因此本节不介绍GET请求乱码,需要的自己百度)

      除此之外,除了上述Tomcat服务器与浏览器间的编码不匹配导致的乱码问题外,我们还要考虑一下由于控制台输出的编码设置引起的乱码,同时还要考虑一下由于本地代码文件中的字符设置引起的乱码

    浏览器若以POST方式发送请求,请求参数保存在【请求体】,在Http请求协议包到达Http服务器之后,第一件事就是进行解码请求体二进制内容由当前请求对象(request)负责解码。request默认使用[IS0-8859-1]字符集解码请求体,一个东欧语系字符集此时如果请求体参数内容是中文,将无法解码只能得到乱码

    解决POST乱码的基本思路

    在Post请求方式下,在读取请求体内容之前,应该通知请求对象使用utf-8字符集对请求体内容进行一次重新解码

    POST乱码、控制台输出乱码、本地代码中文乱码 解决办法

    • 在doPost方法的第一行添加代码 req.setCharacterEncoding("UTF-8");(该方法只针对POST乱码有效,即只能用于doPost)

    1. @Override
    2. protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    3. req.setCharacterEncoding("UTF-8");
    4. System.out.println("编码方式" + req.getCharacterEncoding());
    5. String parameterValue = req.getParameter("userName");
    6. System.out.println(parameterValue);
    7. }

    如果POST加了第一行代码之后还是乱码,甚至GET也乱码,则可以考虑是控制台输出乱码

    解决办法:【点击Edit Configuration ,在VM Options】 输入 -Dfile.encoding=utf-8

    (该方法解决的办法对POST和GET都有效:作用是解决控制台输出乱码) 参考资料1 参考资料2



     

    如果使用了上述两种方法后,来自浏览器的中文不乱码了,但是代码中的中文又乱码了,则可以考虑进入【Settings - Editor - File Encdings】设置一下

    示例

    1. <form action="/web2/postWeb" method="GET">
    2. 请求参数:<input type="text" name="userName"/>
    3. <br/>
    4. <input type="submit" value="POST方式访问Servlet">
    5. form>

     

    1. @Override
    2. protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    3. req.setCharacterEncoding("UTF-8");
    4. System.out.println("编码方式" + req.getCharacterEncoding());
    5. String parameterValue = req.getParameter("userName");
    6. System.out.println(parameterValue);

     

    1. <servlet>
    2. <servlet-name>MyPostServletservlet-name>
    3. <servlet-class>controller.PostServletservlet-class>
    4. servlet>
    5. <servlet-mapping>
    6. <servlet-name>MyPostServletservlet-name>
    7. <url-pattern>/postWeburl-pattern>
    8. servlet-mapping>

  • 相关阅读:
    函数式编程
    2022高教社杯思路汇总A题B题C题D题
    速度精度双SOTA! TPAMI2022最新车道线检测算法(Ultra-Fast-Lane-Detection-V2)
    信息学奥赛一本通:1130:找第一个只出现一次的字符
    金仓数据库 OCCI迁移指南(2. 概述)
    如何通过SK集成chatGPT实现DotNet项目工程化?
    python+requests接口自动化测试框架实例详解教程
    【Python3】【力扣题】258. 各位相加
    Codeforces Round #834 (Div. 3)(D-G)
    解决“org.apache.catalina.startup.Catalina.stopServer 未配置关闭端口。通过OS信号关闭服务器。服务器未关闭“
  • 原文地址:https://blog.csdn.net/m0_57265007/article/details/128005836