- 什么是HttpServletRequest?
公共接口类HttpServletRequest继承自ServletRequest。客户端浏览器发出的请求被封装成为一个HttpServletRequest对象。对象包含了客户端请求信息包括请求的地址,请求的参数,提交的数据,上传的文件客户端的ip甚至客户端操作系统都包含在其内。HttpServletResponse继承了ServletResponse接口,并提供了与Http协议有关的方法,这些方法的主要功能是设置HTTP状态码和管理Cookie。
-
HttpServletRequest常用方法
-
获取客户机信息:
getRequestURL方法返回客户端发出请求时的完整URL。
getRequestURI方法返回请求行中的资源名部分。
getQueryString 方法返回请求行中的参数部分。
getRemoteAddr方法返回发出请求的客户机的IP地址。
范例如下:通过Request获取客户机信息
-
package com.qq.RequestDemo;
-
-
import javax.servlet.ServletException;
-
import javax.servlet.annotation.WebServlet;
-
import javax.servlet.http.HttpServlet;
-
import javax.servlet.http.HttpServletRequest;
-
import javax.servlet.http.HttpServletResponse;
-
import java.io.IOException;
-
import java.io.PrintWriter;
-
-
/**
-
* @Description:
-
* @Author: ZHENGZHIQIANG
-
* @CreateTime: 2019-03-25 19:40
-
*/
-
@WebServlet("/RequestDemo")
-
public class RequestDemo extends HttpServlet {
-
public void doGet(HttpServletRequest request, HttpServletResponse response)
-
throws ServletException, IOException {
-
/**
-
* 1.获得客户机信息
-
*/
-
String requestUrl = request.getRequestURL().toString();//得到请求的URL地址
-
String requestUri = request.getRequestURI();//得到请求的资源
-
String queryString = request.getQueryString();//得到请求的URL地址中附带的参数
-
String remoteAddr = request.getRemoteAddr();//得到来访者的IP地址
-
String remoteHost = request.getRemoteHost();
-
int remotePort = request.getRemotePort();
-
String remoteUser = request.getRemoteUser();
-
String method = request.getMethod();//得到请求URL地址时使用的方法
-
String pathInfo = request.getPathInfo();
-
String localAddr = request.getLocalAddr();//获取WEB服务器的IP地址
-
String localName = request.getLocalName();//获取WEB服务器的主机名
-
response.setCharacterEncoding("UTF-8");//设置将字符以"UTF-8"编码输出到客户端浏览器
-
//通过设置响应头控制浏览器以UTF-8的编码显示数据,如果不加这句话,那么浏览器显示的将是乱码
-
response.setHeader("content-type", "text/html;charset=UTF-8");
-
PrintWriter out = response.getWriter();
-
out.write("获取到的客户机信息如下:");
-
out.write("<hr/>");
-
out.write("请求的URL地址:"+requestUrl);
-
out.write("<br/>");
-
out.write("请求的资源:"+requestUri);
-
out.write("<br/>");
-
out.write("请求的URL地址中附带的参数:"+queryString);
-
out.write("<br/>");
-
out.write("来访者的IP地址:"+remoteAddr);
-
out.write("<br/>");
-
out.write("来访者的主机名:"+remoteHost);
-
out.write("<br/>");
-
out.write("使用的端口号:"+remotePort);
-
out.write("<br/>");
-
out.write("remoteUser:"+remoteUser);
-
out.write("<br/>");
-
out.write("请求使用的方法:"+method);
-
out.write("<br/>");
-
out.write("pathInfo:"+pathInfo);
-
out.write("<br/>");
-
out.write("localAddr:"+localAddr);
-
out.write("<br/>");
-
out.write("localName:"+localName);
-
}
-
-
public void doPost(HttpServletRequest request, HttpServletResponse response)
-
throws ServletException, IOException {
-
doGet(request, response);
-
}
-
}
-
获得客户机请求参数
getParameter(String)方法(常用)
getParameterValues(String name)方法(常用)
getParameterNames()方法(不常用)
request.getParameterNames()方法是将发送请求页面中form表单里所有具有name属性的表单对象获取(包括button).返回一个Enumeration类型的枚举.
通过Enumeration的hasMoreElements()方法遍历.再由nextElement()方法获得枚举的值.此时的值是form表单中所有控件的name属性的值.
最后通过request.getParameter()方法获取表单控件的value值.
Enumeration pNames=request.getParameterNames();
while(pNames.hasMoreElements()){
String name=(String)pNames.nextElement();
String value=request.getParameter(name);
out.print(name + "=" + value);
}
request.getParameterValues("name")方法将获取所有form表单中name属性为"name"的值.该方法返回一个数组.遍历数组就可得到value值.
String values = request.getParameterValues("name");
for(String value : values){
System.out.println(value);
}
request.getParameterNames()的值是无序排列request.getParameterValues()是按照from表单的控件顺序排列.
getParameterMap()方法(编写框架时常用)
在服务器端使用getParameter方法和getParameterValues方法接收表单参数,代码如下:
-
-
package com.qq.RequestDemo;
-
-
import javax.servlet.ServletException;
-
import javax.servlet.annotation.WebServlet;
-
import javax.servlet.http.HttpServlet;
-
import javax.servlet.http.HttpServletRequest;
-
import javax.servlet.http.HttpServletResponse;
-
import java.io.IOException;
-
import java.text.MessageFormat;
-
-
/**
-
* @Description:
-
* @Author: ZHENGZHIQIANG
-
* @CreateTime: 2019-03-25 19:51
-
*/
-
@WebServlet("/RequsetDemo2")
-
public class RequsetDemo2 extends HttpServlet {
-
@Override
-
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
-
//编码中文乱码
-
req.setCharacterEncoding("UTF-8");
-
//getParameter通过name来获取值
-
String userid = req.getParameter("userid");
-
String username = req.getParameter("username");
-
String userpass = req.getParameter("userpass");//获取填写的密码
-
String sex = req.getParameter("sex");//获取选中的性别
-
String dept = req.getParameter("dept");//获取选中的部门
-
//获取选中的兴趣,因为可以选中多个值,所以获取到的值是一个字符串数组,因此需要使用getParameterValues方法来获取
-
//request.getParameterValues("name")方法将获取所有form表单中name属性为"name"的值.该方法返回一个数组.遍历数组就可得到value值.
-
//
-
//String values = request.getParameterValues("name");
-
//for(String value : values){
-
// System.out.println(value);
-
//}
-
//
-
//request.getParameterNames()的值是无序排列request.getParameterValues()是按照from表单的控件顺序排列.
-
String[] insts = req.getParameterValues("inst");
-
String note = req.getParameter("note");//获取填写的说明信息
-
String hiddenField = req.getParameter("hiddenField");//获取隐藏域的内容
-
/**
-
* 获取数组数据的技巧,可以避免insts数组为null时引发的空指针异常错误!
-
*/
-
String instStr="";
-
for (int i = 0; insts!=null && i < insts.length; i++) {
-
if (i == insts.length-1) {
-
instStr+=insts[i];
-
}else {
-
instStr+=insts[i]+",";
-
}
-
}
-
String htmlStr = "<table>" +
-
"<tr><td>填写的编号:</td><td>{0}</td></tr>" +
-
"<tr><td>填写的用户名:</td><td>{1}</td></tr>" +
-
"<tr><td>填写的密码:</td><td>{2}</td></tr>" +
-
"<tr><td>选中的性别:</td><td>{3}</td></tr>" +
-
"<tr><td>选中的部门:</td><td>{4}</td></tr>" +
-
"<tr><td>选中的兴趣:</td><td>{5}</td></tr>" +
-
"<tr><td>填写的说明:</td><td>{6}</td></tr>" +
-
"<tr><td>隐藏域的内容:</td><td>{7}</td></tr>" +
-
"</table>";
-
htmlStr = MessageFormat.format(htmlStr, userid,username,userpass,sex,dept,instStr,note,hiddenField);
-
-
resp.setCharacterEncoding("UTF-8");//设置服务器端以UTF-8编码输出数据到客户端
-
resp.setContentType("text/html;charset=UTF-8");//设置客户端浏览器以UTF-8编码解析数据
-
resp.getWriter().write(htmlStr);//输出htmlStr里面的内容到客户端浏览器显示
-
}
-
@Override
-
public void doPost(HttpServletRequest request, HttpServletResponse response)
-
throws ServletException, IOException {
-
doGet(request, response);
-
}
-
}
-
//request对象封装的参数是以Map的形式存储的
-
Map<String, String[]> paramMap = req.getParameterMap();
-
for(Map.Entry<String, String[]> entry :paramMap.entrySet()){
-
String paramName = entry.getKey();
-
String paramValue = "";
-
String[] paramValueArr = entry.getValue();
-
for (int i = 0; paramValueArr!=null && i < paramValueArr.length; i++) {
-
if (i == paramValueArr.length-1) {
-
paramValue+=paramValueArr[i];
-
}else {
-
paramValue+=paramValueArr[i]+",";
-
}
-
}
-
System.out.println(MessageFormat.format("{0}={1}", paramName,paramValue));
-
}
-
}
From表单如下:
-
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
-
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
-
<html>
-
<head>
-
<title>Html的Form表单元素</title>
-
</head>
-
<fieldset style="500px;">
-
<legend>Html的Form表单元素</legend>
-
<!--form表单的action属性规定当提交表单时,向何处发送表单数据,method属性指明表单的提交方式,分为get和post,默认为get-->
-
<form action="/RequsetDemo2" method="post">
-
<!--输入文本框,SIZE表示显示长度,maxlength表示最多输入长度-->
-
编 号(文本框):
-
<input type="text" name="userid" value="NO." size="2" maxlength="2"><br>
-
<!--输入文本框,通过value指定其显示的默认值-->
-
用户名(文本框):<input type="text" name="username" value="请输入用户名"><br>
-
<!--密码框,其中所有输入的内容都以密文的形式显示-->
-
密 码(密码框):
-
<!-- 表示的是一个空格-->
-
<input type="password" name="userpass" value="请输入密码"><br>
-
<!--单选按钮,通过checked指定默认选中,名称必须一样,其中value为真正需要的内容-->
-
性 别(单选框):
-
<input type="radio" name="sex" value="男" checked>男
-
<input type="radio" name="sex" value="女">女<br>
-
<!--下拉列表框,通过<option>元素指定下拉的选项-->
-
部 门(下拉框):
-
<select name="dept">
-
<option value="技术部">技术部</option>
-
<option value="销售部" SELECTED>销售部</option>
-
<option value="财务部">财务部</option>
-
</select><br>
-
<!--复选框,可以同时选择多个选项,名称必须一样,其中value为真正需要的内容-->
-
兴 趣(复选框):
-
<input type="checkbox" name="inst" value="唱歌">唱歌
-
<input type="checkbox" name="inst" value="游泳">游泳
-
<input type="checkbox" name="inst" value="跳舞">跳舞
-
<input type="checkbox" name="inst" value="编程" checked>编程
-
<input type="checkbox" name="inst" value="上网">上网
-
<br>
-
<!--大文本输入框,宽度为34列,高度为5行-->
-
说 明(文本域):
-
<textarea name="note" cols="34" rows="5">
-
-
-
Request接收表单提交中文乱码问题
-
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
-
-
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
-
<html>
-
<head>
-
<title>request接收中文参数乱码问题</title>
-
</head>
-
-
<body>
-
<form action="<%=request.getContextPath()%>/servlet/RequestDemo04" method="post">
-
用户名:<input type="text" name="userName"/>
-
<input type="submit" value="post方式提交表单">
-
</form>
-
</body>
-
</html>
当UserName为中文提交时,后端对UserName的获取就会出现乱码。
那么为什么会出现这样的问题呢?
主要原因就是因为:服务器《----》客户端之间沟通的编码不一致造成的,因此只要在服务器和客户端之间设置统一的编码格式就可以解决数据的乱码问题。
-
request.setCharacterEncoding("UTF-8");
-
get方式提交中文数据乱码产生的原因和解决办法
为什么使用get方式提交会产生中文乱码呢,并且进行编码设置之后还是乱码?
服务器问题:
- 浏览器发送时文字编码是和页面编码保持一致。
- tomcat中接收请求没有设置编码的情况下,默认使用ISO-8859-1编码。
- 页面编码使用UTF-8,get方式自然使用UTF-8编码,但服务器接收没有指定编码格式,默认使用ISO-8859-1,传参带中文时自然乱码。
解决方法:
在接收到数据后,先获取request对象以ISO8859-1字符编码接收到的原始数据的字节数组,然后通过字节数组以指定的编码构建字符串,解决乱码问题。
String XX = new String(XX.getBytes("ISO8859-1"), "UTF-8") ;//获取request对象以ISO8859-1字符编码接收到的原始数据的字节数组,然后通过字节数组以指定的编码构建字符串,解决乱码问题
-
Request对象实现请求转发
- 转发的基本概念
请求转发:指一个web资源收到客户端请求后,通知服务器去调用另外一个web资源进行处理。
请求转发的应用场景:MVC设计模式
在Servlet中实现请求转发的两种方式:
1、通过ServletContext的getRequestDispatcher(String path)方法,该方法返回一个RequestDispatcher对象,调用这个对象的forward方法可以实现请求转发。
例如:将请求转发的test.jsp页面
-
RequestDispatcher reqDispatcher =this.getServletContext().getRequestDispatcher("/test.jsp");
-
reqDispatcher.forward(request, response);
2、通过request对象提供的getRequestDispatche(String path)方法,该方法返回一个RequestDispatcher对象,调用这个对象的forward方法可以实现请求转发。
例如:将请求转发的test.jsp页面
-
request.getRequestDispatcher("/test.jsp").forward(request, response);
(2)请求重定向和请求转发的区别
一个web资源收到客户端请求后,通知服务器去调用另外一个web资源进行处理,称之为请求转发/307。
一个web资源收到客户端请求后,通知浏览器去访问另外一个web资源进行处理,称之为请求重定向/302。