web框架的前生今世--從servlet到spring mvc到spring boot

 

背景
上世紀90年代,隨着Internet和瀏覽器的飛速發展,基於瀏覽器的B/S模式隨之火爆發展起來。最初,用戶使用瀏覽器向WEB服務器發送的請求都是請求靜態的資源,好比html、css等。  可是能夠想象:根據用戶請求的不一樣動態的處理並返回資源是理所固然必須的要求。   css

servlet的定義

  • Servlet is a technology which is used to create a web application. servlet是一項用來建立web application的技術。
  • Servlet is an API that provides many interfaces and classes including documentation. servlet是一個提供不少接口和類api及其相關文檔。
  • Servlet is an interface that must be implemented for creating any Servlet.servlet是一個接口,建立任何servlet都要實現的接口。
  • Servlet is a class that extends the capabilities of the servers and responds to the incoming requests. It can respond to any requests. servlet是一個實現了服務器各類能力的類,對請求作出響應。它能夠對任何請求作出響應。
  • Servlet is a web component that is deployed on the server to create a dynamic web page.servlet是一個web組件,部署到一個web server上(如tomcat,jetty),用來產生一個動態web頁面。

servlet的歷史

版本 日期 JAVA EE/JDK版本 特性
Servlet 4.0 2017年10月 JavaEE 8 HTTP2 [1] 
Servlet 3.1 2013年5月 JavaEE 7 Non-blocking I/O, HTTP protocol upgrade mechanism
Servlet 3.0 2009年12月 JavaEE 6, JavaSE 6 Pluggability, Ease of development, Async Servlet, Security, File Uploading
Servlet 2.5 2005年10月 JavaEE 5, JavaSE 5 Requires JavaSE 5, supports annotation
Servlet 2.4 2003年11月 J2EE 1.4, J2SE 1.3 web.xml uses XML Schema
Servlet 2.3 2001年8月 J2EE 1.3, J2SE 1.2 Addition of Filter
Servlet 2.2 1999年8月 J2EE 1.2, J2SE 1.2 Becomes part of J2EE, introduced independent web applications in .war files
Servlet 2.1 1998年11月 未指定 First official specification, added RequestDispatcher, ServletContext
Servlet 2.0   JDK 1.1 Part of Java Servlet Development Kit 2.0
Servlet 1.0 1997年6月    

 

 

web Container

web容器也叫servlet容器,負責servlet的生命週期,映射url請求到相應的servlet。html

A web container (also known as a servlet container;[1] and compare "webcontainer"[2]) is the component of a web server that interacts with Java servlets. A web container is responsible for managing the lifecycle of servlets, mapping a URL to a particular servlet and ensuring that the URL requester has the correct access-rights.

A web container handles requests to servlets, JavaServer Pages (JSP) files, and other types of files that include server-side code. The Web container creates servlet instances, loads and unloads servlets, creates and manages request and response objects, and performs other servlet-management tasks.

A web container implements the web component contract of the Java EE architecture. This architecture specifies a runtime environment for additional web components, including security, concurrency, lifecycle management, transaction, deployment, and other services.

常見的web容器以下:java

在web容器中,web應用服務器的結構以下:web

 

1.普通servlet實現頁面訪問spring

 

1.1 實例1:使用web.xml實現一個http服務編程

實現一個簡單的servletapi

package com.howtodoinjava.servlets;
 
import java.io.IOException;
import java.io.PrintWriter;
 
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
 
public class MyFirstServlet extends HttpServlet {
 
    private static final long serialVersionUID = -1915463532411657451L;
 
    @Override
    protected void doGet(HttpServletRequest request,
            HttpServletResponse response) throws ServletException, IOException
    {
        response.setContentType("text/html;charset=UTF-8");
        PrintWriter out = response.getWriter();
        try {
            // Write some content
            out.println("<html>");
            out.println("<head>");
            out.println("<title>MyFirstServlet</title>");
            out.println("</head>");
            out.println("<body>");
            out.println("<h2>Servlet MyFirstServlet at " + request.getContextPath() + "</h2>");
            out.println("</body>");
            out.println("</html>");
        } finally {
            out.close();
        }
    }
     
    @Override
    protected void doPost(HttpServletRequest request,
            HttpServletResponse response) throws ServletException, IOException {
        //Do some other work
    }
 
    @Override
    public String getServletInfo() {
        return "MyFirstServlet";
    }
}

web.xml配置servlet瀏覽器

<?xml version="1.0"?>
<web-app     xmlns="http://xmlns.jcp.org/xml/ns/javaee"
            xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
            xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee
            http://xmlns.jcp.org/xml/ns/javaee/web-app_3_0.xsd"
            version="3.0">
             
    <welcome-file-list>
        <welcome-file>/MyFirstServlet</welcome-file>
    </welcome-file-list>
     
    <servlet>
        <servlet-name>MyFirstServlet</servlet-name>
        <servlet-class>com.howtodoinjava.servlets.MyFirstServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>MyFirstServlet</servlet-name>
        <url-pattern>/MyFirstServlet</url-pattern>
    </servlet-mapping>
     
</web-app>

 1.2 編程方式實現一個http服務請求spring-mvc

 不須要xmltomcat

package com.journaldev.first;

import java.io.IOException;
import java.io.PrintWriter;
import java.util.Date;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebInitParam;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class FirstServlet
 */
@WebServlet(description = "My First Servlet", urlPatterns = { "/FirstServlet" , "/FirstServlet.do"}, initParams = {@WebInitParam(name="id",value="1"),@WebInitParam(name="name",value="pankaj")})
public class FirstServlet extends HttpServlet {
    private static final long serialVersionUID = 1L;
    public static final String HTML_START="<html><body>";
    public static final String HTML_END="</body></html>";
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public FirstServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

    /**
     * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
     */
    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        PrintWriter out = response.getWriter();
        Date date = new Date();
        out.println(HTML_START + "<h2>Hi There!</h2><br/><h3>Date="+date +"</h3>"+HTML_END);
    }

    /**
     * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
     */
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        // TODO Auto-generated method stub
    }

}

 

 2.spring mvc實現頁面訪問

2.1 web.xml方式

示例:

<web-app xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee 
    http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
    version="2.5">

    <display-name>Gradle + Spring MVC Hello World + XML</display-name>
    <description>Spring MVC web application</description>

    <!-- For web context -->
    <servlet>
        <servlet-name>hello-dispatcher</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <init-param>
            <param-name>contextConfigLocation</param-name>
            <param-value>/WEB-INF/spring-mvc-config.xml</param-value>
        </init-param>
        <load-on-startup>1</load-on-startup>
    </servlet>

    <servlet-mapping>
        <servlet-name>hello-dispatcher</servlet-name>
        <url-pattern>/</url-pattern>
    </servlet-mapping>

    <!-- For root context -->
    <listener>
        <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
    </listener>

    <context-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>/WEB-INF/spring-core-config.xml</param-value>
    </context-param>

</web-app>

 2.2 編碼方式

public class MyWebAppInitializer implements WebApplicationInitializer {
 
     @Override
     public void onStartup(ServletContext container) {
       // Create the 'root' Spring application context
       AnnotationConfigWebApplicationContext rootContext =
         new AnnotationConfigWebApplicationContext();
       rootContext.register(AppConfig.class);
 
       // Manage the lifecycle of the root application context
       container.addListener(new ContextLoaderListener(rootContext));
 
       // Create the dispatcher servlet's Spring application context
       AnnotationConfigWebApplicationContext dispatcherContext =
         new AnnotationConfigWebApplicationContext();
       dispatcherContext.register(DispatcherConfig.class);
 
       // Register and map the dispatcher servlet
       ServletRegistration.Dynamic dispatcher =
         container.addServlet("dispatcher", new DispatcherServlet(dispatcherContext));
       dispatcher.setLoadOnStartup(1);
       dispatcher.addMapping("/");
     }
 
  }

內部實現

 

3.spring boot

  繼承了spring mvc的框架,實現SpringBootServletInitializer

package com.mkyong;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.boot.web.support.SpringBootServletInitializer;

@SpringBootApplication
public class SpringBootWebApplication extends SpringBootServletInitializer {

    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        return application.sources(SpringBootWebApplication.class);
    }

    public static void main(String[] args) throws Exception {
        SpringApplication.run(SpringBootWebApplication.class, args);
    }

}

而後controller

package com.mkyong;

import java.util.Map;

import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;

@Controller
public class WelcomeController {

    // inject via application.properties
    @Value("${welcome.message:test}")
    private String message = "Hello World";

    @RequestMapping("/")
    public String welcome(Map<String, Object> model) {
        model.put("message", this.message);
        return "welcome";
    }

}

總結:

1.servlet的本質沒有變化,從web框架的發展來看,web框架只是簡化了開發servlet的工做,但仍是遵循servlet規範的發展而發展的。

2.servlet的歷史發展,從配置方式向編程方式到自動配置方式發展

3.spring mvc框架的分組:root和child(能夠有多個dispatcherservlet),多個child能夠共享root,child直接不共享

參考文獻:

【1】https://en.wikipedia.org/wiki/Web_container

【2】https://baike.baidu.com/item/servlet/477555?fr=aladdin

【3】https://www.javatpoint.com/servlet-tutorial

【4】https://www.journaldev.com/1854/java-web-application-tutorial-for-beginners#deployment-descriptor

【5】https://blog.csdn.net/qq_22075041/article/details/78692780

【6】http://www.mkyong.com/spring-mvc/gradle-spring-mvc-web-project-example/

【7】http://www.mkyong.com/spring-boot/spring-boot-hello-world-example-jsp/

相關文章
相關標籤/搜索