(a) Setvlet basic overview

(1) What is a Servlet?

Servlet (Server Applet) is the abbreviation of JavaServlet, which is called small service program or service connector. It is a server-side program written in Java, which is independent of platform and protocol. Its main function is to browse and generate data interactively and generate dynamic Web content

In JavaWeb, we will contact three major components (Servlet, Filter, Listener), Servlet is called by the server, processing the server received the request, that is, complete, accept the request data -> process the request -> complete the response, It is essentially a Java class that implements the Servlet interface

The Servlet class is written by us, but the object is created by the server and the corresponding method is called by the server

(2) What are servlets used for?

Some of the more common functions in the network, such as login, registration, so there is interactive function, and Servlet can help us to handle these requests, can say Servlet is one of the important knowledge points in JavaWeb knowledge

(2) the way to realize servlets

There are three ways to implement servlets:

  • Implement javax.servlet.servlet interface;
  • Inheritance javax.mail. Servlet. GenericServlet class;
  • Inheritance javax.mail. Servlet. HTTP. HttpServlet class;

In practice, we often choose to inherit the HttpServlet class to complete our servlets, but it is important to understand the Servlet interface in this way, and it is an integral part of our introduction

(1) Create our first servlets

We create a web project, select the corresponding parameters, we install JDK 1.8, you can choose to JavaEE8 version, the corresponding versions is 4.0, but we choose here is more commonly used in the market version 7

We’ll create a Demo class that implements the Servlet interface, and then we’ll quickly generate the methods that are not implemented in that interface. We’ll ignore the other four methods in the Servlet for the moment, and only care about the service() method, because it’s the method that handles requests, and we’ll give an output statement in that method

package cn.ideal.web.servlet;

import javax.servlet.*;
import java.io.IOException;

public class ServeltDemo1 implements Servlet {
    // Initialize the method
    @Override
    public void init(ServletConfig servletConfig) throws ServletException {}//Servlet configuration method
    @Override
    public ServletConfig getServletConfig(a) {
        return null;
    }

    // Provide the service method
    @Override
    public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {
        System.out.println("The ideal is more than twenty years old");
    }

    //Servlet information method
    @Override
    public String getServletInfo(a) {
        return null;
    }

    // Destruction method
    @Override
    public void destroy(a) {}}Copy the code

You’ve written the simplest Servlet code, but how can you access it in a browser?

<servlet>
        <! -- Give the Servlet a name, usually the same as the class name -->
        <servlet-name>ServletDemo1</servlet-name>
        <! -- Class name -->
        <servlet-class>cn.ideal.web.servlet.ServeltDemo1</servlet-class>
    </servlet>

    <! -- Configure the mapping path -->
    <servlet-mapping>
        <servlet-name>ServletDemo1</servlet-name>
        <! -- External access path -->
        <url-pattern>/Demo1</url-pattern>
    </servlet-mapping>
Copy the code

Now we access it according to the path we configured in the URl-pattern, and it prints out in the console, ideally, more than this string

(2) The role of web.xml

The purpose of configuring servlets in web.xml is to tie the access path in the browser to the corresponding servlets. In the example above, the access path is: “/ not” and “cn. Ideal. Web. Servlet. ServeltDemo1” binding together

: specifies ServletDemo1. The name of the servlet is ServletDemo1, which is usually the same as the corresponding class

2,

: set the specific access path

And the two pass again<servlet-name></servlet-name>Tie together

Implementation process:

1. When the server receives the request from the browser, it parses the URL path to obtain the resource path of the Servlet

2, find web.xml file, find

tag, find the corresponding full class name

Tomcat loads the bytecode file into memory, creates the object, and calls the methods in it

So we need to know that most of the methods in the Servlet are not created and invoked by us, but by Tomcat

(3) Servlet interface

(1) Brief overview of the life cycle

I will simply understand the life cycle as these processes:

Live — born — serve — die — buried

** The first time Tomcat accesses a Servlet, Tomcat creates an instance of the Servlet

**Tomcat will call init() to initialize the object

3. Service: When a client accesses a Servlet, the service() method is called

4. Death: The destroy() method is called when Tomcat is closed or the Servlet has not been used for a long time

5. After the bury: destroy() method is called, the Servlet waits for garbage collection (not easy) and is reinitialized with the init() method if necessary

(2) Detailed explanation of the life cycle

1, before

The server creates the Servlet when it is first accessed, or when the server is started. If the servlets are created when the server starts, you also need to configure them in the web.xml file, which means that by default the servlets are created by the server the first time they are accessed

For a Servlet type, the server creates only one instance object: For the first time we visit < http://localhost:8080/Demo1 >, for example, the server through/not found the cn. Ideal. Web. Servlet. ServeltDemo1, server will determine the type of the servlet ever created, If no instance of ServletDmoe1 is created by reflection, otherwise an existing instance is used

2, birth

The server calls the Servlet’s void Init (ServletConfig) method immediately after the Servlet is created, and this method is only called once during the lifetime of a Servlet. We can put some of the initialization work into the Servlet method!

3, service,

Each time the server receives a request, it calls the Servlet’s service() method to process the request. The service() method is called multiple times. The server calls the service() method every time it receives a request, which is why we need to write the code to handle the request to the service() method!

4. Death and burial

The Servlet also needs to be destroyed when the server is shut down, but before doing so, the server calls the destroy() method in the Servlet, where we can put some code to free up resources

(3) Three types of Servlet interfaces

Of these five methods, we can see three types in the parameters that we haven’t touched yet

public void init(ServletConfig servletConfig) throws ServletException {}

public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {}
Copy the code

These are the three types: ServletConfig, ServletRequest, ServletResponse

A: ServletConfig

The ServletConfig is an object created by the server and passed to the init() method of the Servlet

We’ll simply use the first getServletName() in the following method, which will be better understood once we learn to write contexts and other things

// Get the configuration name of the Servlet in the web.xml file, which is the name specified by 
      
String getServletName(a)

// To get the ServletContext object
ServletContext getServletContext(a)

// To get the initialization parameter configured in web. XML, the parameter value is obtained by the parameter name;
String getInitParameter(String name)

// To get the names of all initialization parameters configured in web.xml
Enumeration getInitParameterNames(a)
Copy the code

B: ServletRequest & ServletResponse

The two types appear in the Servlet’s service() method and represent request and response objects, respectively, and instances of both are created by the server

But we want to make a Web application, which is essentially tied to HTTP, and if we want to use http-related functionality in the service() method, ServletRequest and ServletResponse can be strongly converted to HttpServletRequest and HttpServletResponse

It means:

// Get the value of the specified request parameter;
String getParameter(String paramName)

// GET the request method, such as GET or POST
String getMethod(a)
    
// Get the value of the specified request header;
String getHeader(String name)

// Set the encoding of the request body!
/* GET does not have a request body, so this method is only valid for POST requests. This method must be called before getParameter() is called! Use request. SetCharacterEncoding (" utf-8 "), then through the getParameter () method to obtain parameters, parameter values are passed the transcoding, which transformed into utf-8 * /
void setCharacterEncoding(String encoding)
Copy the code

HttpServletResponse method:

// Get a character response stream that can be used to output response information to the client.
PrintWriter getWriter(a)Eg: the response.getWriter(a).print(" < h1 > JustforThe test < / h1 > ");// Get the byte response stream. For example, you can respond to a picture to the client
ServletOutputStream getOutputStream(a)

// Used to set the encoding of the character response stream
void setCharacterEncoding(String encoding)
   
// Add the response header to the client
void setHeader(String name, String value)Eg:setHeader(" Refresh ","3; url=http://www.xxx.com ").The url is automatically refreshed after three seconds// This method is a simple way to setHeader(" content-type ", "XXX"), which is used to add a method named content-type response header
/* Content-type The response header sets the MIME type of the response data. For example, setContentType(" image/jepg ") is used to respond to the client with a JPG image. If the response data is a text type, then set the code as well. For example setContentType (" text/HTML. Chartset = UTF-8 ") indicates that the response data type is HTML, and the setCharacterEncoding(" UTF-8 ") method is called. * /
void setContentType(String contentType)
    
// Send the status code and error message to the client
void sendError(int code, String errorMsg)
Copy the code

GenericServlet class

A: By looking at the source code for this class, you can see that there is only

public abstract void service(ServletRequest var1, ServletResponse var2) throws ServletException, IOException;
Copy the code

One method needs to be implemented; the others are already defined in the source code

B: Init () method of GenericServlet

Two other methods that need to be mentioned

public void init(ServletConfig config) throws ServletException {
        this.config = config;
        this.init();
    }

public void init(a) throws ServletException {}Copy the code

The GenericServlet class implements the Servlet init(ServletConfig) method, assigns the parameter config to the class member config, and then calls the class’s own init() method with no parameters

This method is GenericServlet’s own method, not inherited from Servlet. When we customize a Servlet, we should override init() if we want to complete initialization. Because the Init (ServletConfig) method in GenericServlet holds the ServletConfig object, if you overwrite the code that holds the ServletConfig, you will not be able to use ServletConfig anymore

C: Implements the ServletConfig interface

GenericServlet also implements the ServletConfig interface, so ServletConfig methods such as getInitParameter() and getServletContext() can be called directly.

But this class is still not our focus, so let’s move on to the next class

(5) HttpServlet class

(1) overview

In the Servlet interface, we need to implement 5 methods, very troublesome, and HttpServlet class has implemented all the methods of the Servlet interface, write Servlet, just need to inherit HttpServlet, override the method you need. And it provides special support for HTTP requests, which makes it even more powerful

(2) the service () method

In the HttpServlet service (ServletRequest, ServletResponse) method will reduce the ServletRequest and ServletResponse into it and HttpServletResponse

//HttpServlet source excerpt
public void service(ServletRequest req, ServletResponse res) throws ServletException, IOException {
        HttpServletRequest request;
        HttpServletResponse response;
        try {
            request = (HttpServletRequest)req;
            response = (HttpServletResponse)res;
        } catch (ClassCastException var6) {
            throw new ServletException("non-HTTP request or response");
        }

        this.service(request, response);
    }
Copy the code

Strong after the turn, and then call the HttpServlet class provided by the service (it, HttpServletResponse) method, this is the way to the class itself, rather than inherited, it shows that we are at the time of use, Only need to cover the service (it, HttpServletResponse) is ok, don’t need to turn the two objects better

Note: there are further simplify the steps, also don’t have to use the service (HttpServletResponse) it,

(3) the doGet () and doPost ()

In the HttpServlet service (it, HttpServletResponse) method to judge the request is a GET or POST, if is a GET request, go to call in the class doGet () method, if it is a POST request, We call the doPost() method, which means we override the doGet() or doPost() methods in the subclass

(6) Servlet details

(1) Thread safety issues

A Servlet can only be created as an instance object by the server. In many cases, a Servlet needs to handle multiple requests. Obviously, servlets, while efficient, are not thread-safe

Therefore, we should not easily create a member variable in the Servlet, because there may be multiple threads doing different operations on the member variable at the same time

Conclusion: Do not create members in servlets! Instead of creating local variables, you can create stateless members, or members whose state is only readable

(2) Servlets are created when the server starts

As we mentioned earlier in the life cycle, servlets are created by the server the first time they are accessed, but we can configure servlets in web.xml to create servlets when the server starts

<servlet>
	<servlet-name>ServletDemo1</servlet-name>
	<servlet-class>cn.ideal.web.ServletDemo1</servlet-class>
     <! -- Configure <load-on-startup> in <servlet> to give a non-negative integer! -->
	<load-on-startup>0</load-on-startup>
</servlet>
Copy the code

Its purpose is to determine the order in which servlets are created at server startup

(3) A Servlet can be bound to multiple urls

<servlet-mapping>
	<servlet-name>Servlet</servlet-name>
	<url-pattern>/AServlet</url-pattern>
	<url-pattern>/BServlet</url-pattern>
</servlet-mapping>  
Copy the code

When configured this way, both /AServlet and /BServlet accesses the AServlet

(4) Wildcard matching problem

A wildcard, “*”, can be used in

, which matches any prefix or suffix

<! -- path matching -->
<url-pattern>/servlet/*<url-patter>: /servlet/a and /servlet/b match /servlet/*;<! -- Extension match -->
<url-pattern>*.xx</url-pattern>: / ABC /de.xx, /a.xx, both match *.xx;<! -- Match everything -->
<url-pattern>/ *<url-pattern>: matches all urls.Copy the code

Wildcards are either prefixes or suffixes and cannot appear in the middle of a URL. In addition, a URL can contain only one wildcard. If a specific address exists, the address is preferentially accessed

(7) the ServletContext

(1) overview

The server creates a ServletContext object for each Web application, so to speak, representing the Web site, and this object is created when Tomcat is started and destroyed when Tomcat is shut down

(2) function

All servlets share a ServletContext object, so the purpose of the ServletContext object is to share data between the dynamic resources of the entire Web application, that is, different servlets can communicate with each other through ServletContext, thus sharing data

(3) Get the ServletContext object

The GenericServlet class has a getServletContext() method, so you can get it directly using this.getServletContext()

public class MyServlet implements Servlet {
	public void init(ServletConfig config) { ServletContext context = config.getServletContext(); }}Copy the code
public class MyServlet extends HttpServlet {
	public void doGet(HttpServletRequest request, HttpServletResponse response) {
    	ServletContext context = this.getServletContext(); }}Copy the code

(4) Functions of domain objects

All domain objects have the ability to access data, and you can think of this as a Map way of storing data

Let’s look at a few common ways to manipulate data

storage

// Used to store an object, also known as storing a domain property
void setAttribute(String name, Object value)Eg: the servletContext.setAttribute(" XXX ", "XXX")
// A domain attribute is saved in the ServletContext. The domain attribute name is XXX and the domain attribute value is XXX
Copy the code

To obtain

// To get the data in the ServletContext
Object getAttribute(String name)
// Get the domain property named xxEg: the String value= (String) servletContext. GetAttribute (" XXX ");// Get the names of all domain attributes;
Enumeration getAttributeNames(a)
Copy the code

remove

// Remove domain properties from ServletContext
void removeAttribute(String name)
Copy the code

A small case of traffic statistics

package cn.ideal.web.servlet;

import javax.servlet.*;
import java.io.IOException;

public class ServletDemo2 extends GenericServlet {
    @Override
    public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {
        // Get the ServletContext object
        ServletContext servletContext = this.getServletContext();
        // Get the count attribute in the ServletContext object
        Integer count = (Integer) servletContext.getAttribute("count");
        if (count == null) {
            // If the count attribute does not exist in the ServletContext, set name to count with a value of 1 to indicate the first access
            count = 1;
        } else {
            // If there is a count attribute in the Servlet, which indicates that it was previously accessed, name increments the count by one
            count++;
        }
        servletResponse.setContentType("text/html; charset=UTF-8");
        // Return the number of times the page was accessed to the client
        servletResponse.getWriter().print("

This page is visited"

+ count + "< / h1 >"); // Save the count value into the ServletContext object servletContext.setAttribute("count", count); }}Copy the code

(8) Methods for obtaining resources

(1) Obtain path

The ServletContext object can be used to obtain resources in a Web application. For example, in the root directory of a Web application, create a file called aaa. TXT, and in the web-INF directory, create a file called bbB. TXT

// Obtain the path of aaa.txtString realPath = servletContext. GetRealPath ("/aaa. TXT ")// Obtain the path of bbb.txt String realPath = servletContext. GetRealPath ("/WEB - INF/b.t xt ")Copy the code

In addition to obtaining a single file path, there is another way to obtain all resource paths in a specified directory, such as obtaining all resource paths under /WEB-INF

Set set = context.getResourcePaths("/WEB-INF");
System.out.println(set);
Copy the code

(2) Obtain resource flows

Not only can we use ServletContext to get the path, we can also get the resource flow, using the two files assumed above as an example

/ / to get aaa. TXTInputStream in = servletContext. GetResourceAsStream ("/aaa. TXT ");/ / for BBB. TXTInputStream in = servletContext. GetResourceAsStream ("/WEB - INF/b.t xt ");Copy the code

(3) Obtain resources in the classpath

InputStream in = this.getClass().getClassLoader().getResourceAsStream("xxx.txt");
System.out.println(IOUtils.toString(in));
Copy the code

(9) Use annotations and no longer configure web.xml

Every time we create a Servlet we need to configure it in web.xml, but if we have a Servlet version older than 3.0, we can choose not to create web.xml and use annotations instead, which is very simple and convenient

For example, let’s create a Servlet and configure web.xml as follows

<servlet>
    <servlet-name>ServletDemo2</servlet-name>
    <servlet-class>cn.ideal.web.servlet.ServletDemo2</servlet-class>
</servlet>
<servlet-mapping>
    <servlet-name>ServletDemo2</servlet-name>
    <url-pattern>/Demo2</url-pattern>
</servlet-mapping>
Copy the code
// Write the code above the class name, with the external access path inside the quotes
@WebServlet("/Demo2")
Copy the code

Is it simple and convenient? Let’s see how it works:

//WebServlet source excerpt
@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface WebServlet {
    String name(a) default "";

    String[] value() default {};

    String[] urlPatterns() default {};

    int loadOnStartup(a) default- 1;
Copy the code

@target ({elementType.type}) is scoped for classes, and @retention (retentionPolicy.runtime) is kept at RUNTIME. The name() method is less important here, because in web.xml, String[] urlPatterns() default {}; String[] urlPatterns() default {}; UrlPatterns = “/Demo2” and the most important value in the pattern is the address, so we can write value = “/Demo2” and omit the value. So I can write it as /Demo2.

The end:

If there is any shortage in the content, or the wrong place, welcome everyone to give me comments, crab crab everybody! ^_^

If it can help you, then pay attention to me! (The series of articles will be updated on the official account as soon as possible)

Here we do not know each other, but in order to their dreams and efforts

A adhere to push the original Java technology of the public number: the ideal more than twenty days