Note that there are some explanatory texts on larger screens.

plurals
  1. POHow can a Jersey InjectableProvider depend on the AbstractMethod of the resource?
    primarykey
    data
    text
    <p>I have a <code>ResourceFilterFactory</code> that returns a <code>ContainerRequestFilter</code> if an annotation is present on the <code>AbstractMethod</code>.</p> <p>The filter reads a cookie or API key and checks that it is still valid, and sets a property on the request. The check is expensive, so I only want it to occur when the annotation is present.</p> <p>I want to inject the resulting object into my resource, but it seems that injection happens before <code>ResourceFilterFactory</code> filters are applied. If I add the filter to the <code>ResourceConfig</code> as a <code>PROPERTY_CONTAINER_REQUEST_FILTERS</code>, then it happens before the injection, but it does not have access to the <code>AbstractMethod</code>.</p> <p>How do I bridge the gap, so that the filter is applied and the field is injected only if the method has the annotation?</p> <p>My code looks something like this. <code>AuthFilter</code> is called after <code>UserIdProvider</code>, so <code>c.getProperties().get(USER_ID_PROPERTY)</code> is always <code>null</code>.</p> <pre><code>public class AuthFilter implements ContainerRequestFilter { public ContainerRequest filter(ContainerRequest request) { Integer userId = …; // expensive lookup request.getProperties().set(USER_ID_PROPERTY, userId); return request; } } public class AuthFilterFactory implements ResourceFilterFactory { // … public List&lt;ResourceFilter&gt; create(AbstractMethod am) { if (am.isAnnotationPresent(RequireAuth.class) || am.getResource().isAnnotationPresent(RequireAuth.class)) { return Collections.singletonList(new ResourceFilter() { public ContainerRequestFilter getRequestFilter() { return authFilter; } }); } else { return null } } } </code></pre> <p>InjectableProvider:</p> <pre><code>@Provider public class UserIdProvider implements InjectableProvider&lt;UserId, Parameter&gt; { public ComponentScope getScope() { return ComponentScope.PerRequest; } public Injectable&lt;? extends Object&gt; getInjectable(ComponentContext ic, UserId a, final Parameter t) { return new AbstractHttpContextInjectable&lt;Integer&gt;() { public Integer getValue(HttpContext c) { return (Integer) c.getProperties().get(USER_ID_PROPERTY); } } } } </code></pre> <p>Resource:</p> <pre><code>@Path("/user") public class UserResource { @UserId Integer userId; // userId should only be set on this method @GET @RequireAuth public UserDetails get() { // … } // the auth filter should not be called for this method @POST @Path("/login") public String login() { // … } } </code></pre>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload