How to intercept selective methods and classes in JAX-RS in a container compatible with Java EE 7?

I want to intercept any classor methodsannotated using@Foo

Class level interception:

@Foo
@path("/foo")
public class Attack {...}

Method level interception:

@path("/bar")
public class defend {

@Foo
@GET
public String myMethod(){....}

I want to intercept any class or methods annotated with @Foo, but not other methods or classes. I want to print the entire path or URI before proceeding with the method. One method call completed, I want to print "completed successfully"

This is something similar:

 system.out.println(path) // this is the path the request is made. something like /api/2/imp/foo
   method call happens
   method call finishes
   System.out.println("executed successfully")

My script is different, but this is the main problem I have. I do not want to be implementation specific. There is a way in the Java EE 7 specification to do this using @Postconstruct, @AroundInvoke, etc. But it's really hard for me to put this together.

. (RESTeasy) AcceptByMethod, , .

+4
2

:

@Foo @Interceptor
public class FooInterceptor
{
    @AroundInvoke
    public Object handleFoo(InvocationContext joinPoint) throws Exception
    {
        Method m = joinPoint.getMethod();

        // you can access all annotations on your @Foo-annotated method,
        // not just the @Foo annotation.
        Annotation[] as = m.getDeclaredAnnotations();

        // do stuff before the method call
        ...

        try
        {
            // here you call the actual method
            return joinPoint.proceed();
        }
        finally
        {
            // do stuff after the method call
            ...
        }
    }
}

:

@InterceptorBinding
@Retention(RetentionPolicy.RUNTIME)
@Target({ ElementType.METHOD, ElementType.TYPE })
public @interface Foo
{
    @Nonbinding
    ... // you could add parameters for your annotation, e.g. @Foo(value)
}

:

@Stateless
public class MyService
{
    @Foo("bar")
    public String myWrappedMethod()
    {
        ...
    }
}

myWrappedMethod "" FooInterceptor. , , myWrappedMethod() , .. MyService (, @Inject)

+2

Java EE Tutorial JAX-RS, , jsr339-jaxrs-2.0-final-spec. , .

JAX-RS . , , , , ,

Entity . , .

, , , . , . , , , .

ContainerRequestFilter ContainerResponseFilter ContainerRequestContext ContainerResponseContext , , , UriInfo, .

public interface ContainerResponseFilter {
    void filter(ContainerRequestContext requestContext, 
           ContainerResponseContext responseContext)
}

public interface ContainerRequestFilter {
    void filter(ContainerRequestContext requestContext)
}

. , , , t

public class LoggingFilter implements ContainerRequestFilter,
                                      ContainerResponseFilter {

    private static final Logger logger
            = Logger.getLogger(LoggingFilter.class.getName());

    protected String className;
    protected String methodName;

    public NewLoggingFilter(String className, String methodName) {
        this.className = className;
        this.methodName = methodName;
    }

    @Override
    public void filter(ContainerRequestContext requestContext) 
                                                      throws IOException {
        logger.log(Level.INFO, "Request path: {0}",
                requestContext.getUriInfo().getAbsolutePath().toString());
        logger.log(Level.INFO, "Starting Method: {0}.{1}",
                new Object[]{className, methodName});
    }

    @Override
    public void filter(ContainerRequestContext requestContext,
                       ContainerResponseContext responseContext)
                                                       throws IOException {

        logger.log(Level.INFO, "Finished Method: {0}.{1}",
                                       new Object[]{className, methodName});
    }
}

. . , , LoggingFilter. LogginFilter .

@Provider
public class LoggingBinder implements DynamicFeature {

    @Override
    public void configure(ResourceInfo ri, FeatureContext fc) {
        Class<?> clazz = ri.getResourceClass();
        Method method = ri.getResourceMethod();
        if (method.isAnnotationPresent(Logged.class) 
                || clazz.isAnnotationPresent(Logged.class)) {
            fc.register(new LoggingFilter(clazz.getName(), method.getName()));
        }
    }  
}

, , @Logged ( - @Foo)

@NameBinding
@Retention(RUNTIME)
@Target({METHOD, TYPE})
public @interface Logged {
}

@Path("/log")
public class LogResource {
    @GET
    @Logged
    public Response getLoggingResourceMethod() {
        return Response.ok("Hello Logging Response").build();
    }
}

log

:
Oct 25, 2014 4:36:05 PM jaxrs.stackoverflow.filter.NewLoggingFilter filter
INFO: Request path: http://localhost:8081/rest/log
Oct 25, 2014 4:36:05 PM jaxrs.stackoverflow.filter.NewLoggingFilter filter
INFO: Starting Method: jaxrs.stackoverflow.filter.LogResource.getLoggingResourceMethod
Oct 25, 2014 4:36:05 PM jaxrs.stackoverflow.filter.NewLoggingFilter filter
INFO: Finished Method: jaxrs.stackoverflow.filter.LogResource.getLoggingResourceMethod
Oct 25, 2014 4:36:05 PM jaxrs.stackoverflow.filter.NewLoggingFilter filter
INFO: Method successful.

.

+4

All Articles