服务端处理流程:
浏览器提交表单到服务端 -服务端解析请求-处理请求-发送响应
![](https://img-blog.csdnimg.cn/c940bf89e16841ea9aa82bda18993385.png)
1.1新建一个maven项目,创建一个主启动对象(AppLication),添加构造方法启动服务端,添加start方法启动一个线程与客户端交互
main方法新建主启动对象调用start方法
package com.webserver.core;
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
/**
* 主启动类
*/
public class BirdApplication {
private ServerSocket serverSocket;
public BirdApplication(){
try {
System.out.println("正在启动服务端...");
serverSocket = new ServerSocket(8088);
System.out.println("服务端启动完毕!");
} catch (IOException e) {
e.printStackTrace();
}
}
public void start(){
try {
Socket socket = serverSocket.accept();
//启动一个线程处理与该客户端的交互
ClientHandler handler = new ClientHandler(socket);
Thread t = new Thread(handler);
t.start();
} catch (IOException e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
BirdApplication application = new BirdApplication();
application.start();
}
}
1.2创建一个客户端处理程序对象(ClientHandler) 实现Runable接口
添加构造方法,重写run方法 ,添加sock.getInputStream流读取浏览器发送请求(读取请求行)
测试
**
* 与指定的客户端完成一次HTTP交互
* HTTP协议要求浏览器与服务端交互采取一问一答的原则,因此服务端这里处理一次交互由
* 三步骤完成(参考【服务器处理流程示意图】):
* 1:解析请求
* 2:处理请求
* 3:发送响应
*/
public class ClientHandler implements Runnable{
private Socket socket;
public ClientHandler(Socket socket){
this.socket = socket;
}
public void run() {
try {
InputStream in = socket.getInputStream();
int d;
StringBuilder builder = new StringBuilder();//拼接读取的字符
char cur='a',pre='a';//cur表示本次读取的字符,pre表示上次读取的字符
while((d = in.read())!=-1){
cur = (char)d;//本次读取到的字符
if(pre==13&&cur==10){//是否连续读取到了回车+换行(判断是否读取完一行了)
break;
}
builder.append(cur);//将本次读取的字符拼接到已经读取的字符串中
pre = cur;//再下次读取字符前,将本次读取的字符记作上次读取的字符
}
String line = builder.toString().trim();
System.out.println("请求行:"+line);
String[] data = line.split("\\s");//[GET, /index.html, HTTP/1.1]
String method = data[0];//请求方式
String uri = data[1];//抽象路径
String protocol = data[2];//协议版本
System.out.println("method:"+method);
System.out.println("uri:"+uri);
System.out.println("protocol:"+protocol);
} catch (IOException e) {
e.printStackTrace();
}
}
}
2.1添加readLine方法封装读取浏览器发送的请求(按行读取并返回)
2.2解析请求,通过正则表达式的方式拆分请求行(请求方式/抽象路径/协议版本)
解析消息头:添加map集 通过正则表达式的方式拆分并添加到map集中
package com.webserver.core;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.net.Socket;
import java.util.HashMap;
import java.util.Map;
/**
* 与指定的客户端完成一次HTTP交互
* HTTP协议要求浏览器与服务端交互采取一问一答的原则,因此服务端这里处理一次交互由
* 三步骤完成(参考【服务器处理流程示意图】):
* 1:解析请求
* 2:处理请求
* 3:发送响应
*/
public class ClientHandler implements Runnable {
private Socket socket;
public ClientHandler(Socket socket) {
this.socket = socket;
}
public void run() {
try {
//1解析请求
//1.1:解析请求行
String line = readLine();//读取请求中的第一行(请求行)
System.out.println("请求行:" + line);
String[] data = line.split("\\s");//[GET, /index.html, HTTP/1.1]
String method = data[0];//请求方式
String uri &