在 Spring 的编译期间用另一个注释替换一个注释?

我在我的控制器参数上使用 Swagger 注释。所以,我最终得到了像@ApiParam(name="default name", value="this is a default value"). 我认为这很冗长。我想把它改成类似的东西@Foo。我想知道是否有办法在编译期间@Foo替换为。@ApiParam另外,由于我使用的是 Spring,我想我也必须考虑 Spring 中的注释处理顺序。我的意思是我不应该在 Swagger 或 Spring 接受它之后替换@ApiParam为。@Foo有什么办法吗?

简而言之,我使用了 5 次具有相同参数的相同注释。基本上,我想用一些自定义注释替换它们。

我知道我必须展示我已经尝试过的东西,但我不知道从哪里开始。

另外,这个问题与Swagger无关,它只是一个例子。我想在编译时将一个注解替换为另一个注解,这样 Spring 拾取的将不是我放在源代码上的那个,而是我替换的那个。


慕田峪7331174
浏览 103回答 1
1回答

慕码人2483693

如果我理解您的要求,则无需编译时注释处理即可实现。它并不漂亮,而且可能比它的价值更复杂,但这是一种方法。这是我制作的自定义注释,用于我的速记@ApiParam。@Retention(RetentionPolicy.RUNTIME)@Target(ElementType.PARAMETER)public @interface GameIdParam {&nbsp; &nbsp; String name() default "My Game ID";&nbsp; &nbsp; String value() default "The integer ID of a particular game";}@ApiParam您可以定义您希望覆盖的任何属性。然后您可以使用Springfox 的扩展框架为新注释实现自定义处理程序。import com.google.common.base.Optional;import io.swagger.annotations.ApiParam;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.core.annotation.AnnotationUtils;import org.springframework.stereotype.Component;import springfox.documentation.schema.Example;import springfox.documentation.spi.DocumentationType;import springfox.documentation.spi.schema.EnumTypeDeterminer;import springfox.documentation.spi.service.contexts.ParameterContext;import springfox.documentation.spring.web.DescriptionResolver;import springfox.documentation.swagger.readers.parameter.ApiParamParameterBuilder;import java.util.function.Predicate;import static java.util.Optional.ofNullable;import static springfox.documentation.swagger.common.SwaggerPluginSupport.SWAGGER_PLUGIN_ORDER;import static springfox.documentation.swagger.common.SwaggerPluginSupport.pluginDoesApply;import static springfox.documentation.swagger.readers.parameter.Examples.examples;@Componentpublic class ShorthandAnnotationPlugin extends ApiParamParameterBuilder {&nbsp; &nbsp; private final DescriptionResolver descriptions;&nbsp; &nbsp; private final EnumTypeDeterminer enumTypeDeterminer;&nbsp; &nbsp; @Autowired&nbsp; &nbsp; public ShorthandAnnotationPlugin(&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; DescriptionResolver descriptions,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; EnumTypeDeterminer enumTypeDeterminer) {&nbsp; &nbsp; &nbsp; &nbsp; super(descriptions, enumTypeDeterminer);&nbsp; &nbsp; &nbsp; &nbsp; this.descriptions = descriptions;&nbsp; &nbsp; &nbsp; &nbsp; this.enumTypeDeterminer = enumTypeDeterminer;&nbsp; &nbsp; }&nbsp; &nbsp; @Override&nbsp; &nbsp; public void apply(ParameterContext context) {&nbsp; &nbsp; &nbsp; &nbsp; Optional<GameIdParam> gameIdParam = context.resolvedMethodParameter().findAnnotation(GameIdParam.class);&nbsp; &nbsp; &nbsp; &nbsp; if (gameIdParam.isPresent()) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; GameIdParam annotation = gameIdParam.get();&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; // Instantiate an ApiParam so we can take default values for attributes we didn't override.&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; ApiParam parentAnnotation = AnnotationUtils.synthesizeAnnotation(ApiParam.class);&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; context.parameterBuilder().name(ofNullable(annotation.name())&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .filter(((Predicate<String>) String::isEmpty).negate()).orElse(null))&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .description(ofNullable(descriptions.resolve(annotation.value()))&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .filter(((Predicate<String>) String::isEmpty).negate()).orElse(null))&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .parameterAccess(ofNullable(parentAnnotation.access())&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .filter(((Predicate<String>) String::isEmpty).negate())&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .orElse(null))&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .defaultValue(ofNullable(parentAnnotation.defaultValue())&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .filter(((Predicate<String>) String::isEmpty).negate())&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .orElse(null))&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .allowMultiple(parentAnnotation.allowMultiple())&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .allowEmptyValue(parentAnnotation.allowEmptyValue())&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .required(parentAnnotation.required())&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .scalarExample(new Example(parentAnnotation.example()))&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .complexExamples(examples(parentAnnotation.examples()))&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .hidden(parentAnnotation.hidden())&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .collectionFormat(parentAnnotation.collectionFormat())&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .order(SWAGGER_PLUGIN_ORDER);&nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; }&nbsp; &nbsp; @Override&nbsp; &nbsp; public boolean supports(DocumentationType documentationType) {&nbsp; &nbsp; &nbsp; &nbsp; return pluginDoesApply(documentationType);&nbsp; &nbsp; }}我以Springfox 的 ApiParamParameterBuilder为例。现在,我可以用我的@GameIdParam@PostMapping("/{gameId}/info")public String play(@GameIdParam @PathVariable int gameId) // ...这种模式可以推广到与一系列自定义速记注释一起工作。它并不漂亮,它引入了另一种间接级别,了解 Springfox Swagger 的人不会熟悉。
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Java