- 查看WebMvcAutoConfiguration,默认配置了OrderedHiddenHttpMethodFilter
| @Configuration(proxyBeanMethods = false) |
| @ConditionalOnWebApplication(type = Type.SERVLET) |
| @ConditionalOnClass({ Servlet.class, DispatcherServlet.class, WebMvcConfigurer.class }) |
| @ConditionalOnMissingBean(WebMvcConfigurationSupport.class) |
| @AutoConfigureOrder(Ordered.HIGHEST_PRECEDENCE + 10) |
| @AutoConfigureAfter({ DispatcherServletAutoConfiguration.class, TaskExecutionAutoConfiguration.class, |
| ValidationAutoConfiguration.class }) |
| public class WebMvcAutoConfiguration { |
| |
| public static final String DEFAULT_PREFIX = ""; |
| |
| public static final String DEFAULT_SUFFIX = ""; |
| |
| private static final String[] SERVLET_LOCATIONS = { "/" }; |
| |
| @Bean |
| |
| @ConditionalOnMissingBean(HiddenHttpMethodFilter.class) |
| |
| @ConditionalOnProperty(prefix = "spring.mvc.hiddenmethod.filter", name = "enabled", matchIfMissing = false) |
| public OrderedHiddenHttpMethodFilter hiddenHttpMethodFilter() { |
| return new OrderedHiddenHttpMethodFilter(); |
| } |
- 查看OrderedHiddenHttpMethodFilter
| public class OrderedHiddenHttpMethodFilter extends HiddenHttpMethodFilter implements OrderedFilter { |
| public static final int DEFAULT_ORDER = -10000; |
| private int order = -10000; |
| |
| public OrderedHiddenHttpMethodFilter() { |
| } |
| |
| public int getOrder() { |
| return this.order; |
| } |
| |
| public void setOrder(int order) { |
| this.order = order; |
| } |
| } |
- 查看HiddenHttpMethodFilter,表示我们需要带1个隐藏的参数项_method
| public class HiddenHttpMethodFilter extends OncePerRequestFilter { |
| private static final List<String> ALLOWED_METHODS; |
| public static final String DEFAULT_METHOD_PARAM = "_method"; |
| private String methodParam = "_method"; |
| |
| public HiddenHttpMethodFilter() { |
| } |
| |
| public void setMethodParam(String methodParam) { |
| Assert.hasText(methodParam, "'methodParam' must not be empty"); |
| this.methodParam = methodParam; |
| } |
| ● 表单提交会带上_method=PUT |
| ● 请求过来被HiddenHttpMethodFilter拦截 |
| ○ 请求是否正常,并且是POST |
| ■ 获取到_method的值。 |
| ■ 兼容以下请求;PUT.DELETE.PATCH |
| ■ 原生request(post),包装模式requesWrapper重写了getMethod方法,返回的是传入的值。 |
| ■ 过滤器链放行的时候用wrapper。以后的方法调用getMethod是调用requesWrapper的。 |
| |
| # 前端 |
| 测试REST风格; |
| <form action="/user" method="get"> |
| <input value="REST-GET 提交" type="submit"/> |
| </form> |
| <form action="/user" method="post"> |
| <input value="REST-POST 提交" type="submit"/> |
| </form> |
| <form action="/user" method="post"> |
| <input name="_method" type="hidden" value="delete"/> |
| <input value="REST-DELETE 提交" type="submit"/> |
| </form> |
| <form action="/user" method="post"> |
| <input name="_method" type="hidden" value="PUT"/> |
| <input value="REST-PUT 提交" type="submit"/> |
| </form> |
| |
| # 后端 |
| @RestController |
| public class HelloController { |
| |
| @RequestMapping(value = "/user",method = RequestMethod.GET) |
| public String getUser(){ |
| return "GET-张三"; |
| } |
| |
| @RequestMapping(value = "/user",method = RequestMethod.POST) |
| public String saveUser(){ |
| return "POST-张三"; |
| } |
| |
| |
| @RequestMapping(value = "/user",method = RequestMethod.PUT) |
| public String putUser(){ |
| return "PUT-张三"; |
| } |
| |
| @RequestMapping(value = "/user",method = RequestMethod.DELETE) |
| public String deleteUser(){ |
| return "DELETE-张三"; |
| } |
| |
| } |
| |
| # yml |
| spring: |
| mvc: |
| hiddenmethod: |
| filter: |
| enabled: true #开启页面表单的Rest功能 |
| @RestController |
| public class HelloController { |
| |
| @GetMapping("/user") |
| public String getUser(){ |
| return "GET-张三"; |
| } |
| |
| @PostMapping("/user") |
| public String saveUser(){ |
| return "POST-张三"; |
| } |
| |
| @PutMapping("/user") |
| public String putUser(){ |
| return "PUT-张三"; |
| } |
| |
| @DeleteMapping("/user") |
| public String deleteUser(){ |
| return "DELETE-张三"; |
| } |
| |
| } |
- 自定义filter:作用是将_mothod改为自定义字符
| # 后端webConfig中配置: |
| @Bean |
| public HiddenHttpMethodFilter hiddenHttpMethodFilter(){ |
| HiddenHttpMethodFilter methodFilter = new HiddenHttpMethodFilter(); |
| methodFilter.setMethodParam("_m"); |
| return methodFilter; |
| } |
| |
| # 前端表单中: |
| <form action="/user" method="post"> |
| <input name="_m" type="hidden" value="delete"/> |
| <input value="REST-DELETE 提交" type="submit"/> |
| </form> |
| |
| # 手动开启HiddenHttpMethodFilter,yml中配置 |
| |
| # 后端控制器: |
| @RequestMapping(value = "/user",method = RequestMethod.DELETE) |
| public String deleteUser(){ |
| return "DELETE-张三"; |
| } |
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· AI 智能体引爆开源社区「GitHub 热点速览」
· 三行代码完成国际化适配,妙~啊~
· .NET Core 中如何实现缓存的预热?