Personal Review
Led by the teacher, I made a simple Servlet, because there was too much code, only the first, second and last task code was posted.
Exercise 3: Implementation of Simple Web Server
1. Requirements and implementation methods
First task:
Write server side, multithreaded server side
1. Package: cn.tedu.core
2. Class name: WebServer
3. Declare member variables:
server: ServerSocket
4. Methods:
Parametric-free construction method: WebServer
Function: Initialize server, port number 8080
start method:
Function: Start the server
Receiving client request: accept ()
Define the thread object and start the thread start ()
5. Define internal classes: ClientHandler
Thread class defines member variables: socket: Socket
Define the initialization of the constructor with parameters: socket
Rewrite run Method: Function: Console Output Processing Client Request
6. Define the main method: Start the server 7. Test: Open the browser client: http://localhost:8080/
Second task: read the header information sent by the client to the server
1. Read client requests Processing client requests in run method 1) Get InputStream objects 2) Use read method to read data, judge if!=-1, output int d = -1; while((d= in.read())!=-1){ System.out.print((char)d); } 3) Observing print results: learning http protocol request header information format Every line in the header is 1310 After the entire request header information is completed, there is another 1310 Blank line Request header information 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 // This line must be empty.
Test: http://localhost:8080/myweb/index.html
2. Parse the request line:
GET /myweb/images/logo.png HTTP/1.11310
Core Code Reference: while The last two characters that jump out of the loop are 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());
Third task: Encapsulate three parts of the request line into the HttpRequest class
1. Parse the request line
2. Define the HttpRequest class 1) Define the HttpRequest class in the cn.tedu.http package 2) Define variables: method, url, protocol; 3) Define the construction method with parameters HttpRequest (Input Stream in) 4) get method for defining three variables 5) Definition method: parseRquestLine (Input Stream in): void Function of the method: parse the request line and assign values to three variables Called in the constructor 3. The run Method of Reconstructing Web Server Create HttpRequest object, call get method to print request method, url, protocl 4. Test: Open the browser client: http://localhost:8080/myweb/index.html
Fourth task: read the file and respond to the file to the client
1. Add directory webapps to the project and add a subdirectory myweb to it.
Then we store our defined page index.html in it.
2. Response consists of two parts, response header and response file content.
3. Learning to Master Response Header Information
HTTP/1.1 200 OK1310
Content-Type:text/html1310
Content-Length:201310
1310
4. Response screen to client
5. Test: Open the browser client: http://localhost:8080/myweb/index.html
Fifth task: Encapsulating the HttpResponse class
1. Define the HttpResponse class:
1) Define the HTTPResponse class in the cn.tedu.http package
2) Define variables:
OutputStream out;
File entity;
Define setEntity () and getEntity() methods.
3) Define the construction method: HttpResponse (Output Stream out)
Function: Initialize out member variables
4) Definition method: println (String line): void
Functions:
Send a line of string to the client, which will be converted to a set of bytes by ISO8859-1 and written out. After writing out, CRLF will be written out automatically and continuously.
Reference code:
public void println(String line){
out.write(line.getBytes("ISO8859-1"));
out.write(13);
out.write(10);
}
5) Define method sendStatusLine():void
Function: Send status line information
String line = "HTTP/1.1 200 OK";
Call the println(String line) method in sendStatusLine().
Reference code:
public void sendStatusLine(){
String line = "HTTP/1.1 200 OK";
println(line);
}
6) Definition method: getMimeTypeByEntity(): String Function: Get the corresponding media type according to the name of the entity file, the value used by Content-Type (several commonly used): Return the media type of the file according to the file extension Core Code Reference: 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 ""; Test: 8) Definition method: sendHeaders(); Function: Response Header Information Core Code Reference: println("Content-Type:"+getMimeTypeByEntity()); println("Content-Length:"+entity.length()); println(");// Send CRLF separately to indicate that the hair has been sent. 9) Definition method: sendContent() Function: Send Response Text Information Core Code Reference: 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) Definition method: flush():void Functions: Call sendStatusLine (); sendHeaders(); sendContent() 2. Refactoring WebServer: 1) Create HTTPResponse objects 2) Pass File objects through set method to reponse 3) Call the Flush method Test: http://localhost:8080/myweb/index.html
Sixth task:
1. Add a class HttpContext to cn.tedu.core
This class is used to define the content of relevant Http protocols.
For example, the relationship between the value of Content-Type in header information and file suffixes.
1) Define the HttpContext class in the cn.tedu.core package
2) Define two constants int CR = 13; int LF = 10;
3) Define the type of medium static variable Map < String, String > mimeType Mapping;
4) Define the method private static void initMimeTypeMapping()
Function: Initialize the type of media
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)Definition public static String getContentTypeByMime(String mime)Method //Function: Get the corresponding Content-Type value according to the given media type return mimeTypeMapping.get(mime); 6)Define the method of initialization public static void init() //Function: Complete HTTPContext initialization function //1 Initialize Media Type Mapping initMimeTypeMapping(); 7)Define static blocks //Function: Initialization starts when HttpContext loads static{ //Initialization begins when HttpContext loads init(); } 2.stay HttpResponse Code refactoring 1)Add a Map attribute,Used to save all response header information in response. private Map<String,String> headers = new HashMap<String,String>(); 2)Setting Method for Adding Common Headers,Setting Response Head in Common Outside: public void setContentType(String contentType){ //Adding content types to header information //this.headers.put("Content-Type", contentType); } public void setContentLength(int length){ //Add the length of the response file to the header information this.headers.put("Content-Length", length+""); } 3)Re-realization sendHeaders Method private void sendHeaders(){ Set<String> set = headers.keySet(); for(String name:set){ String line = name+":"+headers.get(name); println(line);//Send each header message } println("");//Sending CRLF separately indicates that the hair has been sent. } 3.Restructure WebServer Of run Method String contentType = HttpContext.getContentTypeByMime(name); //Setting Response Header Content-Type response.setContentType(contentType); response.setContentLength((int)file.length()); //Setting the response body response.setEntity(file); //Response Client response.flush(); //Test: http://localhost:8080/myweb/index.html
The seventh task:
Complete the parsing of message headers in HttpRequest
1.HttpRequest uses Map to create an attribute headers to store the header information sent by all clients.
private Map<String,String> headers = new HashMap<String,String>();
2. Add method parseHeaders to parse all message headers.
public void paresHeader(InputStream in){
Refer to the status line code of the read request
}
3. Add getHeader method to return header information public Map<String, String> getHeaders() { return headers; } Testing: Testing in the server to check whether the request header information is correct private String readLine(InputStream in) throws IOException{ // Returns a row string } Adjust the code: duplicate code definition methods in parseRquestLine(in); paresHeader(in); method call
Task 8: Complete the registration function
1. Refactoring the HttpRequest class
1) Add member variables
// Request information
private String requestLine;
// All parameters attached to the request
private Map<String,String> params = new HashMap<String,String>();
2) Define paresUri ():
Function Completion: Is there any interpretation? If there are parsed methods in the map set
3) Called in the parseRquestLine method private void parseRquestLine(InputStream in){ 4) Define getParameter method and getRequestLine public String getParameter(String name){ return params.get(name); } public String getRequestLine() { return requestLine; } 2. Reconstructing run Method If myweb/reg Processing registration function, response page to client if("/myweb/reg".equals(request.getRequestLine())){ // Getting Client Data // Write data to data files System.out.println("Registered!"); // Response page to client } Test: Encapsulation forward method
Task 9: Reading Media in web.xml
Add the conf directory to the project directory and add it to it
Add the web.xml file (which uses tomcat directly)
This file in the conf directory in the root directory)
The HTTP protocol is mainly recorded in the web.xml file.
The media type corresponding to the header information Content-Type.
Modifying the HttpContext mapping for media types Initialize all of the work in the web.xml file The medium type is parsed out and stored in Map instead of the original one. Write dead content first, so that our server can Supports all media types. For web.xml files Read the media type from the configuration file and set it to mimeType Mapping
Task 10: Complete the login function.
1. Log-in screen
2. Submit the request to the server:
1) Get form data
2) Read the data file, parse the username and password of each line, and do it with the parameters of entry and exit.
Compare
3) If the login is successful, the successful screen login_ok.html will be displayed.
4) Failure, display the failed screen login_error.html
The eleventh task:
1.HttpServlet: abstract class package name: cn.tedu.servlet
1) Define service (request, response) as an abstract method
2) Define forward method
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); //Setting Response Header Content-Type response.setContentType(contentType); response.setContentLength((int)file.length()); //Setting the response body response.setEntity(file); //Response Client response.flush(); } catch (Exception e) { e.printStackTrace(); } } } 2.LoginServlet extends HttpServlet //Rewrite service method to complete login function 3.RegServlet extends HttpServlet //Rewrite service method to complete registration function 4.Restructure run /* * First determine whether the user's request is a business function */ //Whether to request registration function if("/myweb/reg".equals(request.getRequestLine())){ System.out.println("Start registration!"); RegServlet servlet = new RegServlet(); servlet.service(request, response); }else if("/myweb/login".equals(request.getRequestLine())){ System.out.println("Processing login!"); LoginServlet servlet = new LoginServlet(); servlet.service(request, response); }else{ /* * See if the requested page exists */ File file = new File("webapps"+request.getRequestLine()); if(file.exists()){ System.out.println("The document exists!"); /* * Response Client */ forward(request.getRequestLine(), request, response); }else{ System.out.println("This file does not exist!"); } }
Twelfth Task: Use Reflection
Create a Map with key as the request path and value as the processing of the request The name of a Servlet in the business class ClientHandler uses the request path as the starting point for processing requests key extracts the name of the corresponding Servlet, and then based on reflection mechanism Load and instantiate the Servlet, and then call its service method Handle the business. In this way, no matter what new business is added in the future, ClientHandler Neither need to be modified. Contents of the changes: 1: Add the ServletContext class This class is responsible for storing the main configuration information on the server side. 2: Add a Map to ServerContext to save Mapping relationship between requests and corresponding servlets And add a method to initialize the Map 3: Modify the run method of ClientHandler. Based on Map and use it Reflective loading of servlets and service processing 1. Add ServletContext class package name: cn.tedu.core; Define map variables: public static Map < String, String > servlet Mapping; Definition of initServletMapping /** * Initialize Servlet mapping */ 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"); } Define static init methods: Call initServletMapping Define static blocks: Call init method 2. run method of reconstructing server Core Code Reference: 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); }
Thirteenth task: Define configuration files
<?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> //Resolve the configuration file: Reconstruct initServletMapping() of the ServletContext class private static void initServletMapping(){ servletMapping = new HashMap<String,String>(); //Encapsulate the key, value of the configuration file }
Fourteenth task: parsing post requests
Adding a method of parsing post requests to the HTTPRequest class
Called in the constructor
private void parseContent(InputStream in){
//Get Content-Type in the header 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 Form content:"+line); line = URLDecoder.decode(line, "UTF-8"); System.out.println("Decoded form Form content:"+line); //Parsing process and get request } catch (Exception e) { e.printStackTrace(); } } } //Encapsulate the code that parses the data into a method 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], ""); } }
Task 15: Call the doGet, doPost method on request
1. Refactoring the HttpServer class
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.Definition in a class doGet,doPost Method public void doGet(HttpRequest request, HttpResponse response){ } public void doPost(HttpRequest request, HttpResponse response){ }
2. Code Implementation
First task realization
public class WebServer { private ServerSocket serverSocket; private WebServer(){ try { serverSocket=new ServerSocket(8080); System.out.println("Successful server initialization..."); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } public void start(){ while(true){ try { System.out.println("Waiting for Client Request..."); Socket socket = serverSocket.accept(); System.out.println("Accept a client request..."); //Start Thread Service Client 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("Processing client requests"); } } public static void main(String[] args) { new WebServer().start(); } }
Second task realization
public class WebServer { private ServerSocket serverSocket; private WebServer(){ try { serverSocket=new ServerSocket(8080); System.out.println("Successful server initialization..."); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } public void start(){ while(true){ try { System.out.println("Waiting for Client Request..."); Socket socket = serverSocket.accept(); System.out.println("Accept a client request..."); //Start Thread Service Client 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; } //Get the status line of the request String line=builder.toString().trim(); System.out.println(line); String data[] =line.split(" "); //Request mode get, post System.out.println(data[0]); //url of request System.out.println(data[1]); //Request agreement System.out.println(data[2]); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } } public static void main(String[] args) { new WebServer().start(); } }
Last task realization
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 { //Inventory form data 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. Is there a judgment? int index=this.url.indexOf("?"); if(index==-1){ //2. If not, requestLine=url requestLine=url; }else{ //3. If so: requestLine=url? Previous values //Put? The data behind is parsed and set into the params collection 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; } //Get the status line of the request String line=builder.toString().trim(); return line; } public String getMethod() { return method; } public String getUrl() { return url; } public String getProtocol() { return protocol; } //Resolve the status line of the request public void parseRequestLine(InputStream in){ try { String line=readLine(in); System.out.println(line); String data[] =line.split(" "); if(data.length==3){ //Request mode get, post //System.out.println(data[0]); method=data[0]; //url of request //System.out.println(data[1]); url=data[1]; parseUrl(); //Request agreement //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); //Read empty lines if("".equals(line)){ break; } int index=line.indexOf(":"); //Message header key String key=line.substring(0,index); //Header 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); } //Response status line 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()){ //Setting the response body this.setEntity(file); //Get the file suffix file.getName() to get the full file name String name = file.getName().substring( file.getName().lastIndexOf(".")+1); String contentType = HttpContext.getContentTypeByMime(name); //Setting Response Header Content-Type this.setContentType(contentType); this.setContentLength((int)file.length()); //Response Client flush(); }else{ System.out.println("file does not exist");} } //Response header information public void sendHeaders() throws IOException{ Set<String> set = headers.keySet(); for(String name:set){ String line = name+":"+headers.get(name); println(line);//Send each header message } println("");//Sending CRLF separately indicates that the hair has been sent. } public void sendContent() throws IOException{ //Response to document content //Define arrays FileInputStream fileInput=new FileInputStream(entity); byte[] buffer=new byte[(int) entity.length()]; //Read the data into an array fileInput.read(buffer); //Write the data in the array to the output stream out.write(buffer); } public void flush() throws IOException{ this.sendStatusLine(); this.sendHeaders(); this.sendContent(); } //Setting Document Type public void setContentType(String contentType){ this.headers.put("Content-Type", contentType); } //Setting document length 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"); //Write data to a data file try { BufferedReader bf = new BufferedReader(new FileReader("user.txt")); int flag=0;//Indicates that the username password is incorrect 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"); //Write data to a data file PrintWriter printwriter; try { printwriter = new PrintWriter(new FileWriter("user.txt",true)); printwriter.println(username+"&"+pw); printwriter.flush(); printwriter.close(); //admin&123123 //Response to a view 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{ //read file 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;//Indicates that the username password is incorrect 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. Get form data String username=request.getParameter("name"); String pw=request.getParameter("pw"); //Write data to a data file 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(); //Write data to data files PrintWriter printwriter=new PrintWriter("user.txt"); for(String s:data){ printwriter.println(s); printwriter.flush(); } printwriter.close(); //Response page 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("Successful server initialization..."); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } public void start(){ while(true){ try { System.out.println("Waiting for Client Request..."); Socket socket = serverSocket.accept(); System.out.println("Accept a client request..."); //Start Thread Service Client 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> Welcome to my website!<br> <a href="register.html">register</a><br> <a href="login.html">Sign in</a><br> <a href="showUser">Display user information</a><br> <a href="update.html">modify</a><br> <a href="delete.html">delete</a><br> </body>
login.html <body> <form action="/myweb/login" method="get"> //Full name:<input type="text" name="name"/><br> //Password:<input type="password" name="pw"/><br> <input type="submit" value="Sign in"/> </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>