网上的文章五花八门,不写SpringBoot的版本号,导致代码拿来主义不好使了。 本文采用的版本 springBoot 2.7.7Java 1.8 目录 1、默认访问路径2、整个项目增加路由前
网上的文章五花八门,不写SpringBoot的版本号,导致代码拿来主义不好使了。
本文采用的版本
springBoot 2.7.7Java 1.8
package com.example.demo.controller.api;import org.springframework.WEB.bind.annotation.GetMapping;import org.springframework.web.bind.annotation.RequestMapping;import org.springframework.web.bind.annotation.RestController;@RestController@RequestMapping("/api")public class AppIndexController { @GetMapping("/index") public String index() { return "app"; }}
访问地址:Http://localhost:8080/api/index
application.yml
server: servlet: context-path: /prefix
访问地址:http://localhost:8080/prefix/api/index
注意:该方案会将所有的路由都增加一个前缀
注解
package com.example.demo.annotation;import org.springframework.core.annotation.AliasFor;import org.springframework.stereotype.Controller;import org.springframework.web.bind.annotation.RestController;import java.lang.annotation.*;@Target(ElementType.TYPE)@Retention(RetentionPolicy.RUNTIME)@Documented@RestControllerpublic @interface ApiRestController { @AliasFor(annotation = Controller.class) String value() default "";}
配置
package com.example.demo.config;import com.example.demo.annotation.ApiRestController;import org.springframework.context.annotation.Configuration;import org.springframework.web.servlet.config.annotation.PathMatchConfigurer;import org.springframework.web.servlet.config.annotation.WebmvcConfigurer;@Configurationpublic class CustomWebMvcConfig implements WebMvcConfigurer { @Override public void configurePathMatch(PathMatchConfigurer configurer) { configurer .addPathPrefix("/api", c -> c.isAnnotationPresent(ApiRestController.class)); }}
使用注解
package com.example.demo.controller.api;import com.example.demo.annotation.ApiRestController;import org.springframework.web.bind.annotation.GetMapping;@ApiRestController// @RestController// @RequestMapping("/api")public class AppIndexController { @GetMapping("/index") public String index() { return "app"; }}
访问地址:http://localhost:8080/api/index
没有成功,可能是版本的问题
按照网上的实现方式
// 核心代码RequestMappingInfo.paths(prefix).build().combine(mappingInfo);
会报错
Neither PathPatterns nor String patterns condition
2023年6月9日补充
感谢评论区的大佬 @孤独和弦 帮助,补充第四种方式
思路:
将原有路由的所有路径取出,手动拼接前缀,再和原有路由配置合并
项目结构
$ tree -I target -I test.├── pom.xml└── src └── main ├── java │ └── com │ └── example │ └── demo │ ├── Application.java │ ├── config │ │ ├── AutoPrefixConfiguration.java │ │ └── AutoPrefixUrlMapping.java │ └── controller │ └── v1 │ └── IndexController.java └── resources ├── application.yml ├── static └── templates
配置 application.yml
# 需要添加路径前缀的包名api-package: com.example.demo.controller
AutoPrefixUrlMapping.java
package com.example.demo.config;import org.springframework.beans.factory.annotation.Value;import org.springframework.web.servlet.mvc.method.RequestMappingInfo;import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping;import java.lang.reflect.Method;import java.util.Objects;public class AutoPrefixUrlMapping extends RequestMappingHandlerMapping { @Value("${api-package}") private String bathApiPackagePath; @Override protected RequestMappingInfo getMappingFORMethod(Method method, Class<?> handlerType) { RequestMappingInfo mappingInfo = super.getMappingForMethod(method, handlerType); if (Objects.nonNull(mappingInfo)) { String prefix = this.getPrefix(handlerType); if (prefix != null) { String[] paths = mappingInfo.getPatternValues() .stream() .map(path -> prefix + path) .toArray(String[]::new); return mappingInfo.mutate() .paths(paths) .build(); } } return mappingInfo; } private String getPrefix(Class<?> handleType) { String packageName = handleType.getPackage().getName(); // 如果包含指定的包则返回前缀 if (packageName.startsWith(this.bathApiPackagePath)) { return packageName.substring(this.bathApiPackagePath.length()) .replace(".", "/"); } else { return null; } }}
AutoPrefixConfiguration.java
package com.example.demo.config;import org.springframework.boot.autoconfigure.web.servlet.WebMvcReGIStrations;import org.springframework.stereotype.Component;import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping;@Componentpublic class AutoPrefixConfiguration implements WebMvcRegistrations { @Override public RequestMappingHandlerMapping getRequestMappingHandlerMapping() { return new AutoPrefixUrlMapping(); }}
控制器
package com.example.demo.controller.v1;import org.springframework.web.bind.annotation.GetMapping;import org.springframework.web.bind.annotation.RequestMapping;import org.springframework.web.bind.annotation.RestController;@RestController@RequestMapping("/api")public class IndexController { @GetMapping("/index") public String index() { return "Hello"; }}
访问路径:http://localhost:8080/v1/api/index
方 式 | 适用范围 |
---|---|
RequestMapping/PostMapping/GetMapping | 单个方法 或 单个类(多个方法) |
自定义注解 | 多个控制器(可以不同目录) |
目录 / 包名 前缀 | 多个控制器(同目录) |
配置 context-path | 全局前缀 |
包名前缀只能是符合java包名规范的才可以,比如中划线就不行,需要修改代码自定义做映射
--结束END--
本文标题: Java:SpringBoot给Controller添加统一路由前缀
本文链接: https://lsjlt.com/news/398282.html(转载时请注明来源链接)
有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341
2024-04-01
2024-04-03
2024-04-03
2024-01-21
2024-01-21
2024-01-21
2024-01-21
2023-12-23
回答
回答
回答
回答
回答
回答
回答
回答
回答
回答
0