HTTP协议:HTTP请求案例

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了HTTP协议:HTTP请求案例相关的知识,希望对你有一定的参考价值。

HttpServletRequest对象核心API
类别API
请求行

request.getMethod();   请求方式

request.getRequetURI()   / request.getRequetURL()   请求资源

request.getProtocol()   请求http协议版本

请求头

request.getHeader("名称")   根据请求头获取请求值

request.getHeaderNames()    获取所有的请求头名称

实体内容

request.getInputStream()   获取实体内容数据

GET方式获取请求参数

request.getQueryString();

POST方式获取请求参数

request.getInputStream();

GET和POST获取
参数的方法(通用)

request.getParameter("参数名");  根据参数名获取参数值(注意,只能获取一个值的参数)

request.getParameterValue("参数名“);根据参数名获取参数值(可以获取多个值的参数)

request.getParameterNames();   获取所有参数名称列表

1、获取请求行、请求头、实体内部的信息

package com.rk.http.a_request;

import java.io.IOException;
import java.io.PrintWriter;
import java.util.Enumeration;

import javax.servlet.ServletException;
import javax.servlet.ServletInputStream;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * 请求数据的请求行、请求头、实体内容
 */
public class Demo01 extends HttpServlet
{
	/* 
	 * 1)tomcat服务器接收到浏览器发送的请求数据,然后封装到HttpServetRequest对象中
	 * 2)tomcat服务器调用doGet方法,然后把request对象传入到servlet中。
	 * 3)从request对象取出请求数据。
	 */
	@Override
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException
	{
		this.doPost(request, response);
	}
	
	@Override
	protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException
	{
		response.setCharacterEncoding("utf-8");
		response.setContentType("text/html;charset=utf-8");
		printRequestLine(request, response);
		printRequestHeaders(request, response);
		printRequestBody(request, response);//这里只有通过post方式提交的表单数据才能被打印出来
	}
	
	/**
	 * 请求行
	 */
	private void printRequestLine(HttpServletRequest request, HttpServletResponse response) throws IOException
	{
		PrintWriter out = response.getWriter();
		
		String strMethod = request.getMethod();//请求方式
		StringBuffer strURL = request.getRequestURL();//请求资源
		String strURI = request.getRequestURI();
		String strProtocol = request.getProtocol();//http协议
		
		out.write("<h1>请求行(Request Line)</h1>");
		out.write("<strong>Request Method</strong>: " + strMethod + "<br/>");
		out.write("<strong>Request URI</strong>: " + strURI + "<br/>");
		out.write("<strong>Request URL</strong>: " + strURL + "<br/>");
		out.write("<strong>Request Protocol</strong>: " + strProtocol + "<br/>");
		out.write("<hr/>");
	}
	
	/**
	 * 请求头
	 */
	private void printRequestHeaders(HttpServletRequest request, HttpServletResponse response) throws IOException
	{
		PrintWriter out = response.getWriter();
		out.write("<h1>请求头(Request Headers)</h1>");
		
		//遍历所有请求头
		Enumeration<String> requestHeaders = request.getHeaderNames();//得到所有的请求头名称列表
		while(requestHeaders.hasMoreElements())//判断是否有下一个元素
		{
			String headerName = requestHeaders.nextElement();//取出下一个元素
			String headerValue = request.getHeader(headerName);//根据头名称的到头的内容
			out.write("<strong>" + headerName + "</strong>: " + headerValue + "<br/>");
		}
		out.write("<hr/>");
	}
	
	/**
	 * 请求的实体内容
	 */
	private void printRequestBody(HttpServletRequest request, HttpServletResponse response) throws IOException
	{
		PrintWriter out = response.getWriter();
		out.write("<h1>实体内容(Request Body)</h1>");
		
		ServletInputStream inStream = request.getInputStream();//得到实体内容
		byte[] buf = new byte[1024];
		int len = 0;
		while((len=inStream.readLine(buf, 0, buf.length)) != -1)
		{
			String strValue = new String(buf, 0, len);
			out.print(strValue);
		}
		out.write("<hr/>");
	}

}



2、获取浏览器的类型

获取浏览器的类型主要是依据HTTP请求头中的user-agent。

package com.rk.http.a_request;

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * 案例:获取浏览器的类型
 */
public class Demo02 extends HttpServlet
{
	@Override
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException
	{
		response.setCharacterEncoding("UTF-8");
		response.setContentType("text/html;charset=utf-8");//ContentType可以参照%tomcat%/conf/web.xml文件中的内容
		PrintWriter out = response.getWriter();
		
		StringBuilder sb = new StringBuilder();
		sb.append("你正在使用的是");
		String userAgent = request.getHeader("user-agent");//获取请求头: user-agent
		
		//判断用户使用的浏览器类型
		if(userAgent.contains("Chrome"))
		{
			sb.append("Chrome");
		}
		else if(userAgent.contains("Firefox"))
		{
			sb.append("Firefox");
		}
		else if(userAgent.contains("Trident"))
		{
			sb.append("IE");
		}
		else 
		{
			sb.append("未知的");
		}
		sb.append("浏览器");
		out.write(sb.toString());
	}
}



3、防止非法链接

防止非法链接主要是依据HTTP请求头中的referer。

package com.rk.http.a_request;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * 案例:防止非法链接
 * 这是需要下载的资源
 */
public class Demo03 extends HttpServlet
{
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException ,IOException 
	{
		response.setCharacterEncoding("UTF-8");
		response.setContentType("text/html;charset=utf-8");
		
		String referer = request.getHeader("referer");//得到referer头
		System.out.println("referer: " + referer);
		
		/**
		 * 判断非法链接:
		 * 	1)直接访问的话referer==null
		 *  2)如果当前请求不是来自广告   
		 */
		if((referer == null) || !(referer.contains("/RK007HTTP/ad.html")))
		{
			response.getWriter().write("当前是非法链接,请回到首页。<a href=‘/RK007HTTP/ad.html‘>首页</a>");
		}
		else
		{
			response.getWriter().write("资源正在下载...");
		}
	}
}



4、获取GET方式和Post方式提交的参数

package com.rk.http.a_request;

import java.io.IOException;
import java.io.InputStream;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * 获取GET方式和Post方式提交的参数
 */
public class Demo04 extends HttpServlet
{
	@Override
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException
	{
		response.setCharacterEncoding("UTF-8");
		response.setContentType("text/html;charset=utf-8");
		String queryString = request.getQueryString();//获取到QueryString
		response.getWriter().write("<h1>通过GET方式获取提交的表单参数</h1>");
		response.getWriter().write(queryString);
	}

	@Override
	protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException
	{
		response.setCharacterEncoding("UTF-8");
		response.setContentType("text/html;charset=utf-8");
		response.getWriter().write("<h1>通过POST方式获取提交的表单参数</h1>");
		InputStream inStream = request.getInputStream();//获取到InputStream
		byte[] buf = new byte[1024];
		int len = 0;
		while((len = inStream.read(buf, 0, buf.length)) != -1)
		{
			String postData = new String(buf,0,len);
			response.getWriter().write(postData);
		}
	}
	
}



5、请求参数编码问题

参数编码问题的原因:

a)浏览器默认情况下以UTF-8编码向Tomcat服务器发送HTTP请求。 同样,Tomcat在接收到HTTP请求时,默认以iso-8859-1进行解码。

b)如果HTTP请求中的数据是英文字符,由于UTF-8对iso-8859-1字符集的兼容性,因此不会出现乱码的问题。

c)如果HTTP请求中的数据是中文字符,由于字符编码和解码的不同,就会出乱码的情况。

要解决乱码的问题,就需要进行编码的转换,思路如下:    String str --> byte[] bytes --> String newString

首先,得到到Tomcat接收到的字符串str;

其次,用iso-8859-1编码方式获取到字符串str的字节数组bytes;

最后,用utf-8编码的方式将字节数组bytes转换为新的字符串newString。

GET方式和POST方式解决乱码问题的一些差异

通过GET方式传递的参数,只能通过对每一个传递的参数进行编码转换。

而通过POST方式传递的参数,除了对每个传递的参数进行编码转换之外,    还有一种简单的方式,就是使用request.setCharacterEncoding("UTF-8");这样后续获取参数时就不需要再进行编码转换了。

package com.rk.http.a_request;

import java.io.IOException;
import java.io.PrintWriter;
import java.io.UnsupportedEncodingException;
import java.util.Arrays;
import java.util.Enumeration;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class Demo05 extends HttpServlet
{

	@Override
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException
	{
		response.setCharacterEncoding("UTF-8");
		response.setContentType("text/html;charset=utf-8");
		PrintWriter out = response.getWriter();
		out.write("<h1>"+request.getMethod()+"方式</h1>");
		
		Enumeration<String> paramEnum =  request.getParameterNames();
		while(paramEnum.hasMoreElements())
		{
			String paramName = paramEnum.nextElement();
			if(paramName.equals("hobby"))//如果参数名是hobby,则调用getParameterValues
			{
				String[] hobbies_iso_8859_1 = request.getParameterValues("hobby");//根据参数名获取参数值(可以获取多个值的同名参数)
				String[] hobbies = new String[hobbies_iso_8859_1.length];
				for(int i=0;i<hobbies_iso_8859_1.length;i++)
				{
					hobbies[i] = convertToUTF8Encoding(hobbies_iso_8859_1[i]);
				}
				out.write(paramName + ": " + Arrays.toString(hobbies) + "<br/>");
			}
			else
			{
				String paramValue_iso_8859_1 = request.getParameter(paramName);// 根据参数名得到参数值(只能获取一个值的参数)
				String paramValue = convertToUTF8Encoding(paramValue_iso_8859_1);
				out.write(paramName + ": " + paramValue + "<br/>");
			}
			
		}
	}

	@Override
	protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException
	{
		/**
		 * 设置参数查询的编码request.setCharacterEncoding("UTF-8");
		 * 该方法只能对请求实体内容的数据编码起作用。POST提交的数据在实体内容中,所以该方法对POST方法有效!
		 * GET方法的参数放在URI后面,所以对GET方式无效!!!
		 * Overrides the name of the character encoding used in the body of this request. 
		 * This method must be called prior to reading request parameters or reading input using getReader().
		 */
		request.setCharacterEncoding("UTF-8");
		
		response.setCharacterEncoding("UTF-8");
		response.setContentType("text/html;charset=utf-8");
		PrintWriter out = response.getWriter();
		out.write("<h1>"+request.getMethod()+"方式</h1>");
		
		Enumeration<String> paramEnum =  request.getParameterNames();
		while(paramEnum.hasMoreElements())
		{
			String paramName = paramEnum.nextElement();
			if(paramName.equals("hobby"))//如果参数名是hobby,则调用getParameterValues
			{
				String[] hobbies = request.getParameterValues("hobby");//根据参数名获取参数值(可以获取多个值的同名参数)
				out.write(paramName + ": " + Arrays.toString(hobbies) + "<br/>");
			}
			else
			{
				String paramValue = request.getParameter(paramName);// 根据参数名得到参数值(只能获取一个值的参数)
				out.write(paramName + ": " + paramValue + "<br/>");
			}
		}
	}
	
	/**
	 * 手动重新解码(iso-8859-1 字符串-> utf-8 字符串)
	 */
	private String convertToUTF8Encoding(String orginalString) throws IOException
	{
		return new String(orginalString.getBytes("iso-8859-1"),"UTF-8");
	}
	
}



以上是关于HTTP协议:HTTP请求案例的主要内容,如果未能解决你的问题,请参考以下文章

通过使用Socket来向Servlet服务器发送GET和POST的HTTP请求协议以及响应案例

怎么用http协议实现安卓数据

Http协议中的请求头

Flutter 报错 DioError [DioErrorType.DEFAULT]: Bad state: Insecure HTTP is not allowed by platform(代码片段

简单的 Javascript http 请求片段但不起作用

接口测试HttpClient&fastJson 总结与案例