Skip to content

Commit 8d18990

Browse files
authored
Merge pull request #815 from jonife/iam
Add support for IAM Authorizers in combination with 2.0 payload
2 parents 79b6d34 + bae6801 commit 8d18990

File tree

3 files changed

+176
-9
lines changed

3 files changed

+176
-9
lines changed

aws-serverless-java-container-core/src/main/java/com/amazonaws/serverless/proxy/model/HttpApiV2AuthorizerMap.java

Lines changed: 28 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -34,16 +34,21 @@
3434
public class HttpApiV2AuthorizerMap extends HashMap<String, Object> {
3535
private static final String JWT_KEY = "jwt";
3636
private static final String LAMBDA_KEY = "lambda";
37+
private static final String IAM_KEY = "iam";
3738
private static final long serialVersionUID = 42L;
3839

3940
public HttpApiV2JwtAuthorizer getJwtAuthorizer() {
40-
return (HttpApiV2JwtAuthorizer)get(JWT_KEY);
41+
return (HttpApiV2JwtAuthorizer) get(JWT_KEY);
4142
}
4243

4344
public Map<String, Object> getLambdaAuthorizerContext() {
4445
return (Map<String, Object>) get(LAMBDA_KEY);
4546
}
4647

48+
public HttpApiV2IamAuthorizer getIamAuthorizer() {
49+
return (HttpApiV2IamAuthorizer) get(IAM_KEY);
50+
}
51+
4752
public boolean isJwt() {
4853
return containsKey(JWT_KEY);
4954
}
@@ -52,10 +57,18 @@ public boolean isLambda() {
5257
return containsKey(LAMBDA_KEY);
5358
}
5459

60+
public boolean isIam() {
61+
return containsKey(IAM_KEY);
62+
}
63+
5564
public void putJwtAuthorizer(HttpApiV2JwtAuthorizer jwt) {
5665
put(JWT_KEY, jwt);
5766
}
5867

68+
public void putIamAuthorizer(HttpApiV2IamAuthorizer iam) {
69+
put(IAM_KEY, iam);
70+
}
71+
5972
public static class HttpApiV2AuthorizerDeserializer extends StdDeserializer<HttpApiV2AuthorizerMap> {
6073
private static final long serialVersionUID = 42L;
6174

@@ -64,18 +77,25 @@ public HttpApiV2AuthorizerDeserializer() {
6477
}
6578

6679
@Override
67-
public HttpApiV2AuthorizerMap deserialize(JsonParser jsonParser, DeserializationContext deserializationContext) throws IOException, JsonProcessingException {
80+
public HttpApiV2AuthorizerMap deserialize(JsonParser jsonParser, DeserializationContext deserializationContext)
81+
throws IOException, JsonProcessingException {
6882
HttpApiV2AuthorizerMap map = new HttpApiV2AuthorizerMap();
6983
JsonNode node = jsonParser.getCodec().readTree(jsonParser);
7084
if (node.has(JWT_KEY)) {
71-
HttpApiV2JwtAuthorizer authorizer = LambdaContainerHandler.getObjectMapper().treeToValue(node.get(JWT_KEY), HttpApiV2JwtAuthorizer.class);
85+
HttpApiV2JwtAuthorizer authorizer = LambdaContainerHandler.getObjectMapper()
86+
.treeToValue(node.get(JWT_KEY), HttpApiV2JwtAuthorizer.class);
7287
map.putJwtAuthorizer(authorizer);
7388
}
7489
if (node.has(LAMBDA_KEY)) {
7590
Map<String, Object> context = LambdaContainerHandler.getObjectMapper().treeToValue(node.get(LAMBDA_KEY),
7691
TypeFactory.defaultInstance().constructMapType(HashMap.class, String.class, Object.class));
7792
map.put(LAMBDA_KEY, context);
7893
}
94+
if (node.has(IAM_KEY)) {
95+
HttpApiV2IamAuthorizer iam_authorizer = LambdaContainerHandler.getObjectMapper()
96+
.treeToValue(node.get(IAM_KEY), HttpApiV2IamAuthorizer.class);
97+
map.putIamAuthorizer(iam_authorizer);
98+
}
7999
// we ignore other, unknown values
80100
return map;
81101
}
@@ -89,14 +109,18 @@ public HttpApiV2AuthorizerSerializer() {
89109
}
90110

91111
@Override
92-
public void serialize(HttpApiV2AuthorizerMap httpApiV2AuthorizerMap, JsonGenerator jsonGenerator, SerializerProvider serializerProvider) throws IOException {
112+
public void serialize(HttpApiV2AuthorizerMap httpApiV2AuthorizerMap, JsonGenerator jsonGenerator,
113+
SerializerProvider serializerProvider) throws IOException {
93114
jsonGenerator.writeStartObject();
94115
if (httpApiV2AuthorizerMap.isJwt()) {
95116
jsonGenerator.writeObjectField(JWT_KEY, httpApiV2AuthorizerMap.getJwtAuthorizer());
96117
}
97118
if (httpApiV2AuthorizerMap.isLambda()) {
98119
jsonGenerator.writeObjectField(LAMBDA_KEY, httpApiV2AuthorizerMap.getLambdaAuthorizerContext());
99120
}
121+
if (httpApiV2AuthorizerMap.isIam()) {
122+
jsonGenerator.writeObjectField(IAM_KEY, httpApiV2AuthorizerMap.get(IAM_KEY));
123+
}
100124
jsonGenerator.writeEndObject();
101125
}
102126
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
package com.amazonaws.serverless.proxy.model;
2+
3+
public class HttpApiV2IamAuthorizer {
4+
public String accessKey;
5+
public String accountId;
6+
public String callerId;
7+
public String cognitoIdentity;
8+
public String principalOrgId;
9+
public String userArn;
10+
public String userId;
11+
12+
public String getAccessKey() {
13+
return accessKey;
14+
}
15+
16+
public String getAccountId() {
17+
return accountId;
18+
}
19+
20+
public String getCallerId() {
21+
return callerId;
22+
}
23+
24+
public String getCognitoIdentity() {
25+
return cognitoIdentity;
26+
}
27+
28+
public String getPrincipalOrgId() {
29+
return principalOrgId;
30+
}
31+
32+
public String getUserArn() {
33+
return userArn;
34+
}
35+
36+
public String getUserId() {
37+
return userId;
38+
}
39+
40+
public void setAccessKey(String accessKey) {
41+
this.accessKey = accessKey;
42+
}
43+
44+
public void setAccountId(String accountId) {
45+
this.accountId = accountId;
46+
}
47+
48+
public void setCallerId(String callerId) {
49+
this.callerId = callerId;
50+
}
51+
52+
public void setCognitoIdentity(String cognitoIdentity) {
53+
this.cognitoIdentity = cognitoIdentity;
54+
}
55+
56+
public void setPrincipalOrgId(String principalOrgId) {
57+
this.principalOrgId = principalOrgId;
58+
}
59+
60+
public void setUserArn(String userArn) {
61+
this.userArn = userArn;
62+
}
63+
64+
public void setUserId(String userId) {
65+
this.userId = userId;
66+
}
67+
68+
}

aws-serverless-java-container-core/src/test/java/com/amazonaws/serverless/proxy/model/HttpApiV2ProxyRequestTest.java

Lines changed: 80 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -129,11 +129,55 @@ public class HttpApiV2ProxyRequestTest {
129129
" \"isBase64Encoded\": false,\n" +
130130
" \"stageVariables\": {\"stageVariable1\": \"value1\", \"stageVariable2\": \"value2\"}\n" +
131131
" }\n";
132+
private static final String IAM_AUTHORIZER = "{\n" +
133+
" \"version\": \"2.0\",\n" +
134+
" \"routeKey\": \"$default\",\n" +
135+
" \"rawPath\": \"/my/path\",\n" +
136+
" \"rawQueryString\": \"parameter1=value1&parameter1=value2&parameter2=value\",\n" +
137+
" \"cookies\": [ \"cookie1\", \"cookie2\" ],\n" +
138+
" \"headers\": {\n" +
139+
" \"Header1\": \"value1\",\n" +
140+
" \"Header2\": \"value2\"\n" +
141+
" },\n" +
142+
" \"queryStringParameters\": { \"parameter1\": \"value1,value2\", \"parameter2\": \"value\" },\n" +
143+
" \"requestContext\": {\n" +
144+
" \"accountId\": \"123456789012\",\n" +
145+
" \"apiId\": \"api-id\",\n" +
146+
" \"authorizer\": { \"iam\": {\n" +
147+
" \"accessKey\": \"AKIAIOSFODNN7EXAMPLE\",\n" +
148+
" \"accountId\": \"123456789012\",\n" +
149+
" \"callerId\": \"AIDACKCEVSQ6C2EXAMPLE\",\n" +
150+
" \"cognitoIdentity\": null,\n" +
151+
" \"principalOrgId\": \"AIDACKCEVSQORGEXAMPLE\",\n" +
152+
" \"userArn\": \"arn:aws:iam::111122223333:user/example-user\",\n" +
153+
" \"userId\": \"AIDACOSFODNN7EXAMPLE2\"\n" +
154+
" }" +
155+
" },\n" +
156+
" \"domainName\": \"id.execute-api.us-east-1.amazonaws.com\",\n" +
157+
" \"domainPrefix\": \"id\",\n" +
158+
" \"http\": {\n" +
159+
" \"method\": \"POST\",\n" +
160+
" \"path\": \"/my/path\",\n" +
161+
" \"protocol\": \"HTTP/1.1\",\n" +
162+
" \"sourceIp\": \"IP\",\n" +
163+
" \"userAgent\": \"agent\"\n" +
164+
" },\n" +
165+
" \"requestId\": \"id\",\n" +
166+
" \"routeKey\": \"$default\",\n" +
167+
" \"stage\": \"$default\",\n" +
168+
" \"time\": \"12/Mar/2020:19:03:58 +0000\",\n" +
169+
" \"timeEpoch\": 1583348638390\n" +
170+
" },\n" +
171+
" \"body\": \"Hello from Lambda\",\n" +
172+
" \"isBase64Encoded\": false,\n" +
173+
" \"stageVariables\": {\"stageVariable1\": \"value1\", \"stageVariable2\": \"value2\"}\n" +
174+
" }\n";
132175

133176
@Test
134177
void deserialize_fromJsonString_authorizerPopulatedCorrectly() {
135178
try {
136-
HttpApiV2ProxyRequest req = LambdaContainerHandler.getObjectMapper().readValue(BASE_PROXY_REQUEST, HttpApiV2ProxyRequest.class);
179+
HttpApiV2ProxyRequest req = LambdaContainerHandler.getObjectMapper().readValue(BASE_PROXY_REQUEST,
180+
HttpApiV2ProxyRequest.class);
137181
assertTrue(req.getRequestContext().getAuthorizer().getJwtAuthorizer().getClaims().containsKey("claim1"));
138182
assertEquals(2, req.getRequestContext().getAuthorizer().getJwtAuthorizer().getScopes().size());
139183
assertEquals(RequestSource.API_GATEWAY, req.getRequestSource());
@@ -146,10 +190,12 @@ void deserialize_fromJsonString_authorizerPopulatedCorrectly() {
146190
@Test
147191
void deserialize_fromJsonString_authorizerEmptyMap() {
148192
try {
149-
HttpApiV2ProxyRequest req = LambdaContainerHandler.getObjectMapper().readValue(NO_AUTH_PROXY, HttpApiV2ProxyRequest.class);
193+
HttpApiV2ProxyRequest req = LambdaContainerHandler.getObjectMapper().readValue(NO_AUTH_PROXY,
194+
HttpApiV2ProxyRequest.class);
150195
assertNotNull(req.getRequestContext().getAuthorizer());
151196
assertFalse(req.getRequestContext().getAuthorizer().isJwt());
152197
assertFalse(req.getRequestContext().getAuthorizer().isLambda());
198+
assertFalse(req.getRequestContext().getAuthorizer().isIam());
153199
} catch (JsonProcessingException e) {
154200
e.printStackTrace();
155201
fail("Exception while parsing request" + e.getMessage());
@@ -159,7 +205,8 @@ void deserialize_fromJsonString_authorizerEmptyMap() {
159205
@Test
160206
void deserialize_fromJsonString_lambdaAuthorizer() {
161207
try {
162-
HttpApiV2ProxyRequest req = LambdaContainerHandler.getObjectMapper().readValue(LAMBDA_AUTHORIZER, HttpApiV2ProxyRequest.class);
208+
HttpApiV2ProxyRequest req = LambdaContainerHandler.getObjectMapper().readValue(LAMBDA_AUTHORIZER,
209+
HttpApiV2ProxyRequest.class);
163210
assertNotNull(req.getRequestContext().getAuthorizer());
164211
assertFalse(req.getRequestContext().getAuthorizer().isJwt());
165212
assertTrue(req.getRequestContext().getAuthorizer().isLambda());
@@ -171,10 +218,38 @@ void deserialize_fromJsonString_lambdaAuthorizer() {
171218
}
172219
}
173220

221+
@Test
222+
void deserialize_fromJsonString_iamAuthorizer() {
223+
try {
224+
HttpApiV2ProxyRequest req = LambdaContainerHandler.getObjectMapper().readValue(IAM_AUTHORIZER,
225+
HttpApiV2ProxyRequest.class);
226+
assertNotNull(req.getRequestContext().getAuthorizer());
227+
assertFalse(req.getRequestContext().getAuthorizer().isJwt());
228+
assertFalse(req.getRequestContext().getAuthorizer().isLambda());
229+
assertTrue(req.getRequestContext().getAuthorizer().isIam());
230+
assertEquals("AKIAIOSFODNN7EXAMPLE",
231+
req.getRequestContext().getAuthorizer().getIamAuthorizer().getAccessKey());
232+
assertEquals("123456789012", req.getRequestContext().getAuthorizer().getIamAuthorizer().getAccountId());
233+
assertEquals("AIDACKCEVSQ6C2EXAMPLE",
234+
req.getRequestContext().getAuthorizer().getIamAuthorizer().getCallerId());
235+
assertNull(req.getRequestContext().getAuthorizer().getIamAuthorizer().getCognitoIdentity());
236+
assertEquals("AIDACKCEVSQORGEXAMPLE",
237+
req.getRequestContext().getAuthorizer().getIamAuthorizer().getPrincipalOrgId());
238+
assertEquals("arn:aws:iam::111122223333:user/example-user",
239+
req.getRequestContext().getAuthorizer().getIamAuthorizer().getUserArn());
240+
assertEquals("AIDACOSFODNN7EXAMPLE2",
241+
req.getRequestContext().getAuthorizer().getIamAuthorizer().getUserId());
242+
} catch (JsonProcessingException e) {
243+
e.printStackTrace();
244+
fail("Exception while parsing request" + e.getMessage());
245+
}
246+
}
247+
174248
@Test
175249
void deserialize_fromJsonString_isBase64EncodedPopulates() {
176250
try {
177-
HttpApiV2ProxyRequest req = LambdaContainerHandler.getObjectMapper().readValue(BASE_PROXY_REQUEST, HttpApiV2ProxyRequest.class);
251+
HttpApiV2ProxyRequest req = LambdaContainerHandler.getObjectMapper().readValue(BASE_PROXY_REQUEST,
252+
HttpApiV2ProxyRequest.class);
178253
assertFalse(req.isBase64Encoded());
179254
req = LambdaContainerHandler.getObjectMapper().readValue(NO_AUTH_PROXY, HttpApiV2ProxyRequest.class);
180255
assertTrue(req.isBase64Encoded());
@@ -207,4 +282,4 @@ void serialize_toJsonString_authorizerPopulatesCorrectly() {
207282
fail("Exception while serializing request" + e.getMessage());
208283
}
209284
}
210-
}
285+
}

0 commit comments

Comments
 (0)