将动态参数传递给注释 [英] Passing dynamic parameters to an annotation

查看:130
本文介绍了将动态参数传递给注释的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想知道是否有可能将动态值传递给注释属性。

I wonder if there is a possiblity to pass dynamically values to an annotation attribute.

我知道注释不是为了修改而设计的,而是我正在使用< a href =http://docs.jboss.org/hibernate/orm/3.6/reference/en-US/html/filters.html\"rel =nofollow>休眠过滤器和条件是在我的情况下不是静态的。

I know that annotation are not designed to be modified but I'm using Hibernate Filters and condition to be put are not static in my case.

我认为唯一的解决方案是使用librairies,其目的是读取和修改字节代码,如Javassist或 ASM 但如果有另一种解决方案会好得多。

I think that the only solution is to use librairies whose aim is to read and modify byte code such as Javassist or ASM but it would be too much better if there is another solution.

ps:在我的情况下,我应该修改注释(属性的值),但我上面提到的库,允许创建不编辑,这就是为什么我想知道另一个解决方案

ps: The difficulty in my case is that I should modify annotations (attribute's value) but librairies I mentioned above allow to create not to edit that's why I'm wondering for another solution

提前致谢

推荐答案

我不知道它是否与您的框架很好地集成但是我想建议如下:

I don't know if it integrates nicely with your frameworks, but i would like to suggest the following:


  • 创建一个注释,它接收一个实现验证规则的类

  • 创建注释可以接收的界面

  • 为具有规则逻辑的界面创建实现

  • 添加注释到你的模型类

  • 创建一个注释处理器,为每个带注释的字段应用验证

  • Create an annotation which receives a Class that implements the validation rule
  • Create an interface which the annotation can receive
  • Create an implementation for the interface which has the logic for your rule
  • Add the annotations to your model class
  • Create an annotation processor which applies the validation for each annotated field

I在Groovy中编写了以下示例,但使用的是标准Java库和惯用Java。如果有什么不可读的话,请警告我:

I wrote the following example in Groovy, but using standard Java libs and idiomatic Java. Warn me if anything is unreadable:

import java.lang.annotation.*

// Our Rule interface
interface Rule<T> { boolean isValid(T t) }

// Here is the annotation which can receive a Rule class
@Retention(RetentionPolicy.RUNTIME)
@interface Validation { Class<? extends Rule> value() }

// An implementation of our Rule, in this case, for a Person's name
class NameRule implements Rule<Person> {
  PersonDAO dao = new PersonDAO()
  boolean isValid(Person person) {
    Integer mode = dao.getNameValidationMode()
    if (mode == 1) { // Don't hardcode numbers; use enums
      return person.name ==~ "[A-Z]{1}[a-z ]{2,25}" // regex matching
    } else if (mode == 2) {
      return person.name ==~ "[a-zA-Z]{1,25}"
    }
  }
}

在这些声明之后,用法:

After these declarations, the usage:

// Our model with an annotated field
class Person {
  @Validation(NameRule.class)
  String name
}

// Here we are mocking a database select to get the rule save in the database
// Don't use hardcoded numbers, stick to a enum or anything else
class PersonDAO { Integer getNameValidationMode() { return 1 } }

注释的处理:

// Here we get each annotation and process it against the object
class AnnotationProcessor {
  String validate(Person person) {
    def annotatedFields = person.class.declaredFields.findAll { it.annotations.size() > 0 }
    for (field in annotatedFields) {
      for (annotation in field.annotations) {
        Rule rule = annotation.value().newInstance()
        if (! rule.isValid(person)) {
          return "Error: name is not valid"
        }
        else {
          return "Valid"
        }
      }
    }
  }
}

并且测试:

// These two must pass
assert new AnnotationProcessor().validate( 
  new Person(name: "spongebob squarepants") ) == "Error: name is not valid"

assert new AnnotationProcessor().validate( 
  new Person(name: "John doe") ) == "Valid"

另外,看看 GContracts ,它提供了一些有趣的验证通过注释模型。

Also, take a look at GContracts, it provides some interesting validation-through-annotations model.

这篇关于将动态参数传递给注释的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆