JAX-RS Name binding specification allows to have certain filter(s) executed only for a specific resource method(s).
To achieve name binding, we need to define an annotation (say A), which should be meta-annotated with @NameBinding annotation. Then to bind filters and resource methods together, we need to use our annotation A at both places.
Let's see an example to understand name binding.
Example
Defining the NameBinding:
@NameBinding
@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(value = RetentionPolicy.RUNTIME)
public @interface Logged {
}
Binding Resource and Filter
Our filter:
@Provider
@Logged
public class LogFilter implements ContainerRequestFilter, ContainerResponseFilter {
@Override
public void filter(ContainerRequestContext reqContext) throws IOException {
System.out.println("-- req info --");
UriInfo uriInfo = reqContext.getUriInfo();
log(uriInfo, reqContext.getHeaders());
}
@Override
public void filter(ContainerRequestContext reqContext,
ContainerResponseContext resContext) throws IOException {
System.out.println("-- res info --");
UriInfo uriInfo = reqContext.getUriInfo();
log(uriInfo, resContext.getHeaders());
}
private void log(UriInfo uriInfo, MultivaluedMap<String, ?> headers) {
System.out.println("Path: " + uriInfo.getPath());
headers.entrySet().forEach(h -> System.out.println(h.getKey() + ": " + h.getValue()));
}
}
The JAX-RS resource:
@Path("/customers")
public class MyResource {
@GET
public String getAllCustomers() {
System.out.println("in getAllCustomers()");
return "dummy-response for all customers";
}
@Logged
@GET
@Path("{id}")
public String getCustomerById(@PathParam("id") String id) {
System.out.println("in getCustomerById()");
return "dummy-response for customer " + id;
}
}
To try examples, run embedded tomcat (configured in pom.xml of example project below):
mvn tomcat7:run-war
Output
Using HTTPie to access the resource:
Server output:
in getAllCustomers()
Server output:
-- req info --
Path: customers/2
host: [localhost:8080]
connection: [keep-alive]
accept-encoding: [gzip, deflate]
accept: [*/*]
user-agent: [HTTPie/0.9.9]
in getCustomerById()
-- res info --
Path: customers/2
Content-Type: [text/plain]
As seen in above two outputs, the LogFilter only got executed for the URI '/customers/1' (where we used @Logged).
Example ProjectDependencies and Technologies Used: - jersey-server 2.25.1: Jersey core server implementation.
- jersey-container-servlet 2.25.1: Jersey core Servlet 3.x implementation.
- JDK 1.8
- Maven 3.3.9
|