如何获取带注释的方法结果?

时间:2015-07-21 06:59:42

标签: java spring spring-mvc spring-annotations

我想获取方法的结果,然后将它们排入ActiveMQ。因此,我决定创建一个注释(比如@Enqueue(“My_Queue”))来获取结果并将其发送到My_Queue。

cabal test

以下是注释本身:

@ResponseBody
@Enqueue("My_Queue")
@RequestMapping("/list")
public MyClass list() {
  return myService.getAll();
}

那么我该怎么做才能创建这样的注释(请说A-Z)?

3 个答案:

答案 0 :(得分:3)

方面一定是你要找的东西。既然你正在使用Spring,请看看Spring AOP:http://docs.spring.io/spring/docs/current/spring-framework-reference/html/aop.html

使用建议@AfterReturning和切入点@annotation(package.to.Enqueue),每次调用@Enqueue注释的方法时,您都可以访问返回的值:http://docs.spring.io/spring/docs/current/spring-framework-reference/html/aop.html#aop-advice-after-returning

然后,您就可以将其发送到队列中。

答案 1 :(得分:2)

您需要在下面编写代码snap。

 Class aClass = MyClass.class;
 Annotation[] annotations = aClass.getAnnotations();

for(Annotation annotation : annotations){
    if(annotation instanceof Enqueue ){
        Enqueue myAnnotation = (Enqueue ) annotation;
        if(myAnnotation.name().equals("Enqueue")){
         //do your work
         System.out.println("value: " + myAnnotation.value());
        }
    }
}

更新:

  

注释不是"触发" ...您必须编写代码来查找其存在并采取措施。

     

"代码"可以在运行时执行,但更常见的是在编译时使用注释处理工具执行,以更改源以注入适用于注释的额外(通常是交叉)代码。

参考链接:https://stackoverflow.com/a/13040933/1326692

更新:通过查看您的评论,您似乎想要一些动态的东西,您可以在注释方法调用之前完成您的工作。为此,您需要创建如下所示的代理。

1:MyInterface.java

public interface MyInterface {
  void test();
}

2:Enqueue.java

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Enqueue {

  public String value() default "General_Message_Queue";
}

第3。 MyClass.java

import java.lang.reflect.Proxy;

public class MyClass implements MyInterface {

  @Enqueue
  public void test() {
    System.out.println("Inside test");
  }

  public static void main(String[] args) throws IllegalArgumentException, InstantiationException, IllegalAccessException {
    MyInterface test = (MyInterface) getProxyInstance(MyClass.class, MyInterface.class);
    test.test();
  }

  @SuppressWarnings("rawtypes")
  public static Object getProxyInstance(Class clazz, Class interfaze) throws IllegalArgumentException,
      InstantiationException, IllegalAccessException {
    Object proxy =
        Proxy.newProxyInstance(MethodInvocationHandler.class.getClassLoader(),
            new Class[] {interfaze}, new MethodInvocationHandler(clazz.newInstance()));
    return proxy;
  }
}

4:MethodInvocationHandler.java

import java.lang.annotation.Annotation;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;

public class MethodInvocationHandler implements InvocationHandler {
  private Object proxied;

  public MethodInvocationHandler(Object proxied) {
    this.proxied = proxied;
  }

  @Override
  public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
    Method m = proxied.getClass().getMethod(method.getName(), method.getParameterTypes());
    if (m.isAnnotationPresent(Enqueue.class)) {

      // do your work here
      System.out.println("Before " + m.getName() + " call..!");

      /** also you can get annotation and access it's properties..! */
      Enqueue annotation = m.getAnnotation(Enqueue.class);
      System.out.println("name: " + annotation.value());

    }

    /** also you can get all the annotations if you want */
    Annotation[] annotations = method.getDeclaredAnnotations();
    for (Annotation annotation : annotations) {
      // do your annotation specific work here like this,
      if (annotation instanceof Enqueue) {
        // do your work here.
      }
    }
    return method.invoke(proxied, args);
  }
}

我希望它有所帮助:)

答案 2 :(得分:2)

如果您使用的是spring-aop或任何第三方aop库,那么您可以应用以下代码。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq;

namespace ConsoleApplication2
{
    class Program
    {
        static void Main(string[] args)
        {
            string input =
                "<resource Name=\"src/samp1.js\" checkin=\"true\">" +
                    "<metrics>" +
                      "<metric Metric_Domain=\"Size\" Name=\"Lines\" Value=\"8260.0\" />" +
                      "<metric Metric_Domain=\"Size\" Name=\"Generated Lines\" Value=\"\" />" +
                    "</metrics>" +
                    "</resource>" +
                  "<resource Name=\"src/samp2.js\" checkin=\"true\">" +
                        "<metrics>" +
                          "<metric Metric_Domain=\"Size\" Name=\"Lines\" Value=\"860.0\" />" +
                          "<metric Metric_Domain=\"Size\" Name=\"Generated Lines\" Value=\"\" />" +
                        "</metrics>" +
                  "</resource>" +
                  "<resource Name=\"src/samp3.js\" checkin=\"true\">" +
                            "<metrics>" +
                              "<metric Metric_Domain=\"Size\" Name=\"Lines\" Value=\"260.0\" />" +
                              "<metric Metric_Domain=\"Size\" Name=\"Generated Lines\" Value=\"\" />" +
                            "</metrics>" +
                  "</resource>";

            input = "<Root>" + input + "</Root>";

            XDocument doc = XDocument.Parse(input);

            var results = doc.Descendants("resource").Select(x => new {
                name = x.Attribute("Name").Value,
                checkin = x.Attribute("checkin").Value,
                metric = x.Descendants("metric").Select(y => new {
                    metric_Domain = y.Attribute("Metric_Domain").Value,
                    name = y.Attribute("Name").Value,
                    value = y.Attribute("Value").Value
                }).ToList()

            }).ToList();
        }

    }
}
​

如果您的方法具有不同的返回类型,那么您必须为特定的返回类型编写更多的aop建议。