HttpServletRequest對(duì)象方法的用法小結(jié)
深入體驗(yàn)JavaWeb開發(fā)內(nèi)幕——關(guān)于HttpServletRequestRequest對(duì)象
HttpServletRequest對(duì)象代表客戶端的請(qǐng)求,當(dāng)客戶端通過HTTP協(xié)議訪問服務(wù)器時(shí),HTTP請(qǐng)求頭中的所有信息都封裝在這個(gè)對(duì)象中,開發(fā)人員通過這個(gè)對(duì)象的相關(guān)方法,即可以獲得客戶的這些信息。
一、通過request常用方法獲得相關(guān)信息:
1、通過request常用方法獲得客戶機(jī)信息
getRequestURL方法返回客戶端發(fā)出請(qǐng)求時(shí)的完整URL。
getRequestURI方法返回請(qǐng)求行中的資源名部分。
getQueryString 方法返回請(qǐng)求行中的參數(shù)部分。
getRemoteAddr方法返回發(fā)出請(qǐng)求的客戶機(jī)的IP地址
getRemoteHost方法返回發(fā)出請(qǐng)求的客戶機(jī)的完整主機(jī)名
getRemotePort方法返回客戶機(jī)所使用的網(wǎng)絡(luò)端口號(hào)
getLocalAddr方法返回WEB服務(wù)器的IP地址。
getLocalName方法返回WEB服務(wù)器的主機(jī)名
getMethod得到客戶機(jī)請(qǐng)求方式
例如在Request.Java中加入如下代碼:
//返回相關(guān)請(qǐng)求的信息 String uri=request.getRequestURI(); Stringrad = request.getRemoteAddr(); Stringrh = request.getRemoteHost(); Stringru = request.getRemoteUser(); intrp = request.getRemotePort(); Stringcp = request.getContextPath(); Stringla = request.getLocalAddr(); Stringce = request.getCharacterEncoding(); Stringgm = request.getMethod(); Stringqs = request.getQueryString(); System.out.println(uri); System.out.println(rad); System.out.println(rh); System.out.println(ru); System.out.println(rp); System.out.println(cp); System.out.println(la); System.out.println(ce); System.out.println(gm); System.out.println(qs);
即可獲取相關(guān)信息。
2、通過request常用方法獲得客戶機(jī)請(qǐng)求頭信息
getHead(name)方法
getHeaders(String name)方法
getHeaderNames方法
如:
private void getRequestValue(HttpServletRequest request) { //獲得客戶機(jī)請(qǐng)求頭及請(qǐng)求頭的值 System.out.println(request.getHeader("method")); Enumeration e = request.getHeaderNames(); while(e.hasMoreElements()){ String name = (String)e.nextElement(); String value = request.getHeader(name); System.out.println(name+":"+value); } }
3.獲得客戶機(jī)請(qǐng)求參數(shù)(客戶端提交的數(shù)據(jù))
getParameter(name):獲取指定名稱的參數(shù)值。這是最為常用的方法之一。
getParameterValues(String name):獲取指定名稱參數(shù)的所有值數(shù)組。它適用于一個(gè)參數(shù)名對(duì)應(yīng)多個(gè)值的情況。如頁面表單中的復(fù)選框,多選列表提交的值。
getParameterNames():返回一個(gè)包含請(qǐng)求消息中的所有參數(shù)名的Enumeration對(duì)象。通過遍歷這個(gè)Enumeration對(duì)象,就可以獲取請(qǐng)求消息中所有的參數(shù)名
getParameterMap():返回一個(gè)保存了請(qǐng)求消息中的所有參數(shù)名和值的Map對(duì)象。Map對(duì)象的key是字符串類型的參數(shù)名,value是這個(gè)參數(shù)所對(duì)應(yīng)的Object類型的值數(shù)組。
二、request的常見應(yīng)用
1、 各種表單輸入項(xiàng)數(shù)據(jù)的獲取
如可以獲取form表單中的text、password、radio、checkbox、 file、select、textarea、 hidden、image、button等組件的值進(jìn)行數(shù)據(jù)庫操作或其他處理操作。
來看一個(gè)具體應(yīng)用:
界面代碼主體部分如下:
Register.html
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01Transitional//EN"> <html> <head> <title>Register.html</title> <metahttp-equivmetahttp-equiv="keywords"content="keyword1,keyword2,keyword3"> <metahttp-equivmetahttp-equiv="description" content="this is my page"> <meta http-equiv="content-type" content="text/html;charset=UTF-8"> <!--<link rel="stylesheet" type="text/css"href="./styles.css" rel="external nofollow" >--> </head> <body> <form action ="RequestLogin" method ="post"> 用戶名:<input type="text"name = "username" ><br/> 密碼: <inputtypeinputtype="password" name = "password"><br/> 性別:<input type="radio"name = "sex" value ="male">男 <input type="radio" name = "sex" value="female">女<br/> 籍貫: <select name="city"> <option value ="HeBei">河北</option> <opton value ="HuBei">湖北</opton> <option value ="ShanXi">山西</option> </select><br/> 簡歷:<br/> &nsp;<textarea rows="5" cols="20" name="intro"></textarea> <br/> 愛好:<br/> <input type="checkbox" name="hobbies" value ="sing"/>唱歌 <input type="checkbox" name="hobbies" value ="dance"/>跳舞 <input type="checkbox" name="hobbies" value ="readbook"/>讀書 <input type="checkbox" name="hobbies" value ="readnewspaper"/>看報(bào)<br/> 上傳頭像:<br/> <input type="file" value="image" name ="browser"><br/> <input type="submit" value="提交"/> </form> </body> </html>
然后,定義一個(gè)RequestLogin.java類通過request對(duì)象獲取表單中組件的值:
如調(diào)用自定義方法:
private void getInformation(HttpServletRequest request) throws UnsupportedEncodingException { //取出參數(shù)值 String name = request.getParameter("username"); String pass = request.getParameter("password"); String sex = request.getParameter("sex"); String city = request.getParameter("city"); String intro = request.getParameter("intro"); String [] hobbies = request.getParameterValues("hobbies"); String hobby =""; //hobbies!=null對(duì)所取值為空時(shí)進(jìn)行設(shè)置 for(int i=0;hobbies!=null&&i<hobbies.length;i++) { String hovalue = hobbies[i]; hobby += hovalue; } //獲取頭像信息 // String image = request.getParameter("image"); System.out.println("username:"+name); System.out.println("password:"+pass); System.out.println("sex:"+sex); System.out.println("city:"+city); System.out.println("intro:"+intro); System.out.println("hobby:"+hobby);}
即可獲取表單中組件的值。
2、請(qǐng)求參數(shù)的中文亂碼問題
前面我們提到了Response對(duì)象中出現(xiàn)亂碼問題及相應(yīng)的解決措施,那么在Request中如何解決編碼問題呢?
下面來看具體的例子:
例如我想將一個(gè)form表單中的信息提取到并在控制臺(tái)輸出如圖:
假設(shè)在服務(wù)端并未Request對(duì)象給指定編碼時(shí)即服務(wù)器端接收請(qǐng)求的字符編碼為ISO8859-1,這時(shí)你在客戶端添加信息如:
當(dāng)填入的信息有中文時(shí),假設(shè)設(shè)置表單的提交方式為post方式提交
則在服務(wù)端輸出如下:
此時(shí)輸出結(jié)果出現(xiàn)亂碼。
客戶端主體代碼同上:
Register.html <body> <form action ="RequestLogin" method ="post"> 用戶名:<input type="text" name = "username" ><br/> 密碼: <input type="password" name = "password"><br/> 性別:<input type="radio" name = "sex" value ="male">男 <input type="radio" name = "sex" value ="female">女<br/> 籍貫: <select name ="city"> <option value ="HeBei">河北</option> <opton value ="HuBei">湖北</opton> <option value ="ShanXi">山西</option> </select><br/> 簡歷:<br/> &nsp;<textarea rows="5" cols="20" name ="intro"></textarea> <br/> 愛好:<br/> <input type="checkbox" name ="hobbies" value ="sing"/>唱歌 <input type="checkbox" name ="hobbies" value ="dance"/>跳舞 <input type="checkbox" name ="hobbies" value ="readbook"/>讀書 <input type="checkbox" name ="hobbies" value ="readnewspaper"/>看報(bào)<br/> 上傳頭像:<br/> <input type="file" value ="image" name ="browser"><br/> <input type="submit" value ="提交"/> </form> </body>
服務(wù)端主體代碼如下:
RequestLogin.java package net.csdn.request; import java.io.IOException; import java.io.PrintWriter; importjava.io.UnsupportedEncodingException; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; importjavax.servlet.http.HttpServletRequest; importjavax.servlet.http.HttpServletResponse; public class RequestLogin extendsHttpServlet { public void doGet(HttpServletRequest request,HttpServletResponse response) throws ServletException, IOException { getInformation(request); } private voidgetParameter(HttpServletRequest request) throws UnsupportedEncodingException { private voidgetInformation(HttpServletRequest request) throws UnsupportedEncodingException { //取出參數(shù)值 String name =request.getParameter("username"); String pass =request.getParameter("password"); String sex =request.getParameter("sex"); String city =request.getParameter("city"); String intro = request.getParameter("intro"); String [] hobbies =request.getParameterValues("hobbies"); String hobby =""; //hobbies!=null對(duì)所取值為空時(shí)進(jìn)行設(shè)置 for(inti=0;hobbies!=null&&i<hobbies.length;i++) { String hovalue = hobbies[i]; hobby +=hovalue; } //獲取頭像信息 // String image = request.getParameter("image"); System.out.println("username:"+name); System.out.println("password:"+pass); System.out.println("sex:"+sex);System.out.println("city:"+city); System.out.println("intro:"+intro);System.out.println("hobby:"+hobby);} public void doPost(HttpServletRequestrequest, HttpServletResponse response) throws ServletException, IOException{doGet(request, response);}}
這里會(huì)出現(xiàn)亂碼問題,是因?yàn)槟阍赗egisterLogin.java中并沒有給Request對(duì)象設(shè)置編碼集,而Request對(duì)象的默認(rèn)編碼集是ISO8859-1是不支持漢字的,所以你只需要在此類中為其指明相應(yīng)的編碼即可:
改正:在doGet方法中加入如下代碼指明接收請(qǐng)求的編碼方式:
request.setCharacterEncoding("utf-8");
即可輸出:
但是這種修改方式只在提交方式為post時(shí)才有效。當(dāng)提交方式為get時(shí)是不起作用的。
即;
<form action ="RequestLogin" method ="get">
時(shí)即便在
RequestLogin.java
中再設(shè)置
request.setCharacterEncoding("utf-8");
也不會(huì)起任何作用了程序還會(huì)輸出如圖所示信息:
這時(shí)就需要在
RequestLogin.java
中含有中文的地方進(jìn)行如下設(shè)置了即在doGet方法中加入如下代碼:
String username = new String(name.getBytes("iso8859-1"),"utf-8"); String introduction = new String(intro.getBytes("iso8859-1"),"utf-8"); System.out.println("username:"+username); System.out.println("password:"+introduction);
此時(shí)再度測試時(shí)就OK了!如圖
好了到這里,你大概已經(jīng)知道該如何對(duì)Response和Request對(duì)象中的亂碼問題進(jìn)行操作了吧!
3、防盜鏈
所謂的防盜鏈就是當(dāng)你以一個(gè)非正常渠道去訪問某一個(gè)Web資源的時(shí)候,服務(wù)器會(huì)將你的請(qǐng)求忽略并且將你的當(dāng)前請(qǐng)求變?yōu)榘凑G涝L問時(shí)的請(qǐng)求并返回到相應(yīng)的頁面,用戶只有通過該頁面中的相關(guān)操作去訪問想要請(qǐng)求的最終資源。
例如,你有一個(gè)訪問某資源的網(wǎng)址,但是你事先不知道這個(gè)網(wǎng)址是有防盜鏈的,那么當(dāng)你輸入該網(wǎng)址時(shí)你可能會(huì)發(fā)現(xiàn),并沒有馬上跳轉(zhuǎn)到你想要的資源頁面而是一些無關(guān)的信息頁面,但是就是在這些信息頁面中你發(fā)現(xiàn)有一個(gè)超鏈接或是其他操作可以跳轉(zhuǎn)到你所訪問的最終資源頁面。
這就是防盜鏈技術(shù)了,好了來看一個(gè)具體應(yīng)用:
Rquest.java
public class Request extends HttpServlet { public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {getDoorChain(request, response);} private void getDoorChain(HttpServletRequest request, HttpServletResponse response) throws IOException { //通過request獲取請(qǐng)求頭參數(shù) String referer = request.getHeader("referer"); if(referer==null || !referer.endsWith("http://localhost:8080/Request/index.jsp")){ response.sendRedirect("http://localhost:8080/Request/index.jsp"); return; } response.setCharacterEncoding("utf-8"); response.setContentType("text/html;charset =utf-8"); PrintWriter pw = response.getWriter(); pw.write("喜劇片《東成西就》"); } public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { doGet(request, response); } }
index.jsp部分的主體代碼:
<body> 這里是防盜鏈技術(shù)的應(yīng)用檢測! <br> <a href ="/Request/Request" >喜劇片 </a> </body> </html>
效果如圖:
例如我最終想要通過http://lcoalhost:8080/Request/Request這個(gè)網(wǎng)址獲取到我想要的《東成西就》
的資源可是當(dāng)我真正的輸入這個(gè)網(wǎng)址時(shí),卻轉(zhuǎn)到了:
http://localhost:8080/Request/index.jsp這個(gè)頁面
只有當(dāng)你點(diǎn)擊“喜劇片”這個(gè)超鏈接時(shí)才會(huì)真正的得到你想要的資源頁面即:
好了趕快自己動(dòng)手試一試吧!
4、request對(duì)象實(shí)現(xiàn)請(qǐng)求轉(zhuǎn)發(fā):
Servlet API中定義了一個(gè)RequestDispatcher接口,俗稱請(qǐng)求分派器。它定義了如下兩個(gè)方法: public void forward(ServletRequest request, ServletResponseresponse) 、public void include(ServletRequest request,ServletResponse response) ,
獲取RequestDispatcher實(shí)例的方式主要有兩種:
調(diào)用ServletContext接口提供的getRequestDispatcher(Stringurl)方法。
調(diào)用ServletRequest接口提供的getRequestDispatcher(Stringurl)方法。
RequestDispatcher:
被包含的Servlet程序不能改變響應(yīng)消息的狀態(tài)碼和響應(yīng)頭,如果它里面存在這樣的語句,這些語句的執(zhí)行結(jié)果將被忽略。
例:
request.getRequestDispatcher("./Welcome.jsp").forward(request,response);即可從當(dāng)前應(yīng)用跳轉(zhuǎn)到相應(yīng)的"./Welcome.jsp"頁面。
request對(duì)象提供了一個(gè)getRequestDispatcher方法,該方法返回一個(gè)RequestDispatcher對(duì)象,調(diào)用這個(gè)對(duì)象的forward方法可以實(shí)現(xiàn)請(qǐng)求轉(zhuǎn)發(fā)。
request對(duì)象同時(shí)也是一個(gè)域?qū)ο?,開發(fā)人員通過request對(duì)象在實(shí)現(xiàn)轉(zhuǎn)發(fā)時(shí),把數(shù)據(jù)通過request對(duì)象帶給其它web資源處理。
可通過如下方法對(duì)request中的數(shù)據(jù)對(duì)象進(jìn)行操作:
setAttribute方法 ;
getAttribute方法 ;
removeAttribute方法;
getAttributeNames方法;
三、關(guān)于請(qǐng)求轉(zhuǎn)發(fā)的一些細(xì)節(jié)
forward方法用于將請(qǐng)求轉(zhuǎn)發(fā)到RequestDispatcher對(duì)象封裝的資源。
如果在調(diào)用forward方法之前,在Servlet程序中寫入的部分內(nèi)容已經(jīng)被真正地傳送到了客戶端,forward方法將拋出IllegalStateException異常。
如果在調(diào)用forward方法之前向Servlet引擎的緩沖區(qū) (response)中寫入了內(nèi)容,只要寫入到緩沖區(qū)中的內(nèi)容還沒有被真正輸出到客戶端,forward方法就可以被正常執(zhí)行,原來寫入到輸出緩沖區(qū)中的 內(nèi)容將被清空,但是,已寫入到HttpServletResponse對(duì)象中的響應(yīng)頭字段信息保持有效。
四、請(qǐng)求重定向和請(qǐng)求轉(zhuǎn)發(fā)的區(qū)別
一個(gè)web資源收到客戶端請(qǐng)求后,通知服務(wù)器去調(diào)用另外一個(gè)web資源進(jìn)行處理,稱之為請(qǐng)求轉(zhuǎn)發(fā)。
一個(gè)web資源收到客戶端請(qǐng)求后,通知瀏覽器去訪問另外一個(gè)web資源,稱之為請(qǐng)求重定向。
注意:
RequestDispatcher.forward方法只能將請(qǐng)求 轉(zhuǎn)發(fā)給同一個(gè)WEB應(yīng)用中的組件;而HttpServletResponse.sendRedirect方法還可以重定向到同一個(gè)站點(diǎn)上的其他應(yīng)用程序中的資源,甚至是使用絕對(duì)URL重定向到其他站點(diǎn)的資源。 如果傳遞HttpServletResponse.sendRedirect方法的相對(duì)URL以“/”開頭,它是相對(duì)于整個(gè)WEB站點(diǎn)的根目錄;如果創(chuàng)建RequestDispatcher對(duì)象時(shí)指定的相對(duì)URL以“/”開頭,它是相對(duì)于當(dāng)前WEB應(yīng)用程序的根目錄。
調(diào)用HttpServletResponse.sendRedirect方法重定向的訪問過程結(jié)束后,瀏覽器地址欄中顯示的URL會(huì)發(fā)生改變,由初始的URL 地址變成重定向的目標(biāo)URL;調(diào)用RequestDispatcher.forward 方法的請(qǐng)求轉(zhuǎn)發(fā)過程結(jié)束后,瀏覽器地址欄保持初始的URL地址不變。
HttpServletResponse.sendRedirect 方法對(duì)瀏覽器的請(qǐng)求直接作出響應(yīng),響應(yīng)的結(jié)果就是告訴瀏覽器去重新發(fā)出對(duì)另外一個(gè)URL的訪問請(qǐng)求;RequestDispatcher.forward方法在服務(wù)器端內(nèi)部將請(qǐng)求轉(zhuǎn)發(fā)給另外一個(gè)資源,瀏覽器只知道發(fā)出了請(qǐng)求并得到了響應(yīng)結(jié)果,并不知道在服務(wù)器程序內(nèi)部發(fā)生了轉(zhuǎn)發(fā)行為。
RequestDispatcher.forward方法的調(diào)用者與 被調(diào)用者之間共享相同的request對(duì)象和response對(duì)象,它們屬于同一個(gè)訪問請(qǐng)求和響應(yīng)過程;而 HttpServletResponse.sendRedirect方法調(diào)用者與被調(diào)用者使用各自的request對(duì)象和response對(duì)象,它們屬于 兩個(gè)獨(dú)立的訪問請(qǐng)求和響應(yīng)過程。
關(guān)于請(qǐng)求消息頭我們?cè)谝院蟮膶W(xué)習(xí)中還會(huì)經(jīng)常用到request對(duì)象是我們目前在JavaWeb開發(fā)中學(xué)到的三個(gè)作用域即ServletContext、Request和Session域之一,是非常重要的一個(gè)請(qǐng)求對(duì)象,希望以上的相關(guān)介紹對(duì)能你有所幫助!
- SpringCloud Feign傳遞HttpServletRequest對(duì)象流程
- SpringBoot實(shí)現(xiàn)任意位置獲取HttpServletRequest對(duì)象
- 如何HttpServletRequest文件對(duì)象并儲(chǔ)存
- HttpServletRequest對(duì)象常用功能_動(dòng)力節(jié)點(diǎn)Java學(xué)院整理
- HttpServletRequest對(duì)象簡介_動(dòng)力節(jié)點(diǎn)Java學(xué)院整理
- 解決子線程中獲取不到HttpServletRequest對(duì)象的問題
相關(guān)文章
Java使用poi導(dǎo)出ppt文件的實(shí)現(xiàn)代碼
Apache POI 是用Java編寫的免費(fèi)開源的跨平臺(tái)的 Java API,Apache POI提供API給Java對(duì)Microsoft Office格式檔案讀和寫的功能。本文給大家介紹Java使用poi導(dǎo)出ppt文件的實(shí)現(xiàn)代碼,需要的朋友參考下吧2021-06-06springcloud整合gateway實(shí)現(xiàn)網(wǎng)關(guān)全局過濾器功能
本文主要介紹了springcloud整合gateway實(shí)現(xiàn)網(wǎng)關(guān)全局過濾器功能,文中通過示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2022-02-02java7鉆石語法知識(shí)點(diǎn)總結(jié)
在本篇文章里小編給大家整理的是關(guān)于java7鉆石語法的相關(guān)知識(shí)點(diǎn)內(nèi)容,有需要的朋友們參考下。2019-11-11Java常問面試內(nèi)容--數(shù)組、聲明、初始化、冒泡、多維數(shù)組、稀疏數(shù)組
這篇文章主要介紹了Java多線程面試題(面試官常問),本文給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2021-07-07Java新特性中Preview功能如何運(yùn)行調(diào)試詳解
這篇文章主要為大家介紹了Java新特性中Preview功能如何運(yùn)行調(diào)試詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-10-10Java使用wait() notify()方法操作共享資源詳解
這篇文章主要為大家詳細(xì)介紹了Java使用wait() notify()方法操作共享資源,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-10-10springboot 實(shí)現(xiàn)記錄業(yè)務(wù)日志和異常業(yè)務(wù)日志的操作
這篇文章主要介紹了springboot 實(shí)現(xiàn)記錄業(yè)務(wù)日志和異常業(yè)務(wù)日志的操作,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2021-07-07