So I have been trying to make my sample Rest API work without using APIGateway. The routing is done by ALB to the lambda. I am new to this kind of setup. I have set up custom filters when initializing the jersey application. I tried to follow the setup as directed in
https://gitlab.com/jamietanna/jersey-servlet-filter-example/-/tree/master/src/main/java/com/amazonaws/serverless/sample/jersey
The LambdaStreamHandler class shows that I have Bearer token in authorization. The input stream does show what I am requesting but when it gets to the registered filter which looks for the AuthToken it fails to find it and I get unauthorized.
{
"requestContext": {
"elb": {
"targetGroupArn": "arn:aws:elasticloadbalancing:us-east-1:`account`:targetgroup/`targetGroupId`/`id`"
}
},
"httpMethod": "GET",
"path": "/api/1/users",
"queryStringParameters": {
"type": "default"
},
"headers": {
"accept": "*/*",
"accept-encoding": "gzip, deflate, br",
"authorization": "Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c",
"cache-control": "no-cache",
"connection": "keep-alive",
"host": "localhost:54321",
"postman-token": "44a40191-889e-4059-8e7d-0b57a00c403b",
"user-agent": "PostmanRuntime/7.29.0",
"x-amzn-trace-id": "Root=1-628e81cb-0b7bcdb36837c59b47862384",
"x-forwarded-for": "104.1.102.155",
"x-forwarded-port": "443",
"x-forwarded-proto": "https"
},
"body": "",
"isBase64Encoded": false
}
The filter I have setup looks like
public class AuthFilter implements Filter {
public AuthFilter() {
}
@Override
public void init(final FilterConfig arg0) throws ServletException {
}
@Override
public void destroy() {
}
@Override
public void doFilter(final ServletRequest request, final ServletResponse response, final FilterChain filterChain)
throws IOException, ServletException {
final HttpServletRequest httpReq = request instanceof HttpServletRequest ? (HttpServletRequest) request : null;
final HttpServletResponse httpResp = response instanceof HttpServletResponse ? (HttpServletResponse) response : null;
if (httpReq == null || httpResp == null) {
Log.warn("No http request or response found");
return;
}
StringBuilder headers = new StringBuilder();
Iterator<String> it = httpReq.getHeaderNames().asIterator();
while (it.hasNext()) {
headers.append(it.next());
headers.append(" ");
}
StringBuilder params = new StringBuilder();
Iterator<String> it2 = httpReq.getParameterNames().asIterator();
while(it2.hasNext()) {
headers.append(it2.next());
headers.append(" ");
}
String log = "\n" +
"--------------------------------------------------" + "\n" +
"Received request with pathInfo: " + httpReq.getPathInfo() + "\n" +
"---queryString: " + httpReq.getQueryString() + "\n" +
"---URI: " + httpReq.getRequestURI() + "\n" +
"---parameterMap: " + httpReq.getParameterMap() + "\n" +
"---headerNames: " + it + "\n" +
"---method: " + httpReq.getMethod() + "\n" +
"---translatedPath: " + httpReq.getPathTranslated() + "\n" +
"---params: " + it2 + "\n" +
"---servletPath: " + httpReq.getServletPath() + "\n" +
"--------------------------------------------------" + "\n";
Log.info(log);
// if it's a pre-flight request, then let the request pass through
if (httpReq.getMethod().equals("OPTIONS")) {
logger.warn("Ignoring preFlight request");
filterChain.doFilter(httpReq, httpResp);
return;
}
final String authToken = httpReq.getHeader("Authorization");
if (Strings.isNullOrEmpty(authToken) || !authToken.startsWith("Bearer")) {
Log.info("AuthToken not found hence unauthorized!!");
HttpUtils.sendErrorResponse(httpResp, Status.UNAUTHORIZED);
return;
}
final TokenVerifier verifier = new TokenVerifier();
try {
final TokenInfo bti = verifier.extractAndVerifyToken(httpReq, false);
final AuthInfo authInfo = verifier.getAuthInfo(bti.getToken());
if (!Permissions.hasViewAccess(authInfo) && !Permissions.hasWriteAccess(authInfo)) {
HttpUtils.sendErrorResponse(httpResp, Status.FORBIDDEN, "User does not have permission.");
}
httpReq.setAttribute("authInfo", authInfo);
httpReq.setAttribute("token", authToken.replace("Bearer ", ""));
filterChain.doFilter(httpReq, httpResp);
} catch (IllegalAccessException | TokenAuthenticationException e) {
HttpUtils.sendErrorResponse(httpResp, Status.UNAUTHORIZED);
}
}
}
The log entry I see is
--------------------------------------------------
Received request with pathInfo: /api/1/users
---queryString: null
---URI: /api/1/users
---parameterMap:
{}
---headerNames:
---method: GET
---translatedPath: null
---params:
---servletPath:
--------------------------------------------------
I am not seeing the authorization header anywhere or any header for that matter in the AWSProxyRequest class. Can you tell me what I am doing wrong here.