【SpringBoot】| SpringBoot 和 web组件

news2024/11/16 3:30:04

目录

一:SpringBoot 和 web组件

1. SpringBoot中使用拦截器(重点)

2. SpringBoot中使用Servlet

3. SpringBoot中使用过滤器(重点)

4. 字符集过滤器的应用


一:SpringBoot 和 web组件

1. SpringBoot中使用拦截器Interceptor(重点)

拦截器是SpringMVC中一种对象,能够拦截器对Controller的请求!

拦截器框架中有系统的拦截器, 还可以自定义拦截器, 实现对请求预先处理!

实现自定义拦截器:

第一步:创建一个类实现SpringMVC框架的HandlerInterceptor接口,重写方法。

HandlerInterceptor接口源码中有三个默认方法,常用的是preHandle方法中进行拦截:

package org.springframework.web.servlet;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.lang.Nullable;

public interface HandlerInterceptor {
    default boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        return true;
    }

    default void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable ModelAndView modelAndView) throws Exception {
    }

    default void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable Exception ex) throws Exception {
    }
}

编写LoginInterceptor类实现HandlerInterceptor接口,并重写preHandler方法

package com.zl.web;

import org.springframework.web.servlet.HandlerInterceptor;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

// 自定义拦截器
public class LoginInterceptor implements HandlerInterceptor {
    /**
     * @param request
     * @param response
     * @param handler 被拦截的控制器对象
     * @return boolean,true:表示请求能被Controller处理,false:表示被截断
     * @throws Exception
     */
    @Override
    public boolean preHandle(HttpServletRequest request,
                             HttpServletResponse response,
                             Object handler) throws Exception { // handler是被拦截的控制器对象

        System.out.println("请求拦截器执行了");
        return false;
    }
}

第二步:SpringBoot中注册声明拦截器

SpringMVC框架中注册声明拦截器

<mvc:interceptors>
	<mvc:interceptor>
    	<mvc:path="url" />
        <bean class="拦截器类全限定名称"/>
    </mvc:interceptor>
</mvc:interceptors>

SpringBoot框架中注册声明拦截器

(1)使用类+注解的方式,编写一个类实现WebMvcConfigurer接口(这个接口很重要,后面会讲,并添加@Configuration注解,关于SpringMVC有关的功能都在WebMvcConfigurer接口中实现了!

(2)重写addInterceptors方法,在方法中添加拦截器对象,注入到容器当中;然后在调用addPathPatterns添加拦截的请求,再调用excludePathPatterns排除拦截的请求。

package com.zl.config;

import com.zl.web.LoginInterceptor;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

@Configuration // 这个类当做配置文件使用
public class MyAppConfigurer implements WebMvcConfigurer {
    // 添加拦截器对象,注入到容器中
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        // 创建拦截器对象
        HandlerInterceptor interceptor = new LoginInterceptor();
        // 调用addInterceptor方法表示注入到容器中
        // 调用addPathPatterns方法表示可以拦截的请求
        // 调用excludePathPatterns方法表示通过的请求
        registry.addInterceptor(interceptor)
                .addPathPatterns("/user/**")
                .excludePathPatterns("/user/login");
    }
}

第三步:编写controller进行访问

package com.zl.controller;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;


@Controller
public class BootController {

    @RequestMapping("/user/account") // 会被拦截
    @ResponseBody
    public String userAccount(){
        return "访问user/account地址";
    }

    @RequestMapping("/user/login")
    @ResponseBody
    public String userLogin(){
        return "访问user/login地址"; // 会被通过
}

2. SpringBoot中使用Servlet

在SpringBoot框架中使用Servlet对象!

使用步骤:

②创建Servlet类继承HttpServlet类

注册Servlet ,让框架能找到Servlet。

第一步:创建Servlet类继承HttpServlet

重写doGet和doPost方法,并且在doGet中调用doPost方法,这样不论发过来post请求还是get请求都没有问题!

package com.zl.web;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;

public class MyServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        // 调用doPost方法
       doPost(request,response);
    }

    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        // 使用HttpServletResponse输出数据,应答结果
        response.setContentType("text/html;charset=UTF-8");
        PrintWriter out = response.getWriter();
        out.println("执行的是Servlet");
        out.flush();
        out.close();
    }
}

第二步:注册Servlet ,让框架能找到Servlet

(1)ServletRegistrationBean用来做在 servlet 3.0+容器中注册 servlet 的功能,但更具有 SpringBean友好性。

(2)首先写一个类,类名随意加上@Configuration注解,表示这个类是配置信息的类;再类中编写一个servletRegistrationBean()方法返回值是ServletRegistrationBean对象

(3)添加上@Bean注解。@Bean用于将对象存入spring的ioc容器中,同@controller、@Service、@Component、@Configuration、@Repository等几个注解是一样的,都是负责将对象存入容器当中。只不过方式不同,四个注解它们是用在类上面的,然后将当前类通过无参构造函数创建对象然后放入容器;而@Bean是用在方法上,将当前方法的返回值对象放到容器当中!可以理解为前者是由spring自动创建对象,而@Bean创建对象是交给我们自己来控制。

package com.zl.config;

import com.zl.web.MyServlet;
import org.springframework.boot.web.servlet.ServletRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import javax.servlet.Servlet;
import javax.servlet.http.HttpServlet;

@Configuration
public class WebAppConfig {
    // 定义方法,注册Servlet对象
    @Bean // 把ServletRegistrationBean对象放到容器当中
    public ServletRegistrationBean servletRegistrationBean(){
        // 创建ServletRegistrationBean对象,有两个参数:
        // 一个参数是servlet,一个参数是url地址
        HttpServlet servlet = new MyServlet();
        ServletRegistrationBean bean = new ServletRegistrationBean(servlet,"/myservlet");
        return bean;
    }
}

当然也可以使用无参数构造方法,调用引用.set方法进行赋值,对于路径也可以赋多个

ServletRegistrationBean bean = new ServletRegistrationBean();
bean.setServlet(servlet);
bean.addUrlMappings("/login","/test"); // 多个路径都可以访问

3. SpringBoot中使用过滤器Filter(重点)

Filter是Servlet规范中的过滤器,可以处理请求、对请求的参数、属性进行调整; 常常在过滤器中处理字符编码

使用步骤:

①创建自定义过滤器类;

②注册Filter过滤器对象;

注:对于过滤器和拦截器的简单理解

(1)过滤器是用来过滤request或者response参数的(比如:增加一些乱码),侧重于对数据的过滤;

(2)而拦截器是用来验证请求的,能够截断请求!

第一步:创建自定义过滤器类

创建MyFilter类实现Filter接口重写doFilter方法,进行处理;处理好以后调用filterChain参数的doFilter方法,把请求传递出去,继续进行下一步操作。

package com.zl.web;

import javax.servlet.*;
import java.io.IOException;
// 自定义过滤器类
public class MyFilter implements Filter {
    @Override
    public void doFilter(ServletRequest request, 
                         ServletResponse response, 
                         FilterChain filterChain) throws IOException, ServletException {
       // 处理字符集编码
        response.setContentType("text/html;charset=UTF-8");
        System.out.println("Filter过滤器执行了");
        // 把请求转发出去
        filterChain.doFilter(request,response);
    }
}

第二步:注册过滤器对象

写一个配置类,类名随意加上@Configuration注解,表示这个类是配置信息的类;再类中编写一个filterRegistrationBean()方法返回值是FilterRegistrationBean对象,并在方法上加上@Bean注解,把返回的对象交给Spring容器管理。

package com.zl.config;

import com.zl.web.MyFilter;
import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import javax.servlet.FilterRegistration;

@Configuration
public class WebApplicationConfig {
    @Bean
    public FilterRegistrationBean filterRegistrationBean (){
        // 调用无参数构造方法
        FilterRegistrationBean bean = new FilterRegistrationBean();
        bean.setFilter(new MyFilter()); // 指定过滤器对象
        bean.addUrlPatterns("/user/*"); // 指定过滤的地址
        return bean;
    }
}

编写controller进行访问

package com.zl.controller;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

@Controller
public class CustomerFilterController {
    @RequestMapping("/user/account")
    @ResponseBody
    public String userAccount(){
        return "user/account执行了";
    }
}

4. 字符集过滤器的应用

CharacterEncodingFilter:解决post请求中乱码的问题;在SpringMVC框架, 在web.xml注册过滤器,配置它的属性,解决乱码问题!

创建一个Servlet

package com.zl.servlet;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;


public class MyServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        doPost(request,response);
    }

    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        response.setContentType("text/html");
        PrintWriter out = response.getWriter();
        out.println("在Servlet中使用中文");
        out.flush();
        out.close();
    }
}

注册Servlet

package com.zl.web;

import com.zl.servlet.MyServlet;
import org.springframework.boot.web.servlet.ServletRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Controller;

@Controller
public class WebAppConfig {
    // 注册Servlet
    @Bean
    public ServletRegistrationBean servletRegistrationBean(){
        MyServlet myServlet = new MyServlet();
        ServletRegistrationBean bean = new ServletRegistrationBean(myServlet, "/myservlet");
        return bean;
    }
}

进行访问:发现中文乱码

F12,刷新请求并打开,发现默认的编码方式是:ISO-8859-1

第一种解决方式:自定义过滤器,比较麻烦,不推荐

①在注册Servlet中添加过滤器

package com.zl.web;

import com.zl.servlet.MyServlet;
import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.boot.web.servlet.ServletRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Controller;
import org.springframework.web.filter.CharacterEncodingFilter;


@Controller
public class WebAppConfig {
    // 注册Servlet
    @Bean
    public ServletRegistrationBean servletRegistrationBean(){
        MyServlet myServlet = new MyServlet();
        ServletRegistrationBean bean = new ServletRegistrationBean(myServlet, "/myservlet");
        return bean;
    }

    // 注册Filter
    @Bean
    public FilterRegistrationBean filterRegistrationBean(){
        FilterRegistrationBean bean = new FilterRegistrationBean();

        // 使用框架中的过滤器
        CharacterEncodingFilter filter = new CharacterEncodingFilter();
        // 指定使用的编码方式
        filter.setEncoding("UTF-8");
        // 指定request,response使用encoding的值
        filter.setForceEncoding(true);
        // 给filter设置参数
        bean.setFilter(filter);
        bean.addUrlPatterns("/*"); // 过滤所有的地址
        
        return bean;

    }
}

②修改application.properties文件, 让自定义的过滤器起作用

#SpringBoot中默认已经配置启用了CharacterEncodingFilter,编码默认ISO-8859-1
#设置enabled=false 作用是关闭系统中配置好的过滤器, 使用自定义的CharacterEncodingFilter
server.servlet.encoding.enabled=false

第二种方式:直接使用框架中的过滤器,比较简单,推荐使用

注:实际上SpringBoot已经把字符编码的过滤器自动纳入容器管理了,通过源码分析可以发现这个配置与配置文件application.properties中的server.servlet.encoding配置进行了绑定。

package org.springframework.boot.autoconfigure.web.servlet;

import org.springframework.boot.autoconfigure.AutoConfiguration;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication;
import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication.Type;
import org.springframework.boot.autoconfigure.web.ServerProperties;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.boot.web.server.WebServerFactoryCustomizer;
import org.springframework.boot.web.servlet.filter.OrderedCharacterEncodingFilter;
import org.springframework.boot.web.servlet.server.ConfigurableServletWebServerFactory;
import org.springframework.boot.web.servlet.server.Encoding;
import org.springframework.context.annotation.Bean;
import org.springframework.core.Ordered;
import org.springframework.web.filter.CharacterEncodingFilter;

@AutoConfiguration
@EnableConfigurationProperties({ServerProperties.class})
@ConditionalOnWebApplication(
    type = Type.SERVLET
)
@ConditionalOnClass({CharacterEncodingFilter.class})
@ConditionalOnProperty(
    prefix = "server.servlet.encoding",
    value = {"enabled"},
    matchIfMissing = true
)
public class HttpEncodingAutoConfiguration {
    private final Encoding properties;

    public HttpEncodingAutoConfiguration(ServerProperties properties) {
        this.properties = properties.getServlet().getEncoding();
    }

    // 自动装入了容器中去
    @Bean
    @ConditionalOnMissingBean
    public CharacterEncodingFilter characterEncodingFilter() {
        CharacterEncodingFilter filter = new OrderedCharacterEncodingFilter();
        filter.setEncoding(this.properties.getCharset().name());
        filter.setForceRequestEncoding(this.properties.shouldForce(org.springframework.boot.web.servlet.server.Encoding.Type.REQUEST));
        filter.setForceResponseEncoding(this.properties.shouldForce(org.springframework.boot.web.servlet.server.Encoding.Type.RESPONSE));
        return filter;
    }

    @Bean
    public LocaleCharsetMappingsCustomizer localeCharsetMappingsCustomizer() {
        return new LocaleCharsetMappingsCustomizer(this.properties);
    }

    static class LocaleCharsetMappingsCustomizer implements WebServerFactoryCustomizer<ConfigurableServletWebServerFactory>, Ordered {
        private final Encoding properties;

        LocaleCharsetMappingsCustomizer(Encoding properties) {
            this.properties = properties;
        }

        public void customize(ConfigurableServletWebServerFactory factory) {
            if (this.properties.getMapping() != null) {
                factory.setLocaleCharsetMappings(this.properties.getMapping());
            }

        }

        public int getOrder() {
            return 0;
        }
    }
}

直接修改application.properties文件进行更改

#让系统的CharacterEncdoingFilter生效,默认就是开启的,不写也行
server.servlet.encoding.enabled=true
#指定使用的编码方式
server.servlet.encoding.charset=utf-8
#强制request,response都使用charset属性的值
server.servlet.encoding.force=true

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/818134.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

yellowbrick:一款特征工程可视化神器!

在建立模型之前一个非常重要的工作就是做特征工程&#xff0c;而在特征工程的过程中&#xff0c;探索性数据分析又是必不可少的一部分。 本次介绍一款功能十分强大的特征工程可视化工具&#xff1a;yellowbrick&#xff0c;包括雷达、一维排序、PCA、特征重要性、递归消除、正…

vue2实现一个树型控件(支持展开树与checkbox勾选)

目录 vue2实现一个树型控件(支持展开树与checkbox勾选)TreeItem.vueTree.vue效果 vue2实现一个树型控件(支持展开树与checkbox勾选) TreeItem.vue <template><div class"tree-item"><span click"toggleExpanded" class"icon" v…

用户需求转化为产品需求的5大注意事项

用户需求不等于产品需求&#xff0c;如果将用户需求和产品需求混为一谈&#xff0c;往往容易产生需求不完整、需求错误以及后期需求变更频繁等问题&#xff0c;那么用户需求转化为产品需求有什么注意事项&#xff1f; 1、了解需求转化落地逻辑流程 需要注意&#xff0c;用户需求…

DT水下照明学习

ocean1.timetime*.5; 水草动画 整体样子 叶子数量相关设置 植物运动相关 晃动不明显 增加这里的值 螺旋 弯曲播放&#xff0c;植物不会变直 表达式 kelp1.spiralMinsin(frame*.1)/5; 水泡 particleShape1.spriteScaleXPP particleShape1.spriteScaleYPP rand(0.1,0.5); part…

Nginx 【实战篇】 ---- Nginx 实战(购买服务器、域名、申请证书)

Nginx 【实战篇】 ---- Nginx 实战 1. 购买域名2. 购买服务器3. 服务器的基础配置和ssh连接4. 配置 LNMP 环境和防火墙配置4.1 配置 LNMP 环境4.2 修改防火墙配置 5. 将域名解析到服务器上6. 在线申请证书7. 将刚申请的证书配置到Nginx上 1. 购买域名 2. 购买服务器 域名和服务…

spring boot项目整合spring security权限认证

一、准备一个spring boot项目 1、引入基础依赖 <dependencies><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency><dependency><groupId>org.sp…

RuoYi-Vue代码常见漏洞修复

Redis未设置密码 解决方法&#xff1a; 此方法永久生效* 找到requirepass关键字&#xff0c;后面就是跟的密码&#xff0c;默认情况下是注释掉的&#xff0c;即默认不需要密码&#xff0c;如下&#xff1a;  打开注释&#xff0c;设置为自己的密码&#xff0c;重启即可 数据…

Scrum敏捷开发管理流程+scrum工具免费

Leangoo领歌它覆盖了敏捷项目研发全流程&#xff0c;包括小型团队Scrum敏捷开发&#xff0c;规模化敏捷SAFe&#xff0c;Scrum of Scrums大规模敏捷。它提供了灵活的敏捷模板和极致的协作体验&#xff0c;可以让团队快速上手&#xff0c;快速落地Scrum敏捷开发管理。 首先建立产…

06 HTTP(下)

06 HTTP&#xff08;下&#xff09; 介绍服务器如何响应请求报文&#xff0c;并将该报文发送给浏览器端。介绍一些基础API&#xff0c;然后结合流程图和代码对服务器响应请求报文进行详解。 基础API部分&#xff0c;介绍stat、mmap、iovec、writev。 流程图部分&#xff0c;描…

ssm员工管理系统

ssm员工管理系统 java员工管理系统 员工管理系统 运行环境&#xff1a; JAVA版本&#xff1a;JDK1.8 IDE类型&#xff1a;IDEA、Eclipse都可运行 数据库类型&#xff1a;MySql&#xff08;8.x版本都可&#xff09; 硬件环境&#xff1a;Windows 功能介绍&#xff1a; 1.用户…

html学习3(表格table、列表list)

1、html表格由<table>标签来定义。 <thead>用来定义表格的标题部分&#xff0c;其内部用 <th > 元素定义列的标题&#xff0c;可以使其在表格中以粗体显示&#xff0c;与普通单元格区分开来。<tbody>用来定义表格的主体部分&#xff0c;其内部用<t…

Java版知识付费免费搭建+spring cloud 前后端分离实现知识付费平台

提供职业教育、企业培训、知识付费系统搭建服务。系统功能包含&#xff1a;录播课、直播课、题库、营销、公司组织架构、员工入职培训等。 提供私有化部署&#xff0c;免费售后&#xff0c;专业技术指导&#xff0c;支持PC、APP、H5、小程序多终端同步&#xff0c;支持二次开发…

CompletableFuture 详解

目录 简单介绍 常见操作 创建 CompletableFuture new 关键字 静态工厂方法 处理异步结算的结果 简单介绍 CompletableFuture 同时实现了 Future 和 CompletionStage 接口。 public class CompletableFuture<T> implements Future<T>, CompletionStage<T…

小白到运维工程师自学之路 第六十集 (docker的概述与安装)

一、概述 1、客户&#xff08;老板&#xff09;-产品-开发-测试-运维项目周期不断延后&#xff0c;项目质量差。 随着云计算和DevOps生态圈的蓬勃发展&#xff0c;产生了大量优秀的系统和软件。软件开发人员可以自由选择各种软件应用环境。但同时带来的问题就是需要维护一个非…

HTTP——HTTP报文内的HTTP信息

HTTP 通信过程包括从客户端发往服务器端的请求及从服务器端返回客户端的响应。本章就让我们来了解一下请求和响应是怎样运作的。 HTTP 一、HTTP报文二、请求报文及响应报文的结构三、编码提升传输速率1、报文主体和实体主题的差异2、压缩传输的内容编码3、分割发送的分块传输编…

【数据分享】1999—2021年地级市地区生产总值及一二三产构成数据(Shp/Excel格式)

在之前的文章中&#xff0c;我们分享过基于2000-2022年《中国城市统计年鉴》整理的1999-2021年地级市的人口相关数据、各类用地面积数据、污染物排放和环境治理相关数据、房地产投资情况和商品房销售面积、社会消费品零售总额和年末金融机构存贷款余额、地方一般公共预算收支状…

ABeam China Global | 探索赞比亚:非洲市场商机、产业发展与劳动挑战(下)

前情回顾 ABeam China Global | 探索赞比亚&#xff1a;非洲市场商机、产业发展与劳动挑战&#xff08;上&#xff09; 在「探索赞比亚」系列的上期&#xff0c;我们介绍了森大集团、非洲市场概述&#xff0c;以及“SADC”这一地区经济组织。本期我们将视角聚焦到赞比亚&…

Android Studio多渠道打包

使用环境&#xff1a; Android studio 多渠道打包 使用方法&#xff1a; 1 APP下build.gradle文件 flavorDimensions "default"productFlavors {huawei {dimension "default"manifestPlaceholders [ channel:"huawei" ]}xiaomi {dimension &…

LLM微调 | Adapter: Parameter-Efficient Transfer Learning for NLP

目的&#xff1a;大模型预训练微调范式&#xff0c;微调成本高。adapter只只微调新增的小部分参数【但adapter增加了模型层数&#xff0c;引入了额外的推理延迟。】 Adapters最初来源于CV领域的《Learning multiple visual domains with residual adapters》一文&#xff0c;其…

数据库信息速递, RAFT 原生系统是未来数据流式系统的未来

开头还是介绍一下群&#xff0c;如果感兴趣polardb ,mongodb ,mysql ,postgresql ,redis 等有问题&#xff0c;有需求都可以加群群内有各大数据库行业大咖&#xff0c;CTO&#xff0c;可以解决你的问题。加群请联系 liuaustin3 &#xff0c;在新加的朋友会分到2群&#xff08;共…