六狼论坛

 找回密码
 立即注册

QQ登录

只需一步,快速开始

新浪微博账号登陆

只需一步,快速开始

搜索
查看: 49|回复: 0

打造自己的web容器(1)

[复制链接]

升级  82%

9

主题

9

主题

9

主题

童生

Rank: 1

积分
41
 楼主| 发表于 2013-1-15 02:55:18 | 显示全部楼层 |阅读模式
---- Socket入门

近日,读到一本好书---《How Tomcat Works》,该书详尽分析了tomcat的实现原理,解释了它的servlet容器的内部运行机制,读来非常有收获,特此撰文将读书过程中的一些心得付诸文字。

HTTP协议基础知识:

HTTP协议属于应用层协议,基于TCP,一个HTTP请求包括三个组成部分:方法—统一资源标识符(URI)—协议/版本、请求的头部、主体内容

HTTP请求示例:
POST /examples/default.jsp HTTP/1.1Accept: text/plain; text/htmlAccept-Language: en-gbConnection: Keep-AliveHost: localhostUser-Agent: Mozilla/4.0 (compatible; MSIE 4.01; Windows 98)Content-Length: 33Content-Type: application/x-www-form-urlencodedAccept-Encoding: gzip, deflatelastName=Franks&firstName=Michael

类似于HTTP请求,一个HTTP响应也包括三个组成部分:方法—统一资源标识符(URI)—协议/版本、响应的头部、主体内容

HTTP响应示例:
HTTP/1.1 200 OKServer: Microsoft-IIS/4.0Date: Mon, 5 Jan 2009 13:13:33 GMTContent-Type: text/htmlLast-Modified: Mon, 5 Jan 2009 13:13:12 GMTContent-Length: 112<html><head><title>HTTP Response Example</title></head><body>Welcome !!</body></html>

基于Socket的客户端-服务器:

客户端代码:

public static void main(String[] args) throws InterruptedException {try {//创建一个流套接字并将其连接到指定 IP 地址的指定端口号Socket socket = new Socket("127.0.0.1", 8080);//模拟发送HTTP请求OutputStream os = socket.getOutputStream();StringBuilder request = new StringBuilder();request.append("GET /index.jsp HTTP/1.1\n");request.append("Host: localhost:8080\n");request.append("Connection: Close\n");request.append("\n");os.write(request.toString().getBytes());os.flush();//os.close();//关闭 OutputStream 将关闭关联套接字//读取服务端响应BufferedReader in = new BufferedReader(new InputStreamReader(socket.getInputStream()));boolean loop = true;StringBuffer sb = new StringBuffer(8096);while (loop) {if (in.ready()) {int i = 0;while (i != -1) {i = in.read();sb.append((char) i);}loop = false;}}System.out.println(sb.toString());socket.close();}catch (UnknownHostException e) {// log error info}catch (IOException e) {// log error info}}


服务器端代码:

public static void main(String[] args) {boolean shutdown = false;ServerSocket serverSocket = null;int port = 8080;try {//ServerSocket构造方法的参数说明:port - 本地 TCP 端口,backlog - 队列的最大长度,bindAddr - 要将服务器绑定到的 InetAddressserverSocket = new ServerSocket(port, 2, InetAddress.getByName("127.0.0.1"));}catch (IOException e) {// log error infoSystem.exit(1);}// 等待请求while (!shutdown) {try {//侦听并接受到此套接字的连接。此方法在连接传入之前一直阻塞Socket socket = serverSocket.accept();//返回此套接字的输出流,用于向客户端写入返回结果OutputStream output = socket.getOutputStream();//获取输入流,即客户端发起的HTTP请求BufferedReader in = new BufferedReader(new InputStreamReader(socket.getInputStream()));StringBuffer sb = new StringBuffer(8096);boolean loop = true;while (loop) {if (in.ready()) {int i = 0;while (i != -1) {i = in.read();sb.append((char) i);}loop = false;}}// display the request to the out consoleSystem.out.println(sb.toString());output.write("Response: HTTP/1.1 200 OK ".getBytes());}catch (Exception e) {// log error infocontinue;}}}
您需要登录后才可以回帖 登录 | 立即注册 新浪微博账号登陆

本版积分规则

快速回复 返回顶部 返回列表