【问题标题】:Java EE - How to inject method parameter on method with custom annotationJava EE - 如何在具有自定义注释的方法上注入方法参数
【发布时间】:2016-12-16 10:02:11
【问题描述】:

假设我在 Java EE / EJB / JAX-RS 中有以下代码:

@POST
@Path("some/path")
@MyAnnotation
public MyResponse createActivation(MyRequest request, CustomValue value) {
   // ...
}

如何检查是否存在自定义@MyAnnotation 注释并在存在注释的情况下根据某些请求上下文参数填充CustomValue value 方法参数?

注意:我已经在 Spring 中使用 HandlerInterceptorAdapterHandlerMethodArgumentResolver 获得了此代码。现在我需要在没有 Spring 的情况下做同样的事情。我已经发现了ContainerRequestFilter 并使用它来检查注释,但现在我正在努力注入方法参数。

【问题讨论】:

    标签: java jakarta-ee jersey jax-rs jersey-2.0


    【解决方案1】:

    自定义方法参数注入的处理方式与普通(即字段、构造函数)注入略有不同。对于 Jersey,这需要实现 ValueFactoryProvider。对于您的情况,它看起来像

    public class MyAnnotationParamValueProvider implements ValueFactoryProvider {
    
        @Inject
        private ServiceLocator locator;
    
        @Override
        public Factory<?> getValueFactory(Parameter parameter) {
            if (parameter.getAnnotation(MyAnnotation.class) != null
                    && parameter.getRawType() == CustomValue.class) {
                final Factory<CustomValue> factory
                        = new AbstractContainerRequestValueFactory<CustomValue>() {
                    @Override
                    public CustomValue provide() {
                        final ContainerRequest request = getContainerRequest();
                        final String value = request.getHeaderString("X-Value");
                        return new CustomValue(value);
                    }
                };
                locator.inject(factory);
                return factory;
            }
            return null;
        }
    
        @Override
        public PriorityType getPriority() {
            return Priority.NORMAL;
        }
    }
    

    那你需要注册ResourceConfig

    public class AppConfig extends ResourceConfig {
        public AppConfig() {
             register(new AbstractBinder() {
                  @Override
                  protected void configure() {
                      bind(MyAnnotationParamValueProvider.class)
                           .to(ValueFactoryProvider.class)
                           .in(Singleton.class);
                  }
             });
        }
    }
    

    查看this Gist中的完整示例

    另请参阅:

    【讨论】:

    • 感谢您的回答! :) 如果没有 ResourceConfig 类,有什么方法可以做到这一点,例如使用注释?我必须管理,使用 Swift 让我变得柔软......:D
    • 所以您使用的是 web.xml(和包扫描)?如果是这样,请查看this post
    • 不,没有 web.xml... 也没有包扫描。但是基于this post,我相信包扫描也可以在代码中配置——我会试一试。 :) 谢谢!
    • 那你是如何配置应用程序的呢?使用标准 JAX-RS Application 类和 @ApplicationPath?
    • 我链接到的帖子,您可以使用相同的解决方案,使用Feature。如果您有一个空的Application 子类,则类路径扫描将获取@Provider 注释。否则,您需要在 Application 类中注册该功能
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-05-22
    • 2020-04-24
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多