So I created a custom AuthenticationFilter for a Jersey Rest service. Locally it deploys and works as intended but when deployed to our actual test server I get the below error when starting Wildfly server.
Caused by: A MultiException has 3 exceptions. They are:
1. java.lang.IllegalStateException: A descriptor SystemDescriptor( implementation=org.glassfish.jersey.server.internal.process.ServerProcess>ingBinder$UriRoutingContextFactory
contracts={org.glassfish.jersey.server.ExtendedUriInfo,javax.ws.rs.core.UriInfo,javax.ws.rs.container.ResourceInfo}
scope=org.glassfish.jersey.process.internal.RequestScoped
qualifiers={}
descriptorType=PROVIDE_METHOD
descriptorVisibility=NORMAL
metadata=
rank=0
loader=org.glassfish.hk2.utilities.binding.AbstractBinder$2@19fb4349
proxiable=true
proxyForSameScope=false
analysisName=null
id=16
locatorId=5
identityHashCode=481594768
reified=true) requires a proxy, but the proxyable library is not on the classpath
2. java.lang.IllegalArgumentException: While attempting to resolve the dependencies of com.lanyon.rest.service.filters.AuthenticationFilter errors were found
3. java.lang.IllegalStateException: Unable to perform operation: resolve on com.lanyon.rest.service.filters.AuthenticationFilter
Caused by: java.lang.IllegalStateException: A descriptor SystemDescriptor(
implementation=org.glassfish.jersey.server.internal.process.ServerProcess>ingBinder$UriRoutingContextFactory
contracts={org.glassfish.jersey.server.ExtendedUriInfo,javax.ws.rs.core.UriInfo,javax.ws.rs.container.ResourceInfo}
scope=org.glassfish.jersey.process.internal.RequestScoped
qualifiers={}
descriptorType=PROVIDE_METHOD
descriptorVisibility=NORMAL
metadata=
rank=0
loader=org.glassfish.hk2.utilities.binding.AbstractBinder$2@19fb4349
proxiable=true
proxyForSameScope=false
analysisName=null
id=16
locatorId=5
identityHashCode=481594768
reified=true) requires a proxy, but the proxyable library is not on the classpath"}}}}
Here is the Auth filter:
@Provider
public class AuthenticationFilter implements javax.ws.rs.container.ContainerRequestFilter {
private static final String AUTHORIZATION_PROPERTY = "Authorization";
private static final String AUTHENTICATION_SCHEME = "Basic";
private static final Response ACCESS_DENIED = Response.status(Response.Status.UNAUTHORIZED)
.entity("Access Denied").build();
private static final Response ACCESS_FORBIDDEN = Response.status(Response.Status.FORBIDDEN)
.entity("Forbidden").build();
private static final String WS_CREDENTIALS_KEY = "DEMAND_WEBSERVICE_CREDENTIALS";
private static final String DEFAULT_DAO_BEAN_NAME = "exchangeDefaultsDAO";
@Context
private ResourceInfo resourceInfo;
@Override
public void filter(ContainerRequestContext requestContext) {
Method method = getResourceMethod();
if (isAnnotationPresent(method, PermitAll.class)) {
return;
}
if (isAnnotationPresent(method, DenyAll.class)) {
requestContext.abortWith(ACCESS_FORBIDDEN);
return;
}
final List<String> authorization = getAuthorizationHeaders(requestContext);
if (authorization == null || authorization.isEmpty()) {
requestContext.abortWith(ACCESS_DENIED);
return;
}
String encodedUserPassword = authorization.get(0).replaceFirst(AUTHENTICATION_SCHEME + " ", "");
final String authToken = new String(encodedUserPassword.getBytes());
if (isAnnotationPresent(method, RolesAllowed.class)) {
RolesAllowed rolesAnnotation = getRolesAllowedAnnotation(method);
Set<String> rolesSet = new HashSet<>(Arrays.asList(rolesAnnotation.value()));
if (!isUserAllowed(authToken, rolesSet)) {
requestContext.abortWith(ACCESS_DENIED);
return;
}
}
}
private boolean isUserAllowed(final String authToken, final Set<String> rolesSet) {
String[] webServiceCredentials = getWebServiceCredentials();
if (webServiceCredentials.length != 2) {
return false;
}
return authToken.equals(webServiceCredentials[0]) && rolesSet.contains(webServiceCredentials[1]);
}
private String[] getWebServiceCredentials() {
return getExchangeDefaultsBean().getDefault(WS_CREDENTIALS_KEY).split("\\|");
}
private Method getResourceMethod() {
return resourceInfo.getResourceMethod();
}
private List<String> getAuthorizationHeaders(ContainerRequestContext requestContext) {
final MultivaluedMap<String, String> headers = requestContext.getHeaders();
final List<String> authorization = headers.get(AUTHORIZATION_PROPERTY);
return authorization;
}
private boolean isAnnotationPresent(Method method, Class<? extends Annotation> annotation) {
return method.isAnnotationPresent(annotation);
}
private RolesAllowed getRolesAllowedAnnotation(Method method) {
return method.getAnnotation(RolesAllowed.class);
}
private ExchangeDefaultsDAO getExchangeDefaultsBean() {
return (ExchangeDefaultsDAO)ApplicationContextProvider.getApplicationContext().getBean(DEFAULT_DAO_BEAN_NAME);
}
}
Then the Jersey Application:
public class JerseyApplication extends ResourceConfig {
public JerseyApplication() {
register(AuthenticationFilter.class);
register(TestAPIService.class);
}
}
Finally the Rest service:
@Path("/somepathname")
public class TestAPIService {
@RolesAllowed("API_ADMIN")
@GET
@Produces(MediaType.TEXT_PLAIN)
public Response getRejectReasons() {
return Response.status(Response.Status.OK).entity("Working as expected!").build();
}
}
I have added javaassist to my classpath but that did nothing. Any help you can provide would be greatly appreciated.
Cheers!