-
Notifications
You must be signed in to change notification settings - Fork 79
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Lambda proxy is routing and passing decoded path variable when it should be encoded #656
Lambda proxy is routing and passing decoded path variable when it should be encoded #656
Comments
+1 |
I had the exact same issue. Variable values are obviously decoded twice in the context of a Lambda handler, which uses void 'variables should be properly decoded for all HttpRequest types'() {
given:
NettyHttpServer embeddedServer = ApplicationContext.run(NettyHttpServer)
String email = '[email protected]'
String encoded = URLEncoder.encode(email, StandardCharsets.UTF_8.toString())
String path = "/users/${encoded}"
when:
def lambdaContext = new MockLambdaContext()
def awsProxyRequest = new AwsProxyRequestBuilder(path, HttpMethod.GET.toString()).build()
HttpRequest<String> awsHttpRequest = new MicronautAwsProxyRequest<String>(path,
awsProxyRequest,
null,
lambdaContext,
null)
Router router = embeddedServer.getApplicationContext().getBean(Router.class)
UriRouteMatch<?, ?> awsMatch = router.find(awsHttpRequest).findFirst().get()
def nettyRequest = new DefaultHttpRequest(HttpVersion.HTTP_1_1,
io.netty.handler.codec.http.HttpMethod.GET, path)
HttpRequest<String> nettyBasedHttpRequest = new NettyHttpRequest<>(nettyRequest,
Mock(ChannelHandlerContext),
embeddedServer.getEnvironment(),
embeddedServer.getServerConfiguration())
UriRouteMatch<?, ?> nettyMatch = router.find(nettyBasedHttpRequest).findFirst().get()
then:
awsMatch.getVariableValues() == nettyMatch.getVariableValues()
} It seems the root cause is that I believe that fixing this requires an answer to the question: what is the actual contract of |
Yes it should be using PRs welcome! |
@graemerocher do you think we should just override the method in |
Hi, Sorry to bump an old issue. We're having a similar problem to this one but related to query parameters, when used with the AWS API Gateway. Logging has validated that the lambda routine receives a payload with a micronaut-projects/micronaut-core#4464 seems to fix the problem with path segments, but our specific problem is with query parameters. |
Context:
Let's say we have the following user class with its respective controller:
If we run the application purely without using
micronaut-aws
and its Lambda proxy, theUserController.show
action will only find the user[email protected]
if we encode the email. If we don't encode the email Micronaut will interpret the plus sign (+
) as a whitespace (because it automatically decodes the path variable), therefore the user won't be found.That means:
GET - /users/email%2Balias%40gmail.com
works as expected, user will be foundGET - /users/[email protected]
doesn't work, user won't be found (Micronaut will interpret the path parameter asemail [email protected]
)So far everything looks good, we just need to make sure emails are encoded when making the request
Problem:
Once you add the Lambda proxy, as explained in this guide https://guides.micronaut.io/mn-application-aws-lambda-java11-groovy/guide/index.html, the issue starts to happen. The following test for example will fail when it shouldn't:
response.statusCode
will be404
when it should be200
.We can also confirm that there is a bug in there when we encode the email twice like this:
Now the test passes and the user is found.
Another thing to note is that if we change the route mapping in the
UserController
like this:The route won't even match, which makes me believe the problem is happening when routing and also when passing URL parameters.
Application example:
demo.zip
The text was updated successfully, but these errors were encountered: