简单练习4(Day17、18 JAVA复习)

个人复习


在老师的带领下做了个简单的Servlet,因为代码过多,只贴出来第一第二和最后一个任务的代码

练习3:简单WebServer的实现

1. 需求及实现方法

第一个任务:
写服务器端,多线程的服务器端
1.包:cn.tedu.core
2.类名:WebServer
3.声明成员变量:
server:ServerSocket
4.方法:
无参的构造方法:WebServer
功能:初始化server,端口号为8080
start方法:
功能:启动服务器
接收客户端请求:accept()
定义线程对象,并启动线程start()
5.定义内部类:ClientHandler
线程类定义成员变量:socket:Socket
定义带参的构造方法初始化:socket
重写run方法:功能:控制台输出处理客户端请求

6.定义main方法:启动服务器

7.测试:打开浏览器客户端:http://localhost:8080/

第二个任务:读客户端发给服务器的报头信息

1.读客户端的请求
在run方法处理客户端请求
1)获取InputStream对象
2)使用read方法读取数据,判断如果!=-1,输出
int d = -1;
	while((d= in.read())!=-1){
				
		System.out.print((char)d);
				
	}
3)观察打印结果:学习http协议请求头信息格式
报头的每一行都是以1310
整个请求报头信息完成后,还有一个1310
空行
请求头信息
GET /myweb/images/logo.png HTTP/1.11310
Accept: text/html, application/xhtml+xml, image/jxr, */*1310
Accept-Language: zh-CN1310
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36 Edge/16.162991310
Accept-Encoding: gzip, deflate1310
Host: localhost:80801310
Connection: Keep-Alive1310
1310
                         //这一行必须空	

测试:http://localhost:8080/myweb/index.html
2.解析请求行:
GET /myweb/images/logo.png HTTP/1.11310

核心代码参考:
while循环跳出 最后两个字符是13,10
StringBuilder

int d = -1;
char c1 = 0,c2=0;
while((d= in.read())!=-1){
	c2 = (char)d;
	if(c1==13&&c2==10){
		break;
	}
	builder.append(c2);
	c1 = c2;
		
}
System.out.println(builder.toString().trim());

第三任务:封装请求行中的三部分内容到HttpRequest类中
1.解析请求行

2.定义HttpRequest类
	1)定义HttpRequest类在cn.tedu.http包中
	2)定义变量:method,url,protocol;
	3)定义带参的构造方法HttpRequest(InputStream in)
	4)定义三个变量的get方法
	5)定义方法:parseRquestLine(InputStream in):void
		方法的功能:解析请求行,给三个变量赋值
		在构造方法中调用
3.重构WebServer的run方法
	创建HttpRequest对象,调用get方法打印请求的方法,url,protocl
	
4.测试:打开浏览器客户端:http://localhost:8080/myweb/index.html

第四个任务:读文件,响应文件到客户端
1.在项目中添加目录webapps,并在里面添加一个子目录myweb,
然后在其中存放我们定义的页面index.html
2.响应包括两部分,响应头和响应文件内容
3.学习掌握响应头信息
HTTP/1.1 200 OK1310
Content-Type:text/html1310
Content-Length:201310
1310
4.响应画面到客户端

5.测试:打开浏览器客户端:http://localhost:8080/myweb/index.html

第五个任务:封装HttpResponse类
1.定义HttpResponse类:
1)定义HTTPResponse类在cn.tedu.http包中
2)定义变量:
OutputStream out;
File entity;
定义setEntity()和getEntity()方法。
3)定义构造方法:HttpResponse(OutputStream out)
功能:初始化out成员变量
4)定义方法: println(String line) :void
功能:
向客户端发送一行字符串,该字符串会通过ISO8859-1转换为一组字节并写出.写出后会自动连续写出CRLF
参考代码:
public void println(String line){
out.write(line.getBytes(“ISO8859-1”));
out.write(13);
out.write(10);
}
5)定义方法sendStatusLine():void
功能:发送状态行信息
String line = “HTTP/1.1 200 OK”;
在sendStatusLine()放中调用println(String line)方法。
参考代码:
public void sendStatusLine(){
String line = “HTTP/1.1 200 OK”;
println(line);
}

6)定义方法:getMimeTypeByEntity():String
	功能:根据实体文件的名字获取对应的介质类型,Content-Type使用的值(常用的几种):根据文件扩展名返回文件的介质类型
	核心代码参考:
	String name = entity.getName().substring(
		entity.getName().lastIndexOf(".")+1
	);
	if("html".equals(name)){
		return "text/html";
	}else if("jpg".equals(name)){
		return "image/jpg";
	}else if("png".equals(name)){
		return "image/png";
	}
	else if("gif".equals(name)){
		return "image/gif";
	}
	return "";
	测试:


8)定义方法:sendHeaders();
	功能:响应头信息
	核心代码参考:
	println("Content-Type:"+getMimeTypeByEntity());
	println("Content-Length:"+entity.length());
	println("");//单独发送CRLF表示头发送完毕

9)定义方法: sendContent()
	功能:发送响应正文信息
		核心代码参考:
		fis = new FileInputStream(entity);
		int len = -1;
		byte[] data = new byte[1024*10];
		while((len = fis.read(data))!=-1){
			out.write(data,0,len);
		}
10)定义方法:flush():void 
	功能:调用sendStatusLine();sendHeaders();sendContent()
	
2.重构WebServer:
1)创建HTTPResponse对象
2)把File对象通过set方法传递到reponse
3)调用Flush方法

测试:http://localhost:8080/myweb/index.html

第六个任务:
1.在cn.tedu.core中添加一个类HttpContext
该类用于定义相关Http协议的内容.
比如头信息中Content-Type的值与文件后缀的关系等.
1)在cn.tedu.core包中定义HttpContext类
2)定义两个常量int CR = 13; int LF = 10;
3)定义介质的类型静态变量 Map<String,String> mimeTypeMapping;
4)定义方法private static void initMimeTypeMapping()
功能:初始化介质的类型
mimeTypeMapping = new HashMap<String,String>();
mimeTypeMapping.put(“html”, “text/html”);
mimeTypeMapping.put(“jpg”, “image/jpg”);
mimeTypeMapping.put(“gif”, “image/gif”);
mimeTypeMapping.put(“png”, “image/png”);

5)定义public static String getContentTypeByMime(String mime)方法
	功能:根据给定的介质类型获取对应的Content-Type的值
	return mimeTypeMapping.get(mime);
6)定义初始化的方法public static void init()
	功能:完成HTTPContext初始化的功能
	//1 初始化介质类型映射
	initMimeTypeMapping();
7)定义静态块
	功能:HttpContext加载的时候开始初始化
	static{
		//HttpContext加载的时候开始初始化
		init();
	}
2.在HttpResponse中进行代码重构
1)添加一个Map属性,用于保存响应在中的所有响应头信息.
private Map<String,String> headers = new HashMap<String,String>();
2)添加常用头的设置方法,共外界设置响应头:
public void setContentType(String contentType){
	//把内容类型添加到头信息中
	//this.headers.put("Content-Type", contentType);
}

public void setContentLength(int length){
	//把响应文件的长度添加到头信息中
	this.headers.put("Content-Length", length+"");
}
3)重新实现sendHeaders方法
private void sendHeaders(){
	Set<String> set = headers.keySet();
	for(String name:set){
		String line = name+":"+headers.get(name);
		println(line);//发送每一个头信息
	}
	println("");//单独发送CRLF表示头发送完毕

}
3.重构WebServer的run方法
String contentType = HttpContext.getContentTypeByMime(name);
//设置响应头Content-Type
response.setContentType(contentType);
response.setContentLength((int)file.length());
//设置响应正文
response.setEntity(file);
//响应客户端
response.flush();

测试:http://localhost:8080/myweb/index.html

第七个任务:
完成HttpRequest中对消息头的解析工作
1.HttpRequest中使用Map创建一个属性headers,用于保存所有客户端发送过来的消息头信息
private Map<String,String> headers = new HashMap<String,String>();
2.添加方法parseHeaders,用于解析所有的消息头.
public void paresHeader(InputStream in){
参考读请求的状态行代码
}

3.添加getHeader方法返回头信息
public Map<String, String> getHeaders() {
	return headers;
}

测试:在服务器中测试,检查请求头信息是否正确
private String readLine(InputStream in) throws IOException{
	//返回行字符串
}

调整代码:重复的代码定义方法,分别在parseRquestLine(in);
	paresHeader(in);方法中调用

第八个任务:完成注册的功能
1.重构HttpRequest类
1)添加成员变量
//请求信息
private String requestLine;
//请求所附带的所有参数
private Map<String,String> params = new HashMap<String,String>();
2)定义paresUri():
功能完成:判读是否有?,如果有解析出来方法map集合中

3)在parseRquestLine方法中调用
private void parseRquestLine(InputStream in){
	
4)定义getParameter方法,和getRequestLine
public String getParameter(String name){
	return params.get(name);
}

public String getRequestLine() {
	return requestLine;
}
2.重构run方法
如果myweb/reg
处理注册功能,响应页面到客户端

if("/myweb/reg".equals(request.getRequestLine())){
	//获取客户端数据
	//写数据到数据文件
	System.out.println("注册完毕!");
	//响应页面到客户端
	
}

测试:
封装forward方法

第九个任务:读取web.xml中的介质
在项目目录中添加conf目录,并在里面
添加web.xml文件(该文件直接使用tomcat
根目录中conf目录中的这个文件)
web.xml文件中主要记录了HTTP协议中
头信息Content-Type对应的介质类型.

修改HttpContext对于介质类型映射的
初始化工作,将web.xml文件中的所有
介质类型解析出来并存入到Map中替代原
先写死的内容.使得我们的服务端可以
支持所有的介质类型.


对web.xml文件
从配置文件中读取介质类型,设置到mimeTypeMapping中

第十个任务:完成登录的功能,
1.登录的画面
2.提交请求到服务器:
1)获取表单数据
2)读数据文件,解析每一行的用户名和密码,与出入的参数做
做比较
3)如果登录成功,显示成功的画面login_ok.html
4)失败,显示失败的画面login_error.html

第十一个任务:
1.HttpServlet:抽象类 包名:cn.tedu.servlet
1)定义service(request,response)定义为抽象方法
2)定义forward方法
public abstract class HttpServlet {
public abstract void service(HttpRequest request,HttpResponse response);

}
public void forward(String path,HttpRequest request,HttpResponse response){
	try {
		File file = new File("webapps"+path);
		String name = file.getName().substring(
				file.getName().lastIndexOf(".")+1);
		String contentType 
			= HttpContext.getContentTypeByMime(name);
		//设置响应头Content-Type
		response.setContentType(contentType);
		response.setContentLength((int)file.length());
		//设置响应正文
		response.setEntity(file);
		//响应客户端
		response.flush();	
	} catch (Exception e) {
		e.printStackTrace();
	}
}
}
2.LoginServlet extends HttpServlet
重写service方法,完成登录功能

3.RegServlet extends HttpServlet
重写service方法,完成注册功能

4.重构run

/*
 * 先判断用户请求的是否为业务功能
 */
//是否请求注册功能
if("/myweb/reg".equals(request.getRequestLine())){
	System.out.println("开始注册!");
	RegServlet servlet = new RegServlet();
	servlet.service(request, response);
	
}else if("/myweb/login".equals(request.getRequestLine())){
	System.out.println("处理登录!");
	LoginServlet servlet = new LoginServlet();
	servlet.service(request, response);	
}else{
				
	/*
	 * 查看请求的该页面是否存在
	 */
	File file = new File("webapps"+request.getRequestLine());
	if(file.exists()){
		System.out.println("该文件存在!");
		/*
		 * 响应客户端
		 */
		
		forward(request.getRequestLine(), request, response);
	}else{
		System.out.println("该文件不存在!");
	}
}

第十二个任务:使用反射

	创建一个Map,key为请求路径,value为处理该请求
	的业务类某个Servlet的名字
	ClientHandler当开始处理请求时使用请求路径作为
	key去提取对应的Servlet的名字,然后基于反射机制
	加载并实例化该Servlet,然后调用它的service方法
	处理该业务.
	这样一来,无论以后加什么新的业务,ClientHandler
	都不用再进行修改.

	改动的内容:
	1:添加类ServletContext
	   该类负责存储服务端主要的配置信息
	2:在ServerContext中添加一个Map,用来保存
		请求与对应的Servlet之间的映射关系
		并添加初始化该Map的方法
	3:修改ClientHandler的run方法.基于Map并使用
	   反射方式加载Servlet并执行service处理业务
    
1.添加ServletContext类  包名:cn.tedu.core;
定义map 变量:public static Map<String,String> servletMapping;
定义	initServletMapping
	/**
	 * 初始化Servlet的映射
	 */
	private static void initServletMapping(){
		servletMapping = new HashMap<String,String>();
		servletMapping.put("/myweb/login", "cn.tedu.servlets.LoginServlet");
		servletMapping.put("/myweb/reg", "cn.tedu.servlets.RegServlet");
	}
定义静态的init方法:
	调用initServletMapping
定义静态块:
	调用init方法

2.重构server的run方法
	核心代码参考:
	if(ServletContext.servletMapping.containsKey(
		request.getRequestLine())){
				
				
	String className = ServletContext.servletMapping.get(request.getRequestLine());
	Class clazz = Class.forName(className);
	HttpServlet servlet = (HttpServlet)clazz.newInstance();
	servlet.service(request, response);
				
	}

第十三个任务:定义配置文件
<?xml version="1.0" encoding="UTF-8"?>

<mappings>
	<mapping 
		uri="/myweb/reg" 
		classname="com.tedu.servlets.RegServlet"
	/>
	<mapping 
		uri="/myweb/login" 
		classname="com.tedu.servlets.LoginServlet"
	/>
</mappings>

解析配置文件:重构ServletContext类的initServletMapping()
private static void initServletMapping(){
	servletMapping = new HashMap<String,String>();
	封装配置文件的key,value
}

第十四个任务:解析post请求
在HTTPRequest类中添加解析post请求的方法
在构造方法中调用
private void parseContent(InputStream in){

	//获取消息头中的Content-Type
	String contentType 
		= this.headers.get("Content-Type");
	if(contentType!=null && "application/x-www-form-urlencoded".equals(contentType)){
	int contentLength = Integer.parseInt(
			this.headers.get("Content-Length"));
		try {
			byte[] buf = new byte[contentLength];
			in.read(buf);
			String line = new String(buf);
			System.out.println("form表单内容:"+line);
			line = URLDecoder.decode(line, "UTF-8");
			System.out.println("解码后的form表单内容:"+line);
			解析过程同get请求
		} catch (Exception e) {
			e.printStackTrace();
		}
		
	}
}
把解析数据的代码封装成方法
parseParams(String line):void
String[] paramArr = line.split("&");
for(String paramStr : paramArr){
	String[] para = paramStr.split("=");
	if(para.length==2){
		this.params.put(para[0], para[1]);
	}else if(para.length==1){
		this.params.put(para[0], "");
	}
}

第十五个任务:根据请求方式调用doGet,doPost方法
1.重构HttpServer类
public void service(HttpRequest request,
HttpResponse response){
if(request.getMethod().equals(“GET”)){
this.doGet(request, response);
}else if(request.getMethod().equals(“POST”)){
this.doPost(request, response);
}else{

	}
}
2.在类中定义doGet,doPost方法
public void doGet(HttpRequest request,
		HttpResponse response){
}
public void doPost(HttpRequest request,
		HttpResponse response){
}

2.代码实现

第一个任务实现

public class WebServer {
	private ServerSocket serverSocket;
	private  WebServer(){
		try {
			serverSocket=new ServerSocket(8080);
			System.out.println("服务器初始化成功...");
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
	}
	public void start(){
		while(true){
		try {
			System.out.println("等待客户端请求...");
			Socket socket = serverSocket.accept();
			System.out.println("接受一个客户端请求...");	
			//启动线程服务客户端
			new Thread(new ClientHandler(socket)).start();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		}
	}
	private class ClientHandler implements Runnable{
		private Socket socket;
		public ClientHandler(Socket socket){
			this.socket=socket;
		}
		@Override
		public void run() {
			System.out.println("处理客户端请求");
		}
	}
	 public static void main(String[] args) {
		new WebServer().start();
	}
}

第二个任务实现

public class WebServer {
	private ServerSocket serverSocket;
	private  WebServer(){
		try {
			serverSocket=new ServerSocket(8080);
			System.out.println("服务器初始化成功...");
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		
	}
	public void start(){
		while(true){
		try {
			System.out.println("等待客户端请求...");
			Socket socket = serverSocket.accept();
			System.out.println("接受一个客户端请求...");	
			//启动线程服务客户端
			new Thread(new ClientHandler(socket)).start();
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		}
	}
	private class ClientHandler implements Runnable{
		private Socket socket;
		public ClientHandler(Socket socket){
			this.socket=socket;
		}
		@Override
		public void run() {
			try {
				StringBuilder builder=new StringBuilder();
				InputStream in=socket.getInputStream();
				
				int d = -1;
				char c1 = 0,c2=0;
				while((d= in.read())!=-1){
					c2 = (char)d;
					
					if(c1==13&&c2==10){
						break;
					}
					builder.append(c2);
					c1 = c2;	
				}
				//获取到请求的状态行
				String line=builder.toString().trim();
				System.out.println(line);
				String data[] =line.split(" ");
				//请求方式get,post
				System.out.println(data[0]);
				//请求的url
				System.out.println(data[1]);
				//请求的协议
				System.out.println(data[2]);
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			
		}
		
	}
	 public static void main(String[] args) {
		new WebServer().start();
	}
}

最后一个任务实现

public class HttpContext {
	public static final int CR=13;
	public static final int LF=10;
	private static Map<String,String> map;
	private static void initMimeTypeMapping() throws Exception{
		//map=new HashMap<String,String>();
		map=new HashMap<String,String>();
		SAXReader reader=new SAXReader();
		Document document=reader.read("conf/web.xml"); 
		Element root=document.getRootElement();
		List<Element> list=root.elements("mime-mapping");
		for(Element e:list){
			String key=e.elementText("extension");
			String value=e.elementText("mime-type");
			map.put(key, value);
		}
	}
	public static String getContentTypeByMime(String name){
		return map.get(name);
	}
	public static void init() throws Exception{
		initMimeTypeMapping();
	}
	static{
		try {
			init();
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
}
public class HttpRequest {
	//存表单数据
	private Map<String,String> params=new HashMap<>();
	private String requestLine;
	private Map<String,String> headers=new HashMap<String,String>();
	private String method;
	private String url;
	private String protocol;
	
	public  HttpRequest(InputStream in){
		parseRequestLine(in);
		parseHeader(in);
		parseContent(in);
	}
	
	public void parseContent(InputStream in){
		String contentType=headers.get("Content-Type");
		if(contentType!=null&&contentType.equals("application/x-www-form-urlencoded")){
			int len=Integer.parseInt(headers.get("Content-Length"));
			try {
				byte[] buffer=new byte[len];
				in.read(buffer);
				String paramsValues=new String(buffer);
				parseParams(paramsValues);
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}
	public void parseParams(String line){
		String[] params1=line.split("&");
		for(String str:params1){
			String[] param=str.split("=");
			if(param.length==2){
			params.put(param[0], param[1]);
			}else if(param.length==1){
				params.put(param[0], "");
			}
		}
	}
	public void parseUrl(){
		//1.判断是否有?
		int index=this.url.indexOf("?");
		if(index==-1){
			//2.如果没有那么requestLine=url
			requestLine=url;
		}else{
			//3.如果有:requestLine=url?之前的值
			//把?后边的数据解析出来,设置到params集合中
			requestLine=url.substring(0, index);
			String datas=url.substring(index+1);
			parseParams(datas);
			
		}
	}
	private String readLine(InputStream in) throws IOException{
			StringBuilder builder=new StringBuilder();
			int d = -1;
			char c1 = 0,c2=0;
			while((d= in.read())!=-1){
				c2 = (char)d;
				
				if(c1==13&&c2==10){
					break;
				}
				builder.append(c2);
				c1 = c2;	
			}
			//获取到请求的状态行
			String line=builder.toString().trim();
			return line;
	}
	public String getMethod() {
		return method;
	}
	public String getUrl() {
		return url;
	}
	public String getProtocol() {
		return protocol;
	}
	//解析请求的状态行
	public void parseRequestLine(InputStream in){
		try {
			String line=readLine(in);
			System.out.println(line);
			String data[] =line.split(" ");
			if(data.length==3){
				//请求方式get,post
				//System.out.println(data[0]);
				method=data[0];
				//请求的url
				//System.out.println(data[1]);
				url=data[1];
				parseUrl();
				//请求的协议
				//System.out.println(data[2]);
				protocol=data[2];
			}
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	public void parseHeader(InputStream in){
		while(true){
			try{
		String line=readLine(in);
			//读到空行
			if("".equals(line)){
				break;
			}
			int index=line.indexOf(":");
			//消息头key
			String key=line.substring(0,index);
			//消息头url
			String value=line.substring(index+1);
			
			headers.put(key.trim(),value.trim());
			}catch(Exception e){
				e.getMessage();
			}
		}
	}
	public Map<String,String> getHeaders(){
		return headers;
	}
	public String getParameter(String name){
		return params.get(name);
	}
	public String getRequestLine(){
		return requestLine;
	}
}
public class HttpResponse {
	private OutputStream out;
	private File entity;
	private Map<String,String> headers = new HashMap<String,String>();
	public File getEntity() {
		return entity;
	}
	public void setEntity(File entity) {
		this.entity = entity;
	}
	public HttpResponse(OutputStream out) {
		this.out = out;
	}
	public void println(String line) throws IOException{
		out.write(line.getBytes("ISO8859-1"));
		out.write(HttpContext.CR);
		out.write(HttpContext.LF);
	}
	//响应状态行
	public void sendStatusLine() throws IOException{
		String line="HTTP/1.1 200 OK";
		println(line);
	}
	public void sendRedirect(String url) throws IOException{
		File file=new File("webapps"+url);
		if(file.exists()){
		//设置响应正文
		this.setEntity(file);
		//获取文件后缀 file.getName()获取到完整文件名
		String name = file.getName().substring(
				file.getName().lastIndexOf(".")+1);
		String contentType = HttpContext.getContentTypeByMime(name);
		//设置响应头Content-Type
		this.setContentType(contentType);
		this.setContentLength((int)file.length());
		//响应客户端
		flush();
	}else{
		System.out.println("文件不存在");}
	}
	//响应头信息
	public void sendHeaders() throws IOException{
		Set<String> set = headers.keySet();
		for(String name:set){
			String line = name+":"+headers.get(name);
			println(line);//发送每一个头信息
		}
		println("");//单独发送CRLF表示头发送完毕
	}
	public void sendContent() throws IOException{
		//响应文档内容
		//定义数组
		FileInputStream fileInput=new FileInputStream(entity);
		byte[] buffer=new byte[(int) entity.length()];
		//把数据读到数组中
		fileInput.read(buffer);
		//把数组中的数据写到输出流
		out.write(buffer);
	}
	public void flush() throws IOException{
		this.sendStatusLine();
		this.sendHeaders();
		this.sendContent();
	}
	//设置文档类型
	public void setContentType(String contentType){
		this.headers.put("Content-Type", contentType);
	}
	//设置文档长度
	public void setContentLength(int length){
		this.headers.put("Content-length", length+"");
	}
	public OutputStream getOut(){
		return out;
	}
}
public abstract class HttpServlet{
	public void service(HttpRequest request,HttpResponse response){
		if(request.getMethod().equals("GET")){
			this.doGet(request,response);
		}else if(request.getMethod().equals("POST")){
			this.doPost(request,response);
		}
	}
	public void doGet(HttpRequest request,HttpResponse response){
		
	}
	public void doPost(HttpRequest request,HttpResponse response){

	}
}
public class LoginServlet extends HttpServlet{
	@Override
	public void doGet(HttpRequest request, HttpResponse response){
		String username=request.getParameter("name");
		String pw=request.getParameter("pw");
		//把数据写到数据文件
		
		try {
			BufferedReader bf = new BufferedReader(new FileReader("user.txt"));
			int flag=0;//表示用户名密码不正确
			String str="";
			while((str=bf.readLine())!=null){
				String data[]=str.split("&");
				if(data[0].equals(username)&&data[1].equals(pw)){
					flag=1;
					break;
				}
			}
			if(flag==1){
				response.sendRedirect("/myweb/loginOK.html");
			}else{
				response.sendRedirect("/myweb/loginERROR.html");
			}
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
}
public class RegisterServlet extends HttpServlet{
	@Override
	public void doGet(HttpRequest request, HttpResponse response){
		String username=request.getParameter("name");
		String pw=request.getParameter("pw");
		//把数据写到数据文件
		PrintWriter printwriter;
		try {
			printwriter = new PrintWriter(new FileWriter("user.txt",true));
			printwriter.println(username+"&"+pw);
			printwriter.flush();
			printwriter.close();
			//admin&123123
			//响应一个视图
			response.sendRedirect("/myweb/registerOK.html");
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	public void doPost(HttpRequest request, HttpResponse response){
		doGet(request, response);
	}
}
public class ServletContext {
	public static Map<String,String> servletMapping=new HashMap<>();
	public static void initServletMapping() throws Exception{
	//读文件
	SAXReader reader=new SAXReader();
	Document document=reader.read("conf/ServletMapping.xml");
	Element root=document.getRootElement();
	List<Element> list=root.elements();
	for(Element e:list){
		String uri=e.attributeValue("uri");
		String classname=e.attributeValue("classname");
		servletMapping.put(uri,classname);
		}
	}
	public static void init() throws Exception{
		initServletMapping();
	}
	static{
		try {
			init();
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
}
public class ShowUserServlet extends HttpServlet {
	public void doGet(HttpRequest request,HttpResponse response){
		OutputStream out=response.getOut();
		BufferedReader bf;
		try {
			bf = new BufferedReader(new FileReader("user.txt"));
			int flag=0;//表示用户名密码不正确
			String str="";
				response.sendStatusLine();
				response.sendHeaders();
				out.write("<html>".getBytes());
				out.write("<body>".getBytes());
			while((str=bf.readLine())!=null){
				String data[]=str.split("&");
				out.write(data[0].getBytes());
				out.write(" ".getBytes());
				out.write(data[1].getBytes());
				out.write("<br>".getBytes());
				}
				out.write("</body>".getBytes());
				out.write("</html>".getBytes());
				out.close();
			
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	public void doPost(HttpRequest request,HttpResponse response){
		doGet(request, response);
	}
}
public class UpdateServlet extends HttpServlet {
	public void doGet(HttpRequest request,HttpResponse response){
		//1.获取表单数据
		String username=request.getParameter("name");
		String pw=request.getParameter("pw");
		//把数据写到数据文件
		try{
			BufferedReader bf = new BufferedReader(new FileReader("user.txt"));
			String str="";
			List<String> data=new ArrayList<>();
			while((str=bf.readLine())!=null){
				data.add(str);
				}
			for(int i=0;i<data.size();i++){
				String[] str1=data.get(i).split("&");
				if(str1[0].equals(username)){
					data.set(i, str1[0]+"&"+pw);
					System.out.println(data.toString());
					break;
				}
			}
			
			bf.close();
			
			
			//写数据到数据文件
			PrintWriter printwriter=new PrintWriter("user.txt");
			for(String s:data){
				printwriter.println(s);
				printwriter.flush();
			}
			printwriter.close();
			//响应页面
			response.sendRedirect("/myweb/index.html");
		}catch(Exception e){
				
			}
	}
	public void doPost(HttpRequest request,HttpResponse response){
		doGet(request, response);
	}

}
public class WebServer {
private ServerSocket serverSocket;
	private  WebServer(){
		try {
			serverSocket=new ServerSocket(8080);
			System.out.println("服务器初始化成功...");
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	public void start(){
		while(true){
			try {
				System.out.println("等待客户端请求...");
				Socket socket = serverSocket.accept();
				System.out.println("接受一个客户端请求...");	
				//启动线程服务客户端
				new Thread(new ClientHandler(socket)).start();
				} catch (IOException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
			}
		}
	}
	private class ClientHandler implements Runnable{
		private Socket socket;
		public ClientHandler(Socket socket){
			this.socket=socket;
		}
		@Override
		public void run() {
			try {
				InputStream in = socket.getInputStream();
				OutputStream out=socket.getOutputStream();
				HttpRequest request=new HttpRequest(in);
				HttpResponse response=new HttpResponse(out);
				
				if(ServletContext.servletMapping.containsKey(request.getRequestLine())){
					String className=ServletContext.servletMapping.get(request.getRequestLine());
					Class clazz=Class.forName(className);
					HttpServlet servlet=(HttpServlet)clazz.newInstance();
					servlet.service(request,response);
				}else{
					response.sendRedirect(request.getUrl());
				}
				out.close();	
			} catch (Exception e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}
	 public static void main(String[] args) {
		new WebServer().start();
	}
}
index.html
<body>
	欢迎来到我的网站!<br>
	<a href="register.html">注册</a><br>
	<a href="login.html">登录</a><br>
	<a href="showUser">显示用户信息</a><br>	
	<a href="update.html">修改</a><br>	
	<a href="delete.html">删除</a><br>	
</body>
login.html
<body>
	<form action="/myweb/login" method="get">
		姓名:<input type="text" name="name"/><br>
		密码:<input type="password" name="pw"/><br>
		<input type="submit" value="登录"/>
	</form>
</body>
ServletMapping.xml
<?xml version="1.0" encoding="UTF-8"?>
	<!-- conf/ServletMapping.xml -->
	<mappings>
		<mapping 
			uri="/myweb/register" 
			classname="test16.RegisterServlet"
		/>
		<mapping 
			uri="/myweb/login" 
			classname="test16.LoginServlet"
		/>
		<mapping 
			uri="/myweb/showUser" 
			classname="test16.ShowUserServlet"
		/>
		<mapping 
			uri="/myweb/update" 
			classname="test16.UpdateServlet"
		/>
		<mapping 
			uri="/myweb/delete" 
			classname="test16.DeleteServlet"
		/>
	</mappings>
上一篇:leetcode每日刷题计划-简单篇day17


下一篇:python-day17