Skip to content

Commit

Permalink
Renaming some modules
Browse files Browse the repository at this point in the history
  • Loading branch information
muhamadto committed Mar 25, 2024
1 parent 4ffa483 commit 336218b
Show file tree
Hide file tree
Showing 11 changed files with 293 additions and 106 deletions.
209 changes: 156 additions & 53 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -77,17 +77,34 @@ $ ./mvnw -ntp clean verify -U
$ curl --location --request POST 'http://localhost:8080' \
--header 'Content-Type: application/json' \
--data-raw '{
"body": "{ \"name\": \"CoffeeBeans\" }"
"httpMethod": "POST",
"body": "{ \"env\": \"production\", \"costCentre\": \"1234\", \"applicationName\": \"some-app\", \"items\": { \"GITHUB_TOKEN\": \"WOAH\", \"AWS_ACCESS_KEY_ID\": \"OMG\", \"AWS_SECRET_ACCESS_KEY\": \"OH NO\" } }"
}'
```
```shell
curl --location --request POST 'http://localhost:8080' \
--header 'Content-Type: application/json' \
--data-raw '{
"httpMethod": "GET",
"pathParameters": {
"proxy": "production-1234-someapp"
}
}'
```

The service responds
```json
[
{
"name": "CoffeeBeans",
"saved": true
}
]
{
"id": "production1234someapp",
"env": "production",
"costCentre": "1234",
"applicationName": "some-app",
"items": {
"GITHUB_TOKEN": "WOAH",
"AWS_ACCESS_KEY_ID": "OMG",
"AWS_SECRET_ACCESS_KEY": "OH NO"
}
}
```

### Github action
Expand Down Expand Up @@ -150,67 +167,151 @@ and the following trust relationship
"Version": "2012-10-17",
"Statement": [
{
"Sid": "ECRPermissions",
"Sid": "S3Permissions",
"Effect": "Allow",
"Action": "s3:GetObject",
"Resource": [
"arn:aws:s3:::cdk-cbcore-assets-718055627712-ap-southeast-2",
"arn:aws:s3:::cdk-cbcore-assets-718055627712-ap-southeast-2/*"
]
},
{
"Sid": "AGWPermissions",
"Effect": "Allow",
"Action": [
"ecr:CreateRepository",
"ecr:DeleteRepository",
"ecr:SetRepositoryPolicy",
"ecr:DescribeRepositories"
"apigateway:POST",
"apigateway:DELETE",
"apigateway:GET",
"apigateway:PATCH",
"apigateway:PUT"
],
"Resource": "arn:aws:ecr:{aws-region}:{aws-account-number}:repository/cdk-{qualifier}-container-assets-{aws-account-number}-{aws-region}"
"Resource": [
"arn:aws:apigateway:ap-southeast-2::/restapis",
"arn:aws:apigateway:ap-southeast-2::/restapis/*",
"arn:aws:apigateway:ap-southeast-2::/account",
"arn:aws:apigateway:ap-southeast-2::/tags/arn:aws:apigateway:ap-southeast-2::/restapis/*"
]
},
{
"Sid": "IAMPermissions",
"Sid": "SNSPermissions",
"Effect": "Allow",
"Action": [
"iam:GetRole",
"iam:CreateRole",
"iam:DeleteRole",
"iam:AttachRolePolicy",
"iam:PutRolePolicy",
"iam:DetachRolePolicy",
"iam:DeleteRolePolicy"
"SNS:CreateTopic",
"SNS:DeleteTopic",
"SNS:Subscribe",
"SNS:GetTopicAttributes",
"SNS:ListSubscriptionsByTopic",
"SNS:Unsubscribe",
"SNS:TagResource",
"SNS:UntagResource"
],
"Resource": [
"arn:aws:iam::{aws-account-number}:role/cdk-{qualifier}-lookup-role-{aws-account-number}-{aws-region}",
"arn:aws:iam::{aws-account-number}:role/cdk-{qualifier}-file-publishing-role-{aws-account-number}-{aws-region}",
"arn:aws:iam::{aws-account-number}:role/cdk-{qualifier}-image-publishing-role-{aws-account-number}-{aws-region}",
"arn:aws:iam::{aws-account-number}:role/cdk-{qualifier}-cfn-exec-role-{aws-account-number}-{aws-region}",
"arn:aws:iam::{aws-account-number}:role/cdk-{qualifier}-deploy-role-{aws-account-number}-{aws-region}"
"arn:aws:sqs:ap-southeast-2:718055627712:SpringNativeAwsFunctionStack-LambdaDeadLetterTopic*"
]
},
{
"Sid": "S3Permissions",
"Sid": "SQSPermissions",
"Effect": "Allow",
"Action": [
"s3:PutBucketPublicAccessBlock",
"s3:CreateBucket",
"s3:DeleteBucketPolicy",
"s3:PutEncryptionConfiguration",
"s3:GetEncryptionConfiguration",
"s3:PutBucketPolicy",
"s3:DeleteBucket",
"s3:PutBucketVersioning"
"sqs:GetQueueAttributes",
"sqs:CreateQueue",
"sqs:DeleteQueue",
"sqs:GetQueueUrl",
"sqs:SetQueueAttributes",
"sqs:ListQueues"
],
"Resource": [
"arn:aws:s3:::{qualifier}-cdk-bucket"
"arn:aws:sqs:ap-southeast-2:718055627712:SpringNativeAwsFunctionStack-LambdaDeadLetterQueue*"
]
},
{
"Sid": "LambdaPermissions",
"Effect": "Allow",
"Action": [
"lambda:GetFunction",
"lambda:ListFunctions",
"lambda:DeleteFunction",
"lambda:CreateFunction",
"lambda:TagResource",
"lambda:AddPermission",
"lambda:RemovePermission",
"lambda:PutFunctionEventInvokeConfig",
"lambda:UpdateFunctionEventInvokeConfig",
"lambda:DeleteFunctionEventInvokeConfig",
"lambda:UpdateFunctionCode",
"lambda:ListTags",
"lambda:UpdateFunctionConfiguration"
],
"Resource": [
"arn:aws:lambda:ap-southeast-2:718055627712:function:SpringNativeAwsFunctionStack*"
]
},
{
"Sid": "SSMPermissions",
"Effect": "Allow",
"Action": [
"ssm:DeleteParameter",
"ssm:AddTagsToResource",
"ssm:GetParameters",
"ssm:PutParameter"
"ssm:GetParameters"
],
"Resource": [
"arn:aws:ssm:ap-southeast-2:718055627712:parameter/cdk-bootstrap/cbcore/version"
]
},
{
"Sid": "DynamoDBPermissions",
"Effect": "Allow",
"Action": [
"dynamodb:DescribeTable",
"dynamodb:CreateTable",
"dynamodb:DeleteTable",
"dynamodb:TagResource",
"dynamodb:UntagResource",
"dynamodb:ListTagsOfResource",
"dynamodb:DescribeTimeToLive",
"dynamodb:DescribeContributorInsights",
"dynamodb:DescribeContinuousBackups",
"dynamodb:DescribeKinesisStreamingDestination"
],
"Resource": [
"arn:aws:dynamodb:ap-southeast-2:718055627712:table/secrets",
"arn:aws:dynamodb:ap-southeast-2:718055627712:table/SpringNativeAwsFunction*"
]
},
{
"Sid": "IAMPermissions",
"Effect": "Allow",
"Action": [
"iam:PassRole",
"iam:GetRole",
"iam:GetRolePolicy",
"iam:CreateRole",
"iam:PutRolePolicy",
"iam:DeleteRole",
"iam:DeleteRolePolicy",
"iam:AttachRolePolicy",
"iam:DetachRolePolicy"
],
"Resource": [
"arn:aws:iam::718055627712:role/SpringNativeAwsFunction*"
]
},
{
"Sid": "CFNPermissions",
"Effect": "Allow",
"Action": "cloudformation:DescribeStacks",
"Resource": "arn:aws:cloudformation:ap-southeast-2:718055627712:stack/cbcore-example-function-dev-stack/*"
},
{
"Sid": "ApplicationAutoscalingPermissions",
"Effect": "Allow",
"Action": [
"application-autoscaling:DeregisterScalableTarget"
],
"Resource": "arn:aws:ssm:{aws-region}:{aws-account-number}:parameter/cdk-bootstrap/{qualifier}/version"
"Resource": [
"arn:aws:application-autoscaling:ap-southeast-2:718055627712:scalable-target/*"
]
}
]
}
```
}```

4. Create an IAM managed policy `CoffeebeansCoreCdkExecutionAccess` to be used
by `cdk-{qualifier}-cfn-exec-role-{aws-account-number}-{aws-region}` which is gonna be created by
Expand Down Expand Up @@ -351,16 +452,18 @@ Now that the setup is done you can deploy to AWS.
environment.
2. Test via curl
```shell
$ curl --location --request POST 'https://{api-id}.execute-api.ap-southeast-2.amazonaws.com/dev/name' \
--header 'Content-Type: application/json' \
--data-raw '{
"name": "CoffeeBeans"
$ curl --location --request POST 'https://lmk0qo0xrl.execute-api.ap-southeast-2.amazonaws.com/dev/' \
--header 'Content-Type: application/json' \
--data-raw '{
"env": "production",
"costCentre": "1234",
"applicationName": "some-app",
"items": {
"GITHUB_TOKEN": "WOAH",
"AWS_ACCESS_KEY_ID": "OMG",
"AWS_SECRET_ACCESS_KEY": "OH NO"
}
}'
```
3. Et voila! It runs with 500 ms for cold start.

```shell
curl --location --request POST 'https://lmk0qo0xrl.execute-api.ap-southeast-2.amazonaws.com/dev/
--header 'Content-Type: application/json' \
--data-raw '{ "env": "production", "costCentre": "1234", "applicationName": "some-app", "items": [ { "key": "GITHUB_TOKEN", "value": "WOAH" }, { "key": "AWS_ACCESS_KEY_ID", "value": "OMG" }, { "key": "AWS_SECRET_ACCESS_KEY", "value": "OH, NO" } ] }'
```

2 changes: 1 addition & 1 deletion docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ services:
'
function package_spring_native_function() {
if [ "$$BUILD_ARTIFACT" = "true" ]; then
./mvnw -ntp clean -Pnative -DskipTests native:compile package -pl "$$FUNCTION_NAME"
./mvnw -ntp clean -Pnative -DskipTests native:compile package -pl "$$FUNCTION_NAME" --settings /home/worker/.m2/settings-nonqantas.xml
else
print_info_message "plain" "BUILD_ARTIFACT environment variable is not set. Skipping Maven build."
fi
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,8 @@
public final class Application extends AbstractApp {
private static final String ENVIRONMENT_NAME_DEV = "dev";
private static final String ENVIRONMENT_NAME_PRD = "prd";


private static final String LAMBDA_CODE_PATH = "spring-native-aws-service/target/spring-native-aws-service-native-zip.zip";

public static void main(final String... args) {
Expand Down
2 changes: 1 addition & 1 deletion spring-native-aws-service/src/assembly/native.xml
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@
<useDefaultExcludes>true</useDefaultExcludes>
<fileMode>0775</fileMode>
<includes>
<include>spring-native-aws-function</include>
<include>spring-native-aws-service</include>
</includes>
</fileSet>
</fileSets>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,12 @@
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.exc.InvalidDefinitionException;
import java.util.Map;
import java.util.Set;
import lombok.extern.slf4j.Slf4j;
import org.springframework.http.HttpMethod;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RestControllerAdvice;
import org.springframework.web.server.MethodNotAllowedException;

@Slf4j
@RestControllerAdvice
Expand All @@ -27,6 +30,25 @@ public APIGatewayProxyResponseEvent handleException(
+ " }");
}

@ExceptionHandler(MethodNotAllowedException.class)
public APIGatewayProxyResponseEvent handleException(
final MethodNotAllowedException e,
final APIGatewayProxyRequestEvent request) {
log.error("Error processing request: {}", e.getMessage());

final Set<HttpMethod> supportedMethods = e.getSupportedMethods();

return new APIGatewayProxyResponseEvent()
.withStatusCode(405)
.withHeaders(Map.of("X-Requested-Id", request.getRequestContext().getRequestId()))
.withBody(
("{\n"
+ "\"message\": \"Method not allowed. Supported methods [%s]\",\n"
+ " \"errorCode\": \"METHOD_NOT_ALLOWED\n"
+ " }").formatted(
supportedMethods));
}

@ExceptionHandler(InvalidDefinitionException.class)
public APIGatewayProxyResponseEvent handleException(
final InvalidDefinitionException e,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,10 +23,6 @@ public class Secret implements Serializable {

private Map<String, String> items;

public String getPartitionKey() {
return env + costCentre + applicationName;
}

public static Secret of(final com.coffeebeans.springnativeawslambda.model.Secret secretModel) {
final String env = secretModel.getEnv();
final String costCentre = secretModel.getCostCentre();
Expand Down
Loading

0 comments on commit 336218b

Please sign in to comment.