当前位置: 首页 > news >正文

SpringBoot的Web开发

目录

一、静态资源映射规则

二、enjoy模板引擎

三、springMVC

1、springMVC的概念理解

2、springMVC的工作流程

3、请求处理

4、springMVC的参数绑定

(1)绑定的机制

(2)支持的数据类型

(3)使用要求

(4)示例代码

5、springMVC常用注解

(1)@RequestParam

(2)@RequestBody

(3)@PathVaribale

(4)@RequestHeader

(5)@CookieValue

6、springMVC的数据传递

7、Spring的文件上传

四、注册Servlet三大组件 Servlet/Filter/Listener

五、切换为其他嵌入式Servlet容器

1、SpringBoot 默认针对Servlet容器提供以下支持


一、静态资源映射规则

        只要静态资源放在类路径下: called /static (or /public or /resources or /METAINF/resources。

        访问:当前项目根路径/ + 静态资源名。

二、enjoy模板引擎

        Spring Boot 的 enjoy 模板引擎是由 JFinal 提供的。JFinal 是一个轻量级的 Java Web 框架,而 Enjoy 是 JFinal 自带的模板引擎。Enjoy 模板引擎具有速度快、语法简洁、功能丰富等特点,适用于生成 HTML、XML、JSON 等各种文本内容。

        首先是导入依赖:

        <dependency><groupId>com.jfinal</groupId><artifactId>enjoy</artifactId><version>5.0.3</version></dependency>

        然后是创建一个配置类EnjoyConfig,用于配置 JFinal Enjoy 模板引擎与 Spring Boot 的集成。它定义了一个 JFinalViewResolver Bean,使得 Enjoy 模板引擎可以作为 Spring Boot 的视图解析器来使用,从而将模板文件渲染成 HTML 响应。

@Configuration
public class EnjoyConfig {@Bean(name = "jfinalViewResolver")public JFinalViewResolver getJFinalViewResolver() {// 创建用于整合 spring boot 的 ViewResolver 扩展对象JFinalViewResolver jfr = new JFinalViewResolver();// 对 spring boot 进行配置jfr.setSuffix(".html");  // 设置模板文件的后缀jfr.setContentType("text/html;charset=UTF-8");  // 设置响应的内容类型和字符编码jfr.setOrder(0);  // 设置视图解析器的优先级,值越小优先级越高// 设置在模板中可通过 #(session.value) 访问 session 中的数据jfr.setSessionInView(true);// 获取 engine 对象,对 enjoy 模板引擎进行配置Engine engine  = JFinalViewResolver.engine;// 热加载配置,启用开发模式,可以在不重启应用的情况下自动加载模板文件的修改engine.setDevMode(true);// 使用 ClassPathSourceFactory 从 class path 和 jar 包中加载模板文件engine.setToClassPathSourceFactory();// 设置模板文件的基础路径,这里设置为 resources 目录下的 templates 文件夹engine.setBaseTemplatePath("/templates/");// 更多的配置可以在这里添加,例如自定义指令、共享方法等// engine.addDirective(...);// engine.addSharedMethod(...);return jfr;}
}

        其中@Configuration表明这是一个配置类,Spring 会自动扫描并加载该类中的配置

        JFinalViewResolver:这是 JFinal 框架提供的一个视图解析器,用于将控制器返回的视图名解析为实际的模板文件,并进行渲染。

        setSuffix:是设置模板后缀,以什么结尾。

        setConentType:是设置响应的内容类型为 text/html,并使用 UTF-8 编码。

        setOrder:是设置这个ViewResolver 的优先级为0,表示它的优先级最高。

        setSessionInView(true):是将允许在模板中直接访问 session 中的数据。例如,可以通过 #(session.value) 语法访问 session 中的 value。

        setDevMode(true):开启开发模式,这样可以在修改模板文件后立即生效,而不需要重启服务器。这对于开发阶段非常有用。

        setBaseTemplatePath("/templates/"):设置模板文件的基础路径为 /templates/。在这种情况下,模板文件应该存放在 resources/templates/ 目录下。

        比如在控制器层中方法返回值:

        @RequestMapping(value="/init")//二级目录public String userInit(){System.out.println("==========进入了springMVC的控制器=========");System.out.println("调用业务层,调用持久层");return "success";//返回方法执行完要跳转的页面名称}

        这段代码因为没有@?所以这段代码的return将返回的 success 视图名加上 .html 后缀,并且在 engine.setBaseTemplatePath("/templates/") 指定的模板路径下查找。                        会在src/main/resources/templates/ 目录下,那么 Spring MVC 会寻找            src/main/resources/templates/success.html 这个文件并渲染它。

三、springMVC

1、springMVC的概念理解

        Spring MVC 是一个基于 MVC 模式的 Java Web 框架,属于 Spring 框架的一部分。它将应用程序分为三层:模型(处理数据和业务逻辑)、视图(展示数据)、控制器(处理用户请求并协调模型和视图)。用户请求由 DispatcherServlet 接收并分发到合适的控制器,控制器处理后返回视图名称,最终生成 HTML 页面返回给用户。

2、springMVC的工作流程
  • 用户请求:用户通过浏览器发起一个 HTTP 请求。
  • 请求处理:请求首先到达 Spring 的 DispatcherServlet(前端控制器),它是整个 Spring MVC 的核心组件,负责协调整个请求处理流程。
  • 处理器映射:DispatcherServlet 通过处理器映射(Handler Mapping)找到对应的控制器(Controller)。
  • 调用控制器:DispatcherServlet 调用找到的控制器中的对应方法。
  • 业务逻辑处理:控制器调用业务层(Service)和数据访问层(DAO)进行数据处理。
  • 返回视图名称:控制器处理完业务逻辑后,返回一个视图名称(或视图对象)。
  • 视图解析:DispatcherServlet 通过视图解析器(ViewResolver)找到对应的视图模板。
  • 渲染视图:视图解析器将视图和模型数据结合,生成最终的 HTML 响应。
  • 返回响应:最终的 HTML 响应通过 DispatcherServlet 返回给用户的浏览器。
3、请求处理

        方式一:

        关键词@RequestMapping。

        意义:处理用户的请求,相似于doget与dopost。

        位置:类上、一级目录。

        方法:二级目录。

        例如:user/save、user/delete、student/save、student/delete。

        属性:value = "",path = ""。

        表示请求路径。

        示例代码

        @RequestMapping(value="/init")//二级目录public String userInit(){System.out.println("==========进入了springMVC的控制器=========");System.out.println("调用业务层,调用持久层");return "success";//返回方法执行完要跳转的页面名称}

         就是当用户访问localhost:8080/init是这个方法就会被调用,并且执行完跳转到/templates/success页面中,value代表二级目录。

        方式二:

        在原有的基础上加上method属性,method=常量,此请求的类型(get,post),若不设置则此请求适配所有的请求方式 。

        示例代码

        @RequestMapping(value="/show1",method ={RequestMethod.POST})public String show1(){System.out.println("==========进入了springMVC的控制器=========");System.out.println("使用post方式发送请求进入");return "success";//返回方法执行完要跳转的页面名称}

        这里这个method={RequestMethod.POST}:限定这个方法只处理HTTP POST请求

        方式三:

        在原有的基础上加params属性,params = "",限制请求参数,例如:params={"msg1","msg2"}表示请求路径中必须携带参数名为msg1与msg2的参数。

        示例代码

        @RequestMapping(value="/show2",params = {"msg1=aa","msg2=bb"})public String show2(){System.out.println("==========进入了springMVC的控制器=========");System.out.println("限制请求携带的参数");return "success";//返回方法执行完要跳转的页面名称}

        只有在请求中包含特定参数msg1=aa和msg2=bb时,这个方法才会被执行。一个字都不能少。

        然后是使用postman测试,超链接默认发送的是get请求 ,所有请求所携带的参数格式均为:key = value。

        其中包含了:@DeleteMapping 删除、@PutMapping 修改、@GetMapping 查询 @PostMapping 新增

        @GetMapping(这个方法会响应GET请求。当客户端发送GET /show3请求时,该方法将被调用)

        @GetMapping("/show3")public String show3(){System.out.println("==========进入了springMVC的控制器=========");System.out.println("必须使用get方式请求");return "success";//返回方法执行完要跳转的页面名称}

        @DeleteMapping(这个方法会响应DELETE请求。当客户端发送DELETE /show5请求时,该方法将被调用)

        @DeleteMapping("/show5")public String show5(){System.out.println("==========进入了springMVC的控制器=========");System.out.println("必须使用delete方式请求");return "success";//返回方法执行完要跳转的页面名称}

        @PutMapping(这个方法会响应PUT请求。当客户端发送PUT /show6请求时,该方法将被调用)

        @PostMapping(这个方法会响应POST请求。当客户端发送POST /show4请求时,该方法将被调用)

        @RequestMapping可以点击查看源码

        @Target({ElementType.METHOD, ElementType.TYPE}),@Target注解用于指定自定义注解可以应用的程序元素类型,METHOD==代表修饰方法,TYPE==代表修饰类。

4、springMVC的参数绑定
(1)绑定的机制

        SpringMVC 绑定请求参数的过程是通过把表单提交请求参数,作为控制器中方法参数进行绑定的。

(2)支持的数据类型

        基本类型参数:包括基本类型和 String 类型。

        POJO类型参数:包括实体类,以及关联的实体类。

        数组和集合类型参数:包括 List 结构和 Map 结构的集合(包括数组)。

        使用 ServletAPI 对象作为方法参数:HttpServletRequest、HttpServletResponse、HttpSession、java.security.Principal、Locale、InputStream、OutputStream、Reader、Writer。

(3)使用要求
  • 发送请求中携带数据的key与方法参数的name必须一致
  • 数据类型合法
(4)示例代码

        首先是创建出两个templates包下的两个html页面,一个one页面,负责完成用户完成功能二点操作界面,一个是success,用户操作成功的界面。

        最开始是进入选择页面:

    @RequestMapping("/show")public String show(){return "one";}

        one页面形式为:

        基本类型和String类型作为参数:

    @RequestMapping("/show2")public String show2(String msg1,int msg2){System.out.println("=====接受到用户发送数据为:"+msg1+"=======");System.out.println("=====接受到用户发送数据为:"+msg2+"=======");return "success";}

        对应one.html界面的a标签为:

<a href="/one/show2?msg1=jdk&msg2=9527">发送请求2</a>

        POJO 类型作为参数(对象嵌套 emp实体类里封装了dept对象):

    @RequestMapping("/show4")public String show4(Emp emp){System.out.println("=====接受到用户发送数据为:"+emp+"=======");return "success";}

        对应one.html界面的a标签为:

    <form action="/one/show4" method="post">员工编号:<input type="text" name="eid" ><br/>员工姓名:<input type="text" name="ename" ><br/>员工性别:<input type="text" name="esex" ><br/>部门编号:<input type="text" name="dept.did" ><br/>部门名称:<input type="text" name="dept.dname" ><br/><input type="submit" value="发送请求4"/></form>

        如果只想要几个属性又不想封装实体类方法,则可以用map来解决:

    @RequestMapping("/map")public String map(@RequestParam Map map){System.out.println(map);return "success";}

        其中的@RequestParam注解用于将HTTP请求的参数绑定到处理方法的参数上。

        对应one.html界面的a标签为:

    <form action="/one/map" method="post">员工编号:<input type="text" name="eids"><br/>员工姓名:<input type="text" name="enames"><br/>员工性别:<input type="text" name="esexs"><br/><input type="submit" value="发送请求4(map)"/></form>

        POJO 类中包含集合类型参数:

        首先是通过逐一绑定来实现:

    @RequestMapping("/show5")public String show5(Dep dep){System.out.println("=====接受到用户发送数据为:"+dep+"=======");return "success";}

        对应one.html界面的a标签为:

    <form action="/one/show5" method="post">部门编号:<input type="text" name="did" ><br/>部门名称:<input type="text" name="dname" ><br/>员工编号1:<input type="text" name="mylist[0].eid" ><br/>员工姓名1:<input type="text" name="mylist[0].ename" ><br/>员工性别1:<input type="text" name="mylist[0].esex" ><br/>员工编号2:<input type="text" name="mylist[1].eid" ><br/>员工姓名2:<input type="text" name="mylist[1].ename" ><br/>员工性别2:<input type="text" name="mylist[1].esex" ><br/>员工编号3:<input type="text" name="myMap['one'].eid" ><br/>员工姓名3:<input type="text" name="myMap['one'].ename" ><br/>员工性别3:<input type="text" name="myMap['one'].esex" ><br/>员工编号4:<input type="text" name="myMap['two'].eid" ><br/>员工姓名4:<input type="text" name="myMap['two'].ename" ><br/>员工性别4:<input type="text" name="myMap['two'].esex" ><br/><input type="submit" value="发送请求5"/></form>

        其次是用数组来接收:

    @RequestMapping("/show6")public String show8(int[] nums){System.out.println("=====接受到用户发送数据为:"+ Arrays.toString(nums) +"=======");return "success";}

        对应one.html界面的a标签为:

<a href="/one/show6?nums=123&nums=456&nums=789">发送请求6</a>

        

        最后是使用 ServletAPI 对象作为方法参数:

    @RequestMapping("/show7")public String show7(HttpServletRequest request, HttpServletResponse response){System.out.println(request);System.out.println(response);request.getParameter("msg1");HttpSession session =     request.getSession();System.out.println(session);session.setAttribute("","");try {response.sendRedirect("重定向");} catch (IOException e) {e.printStackTrace();}ServletContext applaction =  session.getServletContext();return "success";}

        对应one.html界面的a标签为:

<a href="/one/show7">发送请求7</a>

5、springMVC常用注解
(1)@RequestParam

        作用:把请求中指定名称的参数给控制器中的形参赋值,如果页面标签名称和方法参数名称不一致,可以使用此注解实现。

        属性

  • name属性:设置参数名称
  • defaultValue属性:设置默认值
  • required属性:设置是否为必传

        示例代码: 

        /*** @RequestParam("名称必须与页面标签或者url地址key名称一致")* */@RequestMapping("/show1")public String show1(@RequestParam(name="msg1") String msg){System.out.println("=====接受到用户发送数据为:"+msg+"=======");return "success";}

        例如,如果请求是/show1?msg1=hello,那么msg将等于"hello"

        @RequestParam还有defaultValue属性:

    @RequestMapping("/show3")public String show4(@RequestParam(name = "uname",defaultValue = "暂无用户") String name){System.out.println("账号:"+name);return "success";}

        defaultValue = "暂无用户"指定了一个默认值。如果请求中没有提供uname参数,name将被赋值为"暂无用户"。

(2)@RequestBody

        作用:用于获取"请求体"内容。直接使用得到是 key=value&key=value...结构的数据,并可以转换为对象,前后端分离,@RequestBody可以将json转换为javaBean。

        属性:required:是否必须有请求体。默认值是:true。

        注意:前端不能使用GET方式提交数据,GET方式无请求体。

        示例代码:

    public String show4(@RequestBody Emp emp){System.out.println("=========="+emp+"==========");return "success";}

        就比如说用这段json代码来填充:

      {"eid":101,"ename":"詹姆斯邦德","esex":"绅士"}

        那么就会用把这段json代码中的数据按照键值对的方式来填充,存储在emp中。

(3)@PathVaribale

        作用:用于绑定 url 中的占位符。例如:请求 url 中 /delete/{id},这个{id}就是 url 占位符。url 支持占位符是 spring3.0 之后加入的。是 springmvc 支持 rest 风格 URL 的一个重要标志。

        属性

  • value:用于指定 url 中占位符名称。
  • required:是否必须提供占位符。

        示例代码:

    @PostMapping("/show5/{uname}/{pwd}")public String show5(@PathVariable("uname") String msg1, @PathVariable("pwd") String msg2){System.out.println(msg1);System.out.println(msg2);return "success";}
    @PostMapping("/show6/{uname}/{pwd}")public String show6(@PathVariable String uname, @PathVariable String pwd){System.out.println(uname);System.out.println(pwd);return "success";}

        上面这两种方式均可,都是可以直接实现路径变量的名称与方法参数的映射关系。

        Restful风格的请求是使用“url+请求方式”表示一次请求目的的,HTTP 协议里面四个表示操作方式的动词如下:

  • GET:用于获取资源
  • POST:用于新建资源
  • PUT:用于更新资源
  • DELETE:用于删除资源

        例如:

  • 新增 POST http://localhost:8080/user/用户名/用户密码/用户性别
  • 查询 GET http://localhost:8080/user/用户ID
  • 删除 delete http://localhost:8080/user/用户ID
  • 修改 put http://localhost:8080/user/用户ID/用户名/用户密码/用户性别

(4)@RequestHeader

        作用:用于获取请求消息头,获取头信息只获取头信息中的Accept-Language对应的数据(记得使用浏览器测试)。

        属性:value:提供消息头名称,required:是否必须有此消息头。

        示例代码

    @RequestMapping("/show1")public String show1(@RequestHeader(value="msg1") String msg){System.out.println(msg);return "success";}

        必须在请求头中包含一个名为 "msg1" 的字段,其值会传递给 msg 参数,也只会传递msg1参数。

(5)@CookieValue

        作用:用于把指定 cookie 名称的值传入控制器方法参数。

        属性

  • value:指定 cookie 的名称。
  • required:是否必须有此 cookie。

         示例代码:

    @RequestMapping("/show2")public String show2(@CookieValue(value = "JSESSIONID",required = false)String jsessionid){System.out.println(jsessionid);return "success";}

6、springMVC的数据传递
    @RequestMapping("/show")public String show(){return "index";}

        首先是先进入show界面:

        然后是充当试图的逻辑名称,默认页面跳转为请求转发方式:

    @RequestMapping("/show1")public String show1(){System.out.println("=========show1=========");return "success_String";}

        redirect关键词:

    @RequestMapping("/show2")public String show2(){System.out.println("=========show2=========");// 表示客户端会被重定向到 /show1 路径。也就是说,服务器会告诉浏览器发起一个新的请求到 /show1。这会导致浏览器的URL地址栏更新为 /show1。return "redirect:show1";}

        表示当前方法执行完毕后(show2),客户端会重定向到 /string/show1,浏览器会更新 URL 并发起新请求,再执行show1方法。

       

        forward关键词:

    @RequestMapping("/show3")public String show3(){System.out.println("=========show3=========");// 表示请求会被服务器内部转发到 /show1,而不会通知客户端(即浏览器)。这意味着浏览器的URL不会发生变化,仍然是 /show3,但服务器会处理 /show1 的逻辑。return "forward:show1";}

        表示当前方法执行完毕后,Spring MVC 会将请求对象直接传递给另一个处理器方法(show1()),而不会通过浏览器进行第二次请求,也不会通知浏览器客户端,所以界面不会发生变化。

        servlet方式进行获取:

@RequestMapping("/show4")public String show4(HttpServletRequest request){System.out.println("=========show4=========");//1.查询数据库(模拟)Emp emp = new Emp(1,"张毅老师","男");//2.获取sessionrequest.getSession().setAttribute("emp",emp);return "success_String";}

        通过 Spring MVC 提供的 HttpServletRequest 对象,可以访问请求信息,如参数、会话(session)等。创建一个 Emp 对象,模拟从数据库中查询到的一条记录。将创建的 Emp 对象存储在当前会话(session)中,键名为 "emp"。返回一个名为 "success_String" 的视图名称。

        再success_String.html中进行提取并打印操作:

<body><h1>返回值String成功页面</h1><h3>#(session.emp.eid)</h3><h3>#(session.emp.ename)</h3><h3>#(session.emp.esex)</h3>
</body>

        接下来有几个关键词:

  • @ResponseBody:对象转换为json
  • @RequestBody:json转换为对象
  • @RestController = @Controller + @ResponseBody

        示例代码(@ResponseBody):

@RequestMapping("/show1")@ResponseBodypublic List<Emp> show1(){//1模拟数据库Emp emp1 = new Emp(1,"张毅老师","男");Emp emp2 = new Emp(2,"张毅老师","男");Emp emp3 = new Emp(3,"张毅老师","男");List<Emp> list = new ArrayList<>();list.add(emp1);list.add(emp2);list.add(emp3);return list;}

        这段代码主要是通过@ResponseBody告诉 Spring MVC 这个方法的返回值应直接作为 HTTP 响应体,而不是作为视图名称,并且返回的数据(在这里是一个 List<Emp>)会被序列化为 JSON(或 XML,取决于配置),并作为响应体发送给客户端。

        客户端的结果:

        示例代码:

    @RequestMapping("/show2")@ResponseBodypublic String show2(){return "helloWorld";}

        这也是一样的道理,只不过加了@ResponseBody,不会被当成视图名称,而是直接给客户端返回helloWorld。

7、Spring的文件上传

        这里主要是对七云牛云仓库的文件上传和删除操作:

        示例代码(controller层):

    //进入测试页面@RequestMapping("/show")public String show(){return "index";}

        首先进入测试页面:

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>文件上传</title>
</head>
<body>文件上传:<ol><li>坐标</li><li>制作页面-form表单编码</li><li>通过*****接受文件</li></ol><hr/><form action="fileupload" method="post" enctype="multipart/form-data">用户名:<input name="uname"/><br/>图片:<input name="upic" type="file"/><br/><input type="submit" value="上传"/></form></body>
</html>

        定义一个方法上传:

//文件上传@RequestMapping("/fileupload")public String fileupload(String uname, MultipartFile upic, HttpServletRequest request){// 上传的用户名System.out.println("用户名:"+uname);// 是上传的文件System.out.println(upic);// upic.getOriginalFilename() 获取上传文件的原始名称System.out.println(upic.getOriginalFilename());// 获取表单字段名称。System.out.println(upic.getName());//方式1.将文件upic以流的方式写入当前服务器磁盘(应用服务器)//方式2.文件服务器(七牛云)//构造一个带指定 Region 对象的配置类//创建一个七牛云的配置对象,并使用自动选择的区域。Configuration cfg = new Configuration(Region.autoRegion());//...其他参数参考类注释// 创建一个UploadManager对象,这是七牛云提供的用于上传文件的管理器。UploadManager uploadManager = new UploadManager(cfg);//...生成上传凭证,然后准备上传String accessKey = "7tIQFZHzpSykkNeXOqjc1fD7_7BbVtV4h_L6qHsy";String secretKey = "vglGxwOz1SuuZlMzqLI-N_SA9fTs_CCINwt6tU70";String bucket = "zrzwork";//默认不指定key的情况下,以文件内容的hash值作为文件名String key = null;String name = null;try {// 将上传的文件转换为字节数组uploadBytesbyte[] uploadBytes = upic.getBytes();// 使用accessKey和secretKey创建一个Auth对象,用于生成上传凭证upToken。Auth auth = Auth.create(accessKey, secretKey);String upToken = auth.uploadToken(bucket);try {Response response = uploadManager.put(uploadBytes, key, upToken);//解析上传成功的结果DefaultPutRet putRet = new Gson().fromJson(response.bodyString(), DefaultPutRet.class);System.out.println(putRet.key);//获取文件名System.out.println(putRet.hash);//获取文件hash值name = putRet.key;} catch (QiniuException ex) {Response r = ex.response;System.err.println(r.toString());try {System.err.println(r.bodyString());} catch (QiniuException ex2) {//ignore}}} catch (Exception ex) {//ignore}request.getSession().setAttribute("picname",name);return "success";}

        具体实现步骤请看注释

        每次表单上传都会调用/filedeleteload方法,完成上传。

四、注册Servlet三大组件 Servlet/Filter/Listener

        而由于 Spring Boot 默认是以 jar 包的方式运行嵌入式Servlet容器来启动应用,没有web.xml文件, Spring提供以下Bean来注册三大组件。

        分别为:

  • ServletRegistrationBean 注册自定义Servlet(响应器
  • FilterRegistrationBean 注册自定义Filter(过滤器
  • ServletListenerRegistrationBean 注册自定义Listener(监听器

        MyFilter层的代码:

@WebFilter(urlPatterns = {"/*"})
public class MyFilter implements Filter{public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)throws IOException, ServletException {System.out.println("============请求过滤");request.setCharacterEncoding("utf-8");//分水岭chain.doFilter(request, response);response.setCharacterEncoding("utf-8");System.out.println("============响应过滤");}}

        @WebFilter(urlPatterns = {"/*"}):这个注解将过滤器应用于所有的请求路径。"/*"表示所有URL都会经过这个过滤器

        chain.doFilter(request, response):这是分水岭,表示请求继续传递到下一个过滤器或目标Servlet,执行完之后,响应开始处理。

        MyListener层的代码:

@WebListener
public class MyListener implements ServletContextListener {@Overridepublic void contextInitialized(ServletContextEvent sce) {ServletContextListener.super.contextInitialized(sce);System.out.println("-------------MyListener inited !");}@Overridepublic void contextDestroyed(ServletContextEvent sce) {ServletContextListener.super.contextDestroyed(sce);System.out.println("----------------MyListener Destroy !");}
}

        @WebListener:这个注解用于标记类为一个监听器,表示它会监听Web应用的某些事件。在部署时,服务器会自动注册这个监听器。

        implements ServletContextListener:实现了ServletContextListener接口,表示这个类会监听Servlet上下文(即整个Web应用)初始化和销毁的事件。

        contextInitialized方法:保证未来扩展时不会遗漏父类的处理。

        contextDestroyed方法:Web应用关闭(上下文销毁)。

        MyServlet层的代码:

@WebServlet("/myServlet")
public class MyServlet extends HttpServlet {protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException,IOException {System.out.println("进入servlet");resp.getWriter().println("<h1>hello world</h1>");};@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {this.doPost(req, resp);}
}

        resp.getWriter().println("<h1>hello world</h1>");向客户端返回一个简单的HTML响应(即页面上显示“hello world”)。

五、切换为其他嵌入式Servlet容器

1、SpringBoot 默认针对Servlet容器提供以下支持
  • Tomcat(默认使用)
  • Jetty :支持长连接项目(如:聊天页面)[ˈdʒeti]
  • Undertow : 不支持 JSP , 但是并发性能高,是高性能非阻塞的容器[ˈʌndətəʊ]

        默认Tomcat容器:

在spring-boot-starter-web启动器中默认引入了tomcat容器 
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-tomcat</artifactId><version>2.1.0.RELEASE</version><scope>compile</scope>
</dependency>

        切换Jetty容器:

<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId><!-- 排除tomcat容器 --><exclusions><exclusion><artifactId>spring-boot-starter-tomcat</artifactId><groupId>org.springframework.boot</groupId></exclusion></exclusions>
</dependency>
<!--引入其他的Servlet容器-->
<dependency><artifactId>spring-boot-starter-jetty</artifactId><groupId>org.springframework.boot</groupId>
</dependency>

        使用外置Servlet容器Tomcat9.x

        嵌入式Servlet容器:运行启动类就可启动,或将项目打成可执行的 jar 包

  • 优点:简单、快捷;
  • 缺点:默认不支持JSP、优化定制比较复杂使用定制器, 还需要知道 每个功能 的底层原理;

        外置Servlet容器:配置 Tomcat, 将项目部署到Tomcat中运行

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • 护眼大路灯哪个牌子好?公认五款最好护眼大路灯分享
  • C++ 特性之vector详解 + 联合opencv使用
  • 数据库方式实现实时排行榜
  • http参数污染利用php小特性绕过贷齐乐waf
  • Dom 元素转换 Image 图片 (截图)
  • 探索PHP的心脏:流行CMS系统全解析
  • KillWxapkg 自动化反编译微信小程序,小程序安全评估工具,发现小程序安全问题,自动解密,解包,可还原工程目录,支持修改Hook,小程序
  • html复习
  • 大语言模型面试宝典:30+ 必考问题与答案,助你一臂之力
  • 关于100个linux常用的命令
  • 2-63 基于matlab的GMPHD滤波器算法
  • 互联网摸鱼日报(2024-08-13)
  • Java Nacos与Gateway的使用
  • 【一文搞懂】Rewind AI是什么?Rewind AI能干嘛?全网最全指南!
  • Web自动化测试:UI自动化框架结构以及思路!
  • 《剑指offer》分解让复杂问题更简单
  • 【mysql】环境安装、服务启动、密码设置
  • 2017年终总结、随想
  • Create React App 使用
  • HTML5新特性总结
  • interface和setter,getter
  • React-生命周期杂记
  • SQLServer之创建数据库快照
  • vue-router的history模式发布配置
  • webgl (原生)基础入门指南【一】
  • 前端
  • 前端每日实战 2018 年 7 月份项目汇总(共 29 个项目)
  • 区块链分支循环
  • 如何将自己的网站分享到QQ空间,微信,微博等等
  • 我的zsh配置, 2019最新方案
  • 智能合约开发环境搭建及Hello World合约
  • 阿里云重庆大学大数据训练营落地分享
  • ​2020 年大前端技术趋势解读
  • ‌前端列表展示1000条大量数据时,后端通常需要进行一定的处理。‌
  • #define MODIFY_REG(REG, CLEARMASK, SETMASK)
  • #Js篇:单线程模式同步任务异步任务任务队列事件循环setTimeout() setInterval()
  • (Matalb时序预测)WOA-BP鲸鱼算法优化BP神经网络的多维时序回归预测
  • (二)构建dubbo分布式平台-平台功能导图
  • (机器学习-深度学习快速入门)第三章机器学习-第二节:机器学习模型之线性回归
  • (力扣)循环队列的实现与详解(C语言)
  • (五) 一起学 Unix 环境高级编程 (APUE) 之 进程环境
  • (五)activiti-modeler 编辑器初步优化
  • (一)Dubbo快速入门、介绍、使用
  • (转) SpringBoot:使用spring-boot-devtools进行热部署以及不生效的问题解决
  • (转)3D模板阴影原理
  • (转)Oracle存储过程编写经验和优化措施
  • .Net Core 生成管理员权限的应用程序
  • .NET MAUI Sqlite程序应用-数据库配置(一)
  • .NET Project Open Day(2011.11.13)
  • .net 打包工具_pyinstaller打包的exe太大?你需要站在巨人的肩膀上-VC++才是王道
  • .net 桌面开发 运行一阵子就自动关闭_聊城旋转门家用价格大约是多少,全自动旋转门,期待合作...
  • .NET8使用VS2022打包Docker镜像
  • .net实现头像缩放截取功能 -----转载自accp教程网
  • //解决validator验证插件多个name相同只验证第一的问题
  • :如何用SQL脚本保存存储过程返回的结果集