Servlet from concept to practice

Posted by hamza on Thu, 30 Dec 2021 18:31:59 +0100

JAVAweb

6, Serverlet

1. Introduction to Servlet

  • Servlet is a technology for sun company to develop dynamic web
  • sun provides an interface called Servlet in these APIs. If you want to develop a Servlet program, you only need to complete two steps:
    • Write a class to implement the Servlet interface;
    • Deploy the developed java classes to the web server;
  • The java program that implements the Servlet interface is called Servlet

2,HelloServlet

  • Build an ordinary Maven project and the sc directory of the management surface. In the future, we will build Moudel in this project; This empty project is called Maven main project;

  • Understanding of Maven father son project;

There will be in the parent project

      <modules>
          <module>servlet-01</module>
      </modules>

Sub projects will have

<parent>
    <artifactId>javaweb-02-servlet</artifactId>
    <groupId>com.kuang</groupId>
    <version>1.0-SNAPSHOT</version>
</parent>

java subprojects in the parent project can be used directly

son extends father
  • Maven environment optimization

    • Modify web XML is the latest
    • Complete the structure of maven
      .
  • Write a Servlet program

    • Write a common class
    • Implement the Servlet interface. Here we directly inherit HttpServlet
 public class HelloServlet extends HttpServlet {
         
         //Because get or post are only different ways of request implementation, they can call each other, and the business logic is the same;
         @Override
         protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
             //ServletOutputStream outputStream = resp.getOutputStream();
             PrintWriter writer = resp.getWriter(); //Response flow
             writer.print("Hello,Serlvet");
         }
     
         @Override
         protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
             doGet(req, resp);
         }
     }

  • Write the mapping of servlets
    Why mapping is needed: we write JAVA programs, but we need to access them through the browser, and the browser needs to connect to the web server, so we need to register the Servlet we write in the web service and give it a path that the browser can access;
<!--register Servlet-->
      <servlet>
          <servlet-name>hello</servlet-name>
          <servlet-class>com.kuang.servlet.HelloServlet</servlet-class>
      </servlet>
      <!--Servlet Request path for-->
      <servlet-mapping>
          <servlet-name>hello</servlet-name>
          <url-pattern>/hello</url-pattern>
      </servlet-mapping>
  • Configure Tomcat
    Note: just configure the project publishing path

  • Start test

3. Principle of Servlet

4. Mapping problem

  • A Servlet can specify a mapping path or multiple mapping paths;
 	   <servlet-mapping>
          <servlet-name>hello</servlet-name>
          <url-pattern>/hello</url-pattern>
      </servlet-mapping>
      <servlet-mapping>
          <servlet-name>hello</servlet-name>
          <url-pattern>/hello2</url-pattern>
      </servlet-mapping>
      <servlet-mapping>
          <servlet-name>hello</servlet-name>
          <url-pattern>/hello3</url-pattern>
      </servlet-mapping>

  • A Servlet can specify a common mapping path
 	  <servlet-mapping>
          <servlet-name>hello</servlet-name>
          <url-pattern>/hello/*</url-pattern>
      </servlet-mapping>
  • A Servlet can specify the default path
<!--Default request path-->
       <servlet-mapping>
           <servlet-name>hello</servlet-name>
           <url-pattern>/*</url-pattern>
       </servlet-mapping>
  • You can specify some suffixes or prefixes
<!--You can customize the suffix to implement request mapping
      Be careful,*The path of the project mapping cannot be preceded
      hello/sajdlkajda.qinjiang
      -->
  <servlet-mapping>
      <servlet-name>hello</servlet-name>
      <url-pattern>*.lengzher</url-pattern>
  </servlet-mapping>
  • Priority issues

The fixed mapping path is specified with the highest priority. If it cannot be found, the default processing request will be taken;

 <!--404-->
  <servlet>
      <servlet-name>error</servlet-name>
      <servlet-class>com.kuang.servlet.ErrorServlet</servlet-class>
  </servlet>
  <servlet-mapping>
      <servlet-name>error</servlet-name>
      <url-pattern>/*</url-pattern>
  </servlet-mapping>

5,ServletContext

When the web container starts, it will create a corresponding ServletContext object for each web application, which represents the current web application;

  • Shared data:

The data saved to ServletContext in this Servlet can be obtained in another Servlet:

  • On the web Registering servlets in XML

<servlet>
        <servlet-name>hello</servlet-name>
        <servlet-class>com.lengzher.servlet.HelloServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>hello</servlet-name>
        <url-pattern>/hello</url-pattern>
    </servlet-mapping>
    <servlet>
        <servlet-name>getContext</servlet-name>
        <servlet-class>com.lengzher.servlet.GetServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>getContext</servlet-name>
        <url-pattern>/get</url-pattern>
    </servlet-mapping>
  • Pass in data in HelloServlet
ublic class HelloServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        ServletContext context = this.getServletContext();
        //Set a key value pair
        String name ="Malone";
        context.setAttribute("name",name);//Save a data in the ServletContext. The key is name and the value is Malone
    }

}
  • Get data in GetServlet
ublic class GetServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        String name = (String)this.getServletContext().getAttribute("name");
//        resp.setContentType("");
//        resp.setCharacterEncoding("utf-8");
        resp.setContentType("text/html; charset=utf-8");
        PrintWriter writer =resp.getWriter();
        writer.print("Name:"+name);
    }
}
  • When running, you need to access the incoming data from HelloServlet first, and then run getservlet to obtain the data;

  • Get parameters
    • Register and initialize data
    <servlet>
            <servlet-name>context</servlet-name>
            <servlet-class>com.lengzher.servlet.ServletDemo</servlet-class>
        </servlet>
        <servlet-mapping>
            <servlet-name>context</servlet-name>
            <url-pattern>/context</url-pattern>
        </servlet-mapping>
        <!--Configure some initialization parameters-->
        <context-param>
            <param-name>url</param-name>
            <param-value>jdbc:mysql://localhost:3306/root</param-value>
        </context-param>
    
    • Start program to get parameters
    public class ServletDemo extends HttpServlet {
        @Override
        protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws IOException {
            ServletContext context =this.getServletContext();
            //Get parameters
            String url =context.getInitParameter("url");
            resp.getWriter().print(url);
    
        }
    }
    
  • Request forwarding
//Registering servlet s with annotations
@WebServlet(name = "forward" ,value = "/froward")
public class ServletDemo1 extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws IOException, ServletException {
        ServletContext context =this.getServletContext();
        //Path to request forwarding
        RequestDispatcher requestDispatcher = context.getRequestDispatcher("/context");
        //Call forward to forward the request
        requestDispatcher.forward(req,resp);

    }
}
  • Properties

When you create a properties file in the java directory or the resources directory of the project, the runtime will package it in the same path: classes, which we call classpath;

@WebServlet(name = "pts",urlPatterns = "/pts")
public class PropertiesServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //Gets the stream to the configuration file
        InputStream is = this.getServletContext().getResourceAsStream("/WEB-INF/classes/db.properties");

        //Load stream
        Properties prop =new Properties();
        prop.load(is);
        String name =prop.getProperty("name");
        String nickName = prop.getProperty("nickName");
        //Write to page
        resp.setContentType("text/html;charset=utf-8");
        PrintWriter writer = resp.getWriter();
        writer.print(name+"go by the name of:"+nickName);
    }
}

6,HTTPServletResponse

The web server receives the http request from the client. For this request, create an HttpServletRequest object representing the request and an HTTPServletResponse representing the response;

  • If you want to get the parameters from the short request: find HttpServletRequest
  • If you want to respond to the client with some information: find HttpServletResponse
6.1. Simple classification
  • Method responsible for sending data to browser
 	servletOutputstream getOutputstream() throws IOException;	//Other strings
    Printwriter getwriter() throws IOException;					//chinese
  • Method responsible for sending response header to browser
void setCharacterEncoding(String var1);
void setContentLength(int var1);
void setContentLengthLong(long var1);
void setContentType(String var1);
void setDateHeader(String varl,long var2)
void addDateHeader(String var1,long var2)
void setHeader(String var1,String var2);
void addHeader(String var1,String var2);
void setIntHeader(String var1,int var2);
void addIntHeader(String varl,int var2);
  • Response status code
 	int SC_CONTINUE = 100;
    int SC_SWITCHING_PROTOCOLS = 101;
    int SC_OK = 200;					//Response successful
    int SC_CREATED = 201;
    int SC_ACCEPTED = 202;
    int SC_NON_AUTHORITATIVE_INFORMATION = 203;
    int SC_NO_CONTENT = 204;
    int SC_RESET_CONTENT = 205;
    int SC_PARTIAL_CONTENT = 206;
    int SC_MULTIPLE_CHOICES = 300;		//3xx redirection
    int SC_MOVED_PERMANENTLY = 301;
    int SC_MOVED_TEMPORARILY = 302;
    int SC_FOUND = 302;
    int SC_SEE_OTHER = 303;
    int SC_NOT_MODIFIED = 304;
    int SC_USE_PROXY = 305;
    int SC_TEMPORARY_REDIRECT = 307;
    int SC_BAD_REQUEST = 400;
    int SC_UNAUTHORIZED = 401;
    int SC_PAYMENT_REQUIRED = 402;
    int SC_FORBIDDEN = 403;
    int SC_NOT_FOUND = 404;			//Resource not found
    int SC_METHOD_NOT_ALLOWED = 405;
    int SC_NOT_ACCEPTABLE = 406;
    int SC_PROXY_AUTHENTICATION_REQUIRED = 407;
    int SC_REQUEST_TIMEOUT = 408;
    int SC_CONFLICT = 409;
    int SC_GONE = 410;
    int SC_LENGTH_REQUIRED = 411;
    int SC_PRECONDITION_FAILED = 412;
    int SC_REQUEST_ENTITY_TOO_LARGE = 413;
    int SC_REQUEST_URI_TOO_LONG = 414;
    int SC_UNSUPPORTED_MEDIA_TYPE = 415;
    int SC_REQUESTED_RANGE_NOT_SATISFIABLE = 416;
    int SC_EXPECTATION_FAILED = 417;
    int SC_INTERNAL_SERVER_ERROR = 500;			
    int SC_NOT_IMPLEMENTED = 501;
    int SC_BAD_GATEWAY = 502;			//Gateway problem
    int SC_SERVICE_UNAVAILABLE = 503;
    int SC_GATEWAY_TIMEOUT = 504;
    int SC_HTTP_VERSION_NOT_SUPPORTED = 505;
6.2 common applications
  • Output message to browser

  • Download File
    • 1. To get the path of the downloaded file
    • 2. Downloaded file name
    • 3. Set the browser to support downloading the files we need
    • 4. Get the downloaded input stream
    • 5. Create buffer
    • 6. Get OutputStream object
    • 7. Write the FileOutputStream stream to the buffer buffer
    • 8. Use OutputStream to output the data in the buffer to the client
    @WebServlet(name = "load" , urlPatterns = "/load")
    public class FileServlet extends HttpServlet {
        @Override
        protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
    //                * 1. To get the path of the downloaded file
    //        String realPath ="E:\\java\\MYworkspace\\java-web03-maven\\response\\src\\main\\resources\\responseimg.png";
            String realPath =this.getServletContext().getRealPath("/WEB-INF/classes/Good.png");
    //                * 2. Downloaded file name
            String fileName =realPath.substring(realPath.lastIndexOf("/")+1);//Intercept the contents after the last string "\ \"
    //                * 3. Set the browser to support downloading (content disposition) the files we need
            resp.setHeader("Content-Disposition","attachment;filename="+ URLEncoder.encode(fileName,"UTF-8"));
    //                * 4. Get downloaded input stream
            FileInputStream fis = new FileInputStream(realPath);
    //                * 5. Create buffer
            int len=-1;
            byte[] bytes =new byte[1024];
    //                * 6. Get OutputStream object
            ServletOutputStream os = resp.getOutputStream();
    //                * 7. Write the FileOutputStream stream to the buffer buffer, and use OutputStream to output the data in the buffer to the client
            while ((len=fis.read(bytes))!=-1){
                os.write(bytes,0,len);
            }
            os.close();
            fis.close();
        }
        @Override
        protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        }
    }
    
  • Verification code function
    • How does the verification implementation come from?

      • Front end implementation
      • The back-end implementation needs to use the java picture class to generate a picture
      @WebServlet(name = "imgs" , urlPatterns = "/imgs")
      public class ImageServlet extends HttpServlet {
          @Override
          protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
              //Let the browser refresh every few seconds
              resp.setHeader("refresh","3");
      
              //Create a picture in memory and set the size
              BufferedImage img =new BufferedImage(120,60,BufferedImage.TYPE_INT_RGB);
              //Get pictures
              Graphics2D graphics = (Graphics2D)img.getGraphics();
              //Set the background color of the picture
              graphics.setColor(Color.white);
              graphics.fillRect(0,0,120,60);
      
              //Write data to pictures
              graphics.setColor(Color.blue);
              graphics.setFont(new Font(null,Font.BOLD,20));
              graphics.drawString(makeNum(),0,20);
      
              //Tell the browser that the request is opened as a picture
              resp.setContentType("image/jpg");
              //There is a cache in the website. Do not let the browser cache
              resp.setDateHeader("expires",-1);
              resp.setHeader("Cache-Control","no-cache");
              resp.setHeader("Pragma","no-cache");
      
              //Write pictures to browser
              ImageIO.write(img,"jpg",resp.getOutputStream());
              PrintWriter writer = resp.getWriter();
              writer.print(graphics);
          }
          //Generate random number
          private String makeNum(){
              Random random = new Random();
              String s = random.nextInt(99999999)+"";
              StringBuffer sb =new StringBuffer();
              //Less than eight digits, filled with 0
              for (int i = 0; i < 8-s.length(); i++) {
                  sb.append("0");
              }
              s=sb.toString()+s;
              return s;
          }
      }
      
      

  • redirect

After a web resource (A) receives a client request, it will notify the client to access another web resource (B). This process is called redirection:

Common scenario: user login

method:

void sendRedirect(String varl) throws IOEx

Implement redirection:

@WebServlet(name = "red" ,urlPatterns = "/red")
public class RedirectServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
       resp.sendRedirect("/resp/imgs");
        //Implementation principle
        /*
        resp. setHeader("Location","/r/img");
        resp. setstatus (302);
        */
    }

}

Enable login:

1. Design landing page

<html>
<body>
<h2>Hello World!</h2>
<%--${pageContext.request.contextPath}Represents the current project--%>
<form action="${pageContext.request.contextPath}/login" method="get">
    user name:<input type="text" name="username"><br>
    password:<input type="password" name="password"><br>
    <input type="submit">
</form>
</body>
</html>

2. Set redirection jump, pointing to successful JSP page

//@WebServlet(name = "login",urlPatterns = "/login")
public class LoginServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp)throws IOException , ServletException{
        String username =req.getParameter("username");
        String password =req.getParameter("password");
        System.out.println("username:"+username+"\tpassword: "+password);

        resp.sendRedirect("/resp/successful.jsp");
    }
}
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>Successful</title>
</head>
<body>
    <h1>Successful!!!</h1>
</body>
</html>

7,HTTPServletRequest

HttpServletRequest represents the request of the client. The user accesses the server through the HTTP protocol. All the information in the HTTP request will be encapsulated in HttpServletRequest. Through this HttpServletRequest method, all the information of the client can be obtained;

Get the parameters and request forwarding passed by the front end
  • index.jsp login content
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>Sign in</title>
</head>
<body>
    <h1>Sign in</h1>
<div>
    <form action="${pageContext.request.contextPath}/login" method="get">
    user name:<input type="text" name="username"><br>
    password:<input type="password" name="password"><br>
    Hobbies:
    <input type="checkbox" name="hobby" value="Men's ball">Men's ball
    <input type="checkbox" name="hobby" value="Female ball">Female ball
    <input type="checkbox" name="hobby" value="Volleyball">Volleyball
    <input type="checkbox" name="hobby" value="Table tennis">Bing ping pong
    <br>

    <input type="submit">
    </form>
</div>
</body>
</html>
  • The Servlet class implements login jump
@WebServlet(name = "login",urlPatterns = "/login")
public class LoginServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        req.setCharacterEncoding("utf-8");
        resp.setContentType("text/jsp;charset=utf-8");
        String username = req.getParameter("username");
        String password = req.getParameter("password");
        String[] hobbys =req.getParameterValues("hobby");

        System.out.println(username+"|"+password+"Hobbies:"+hobbys);

        req.getRequestDispatcher("/success.jsp").forward(req,resp);
    }
}

Topics: Java Maven Spring Tomcat