Feb 14, 2023

# AWS CDK + API Gateway and Integrations. A little guide how to.

Danilo Desole

3 minutes read

I’ve been working with CDK and I think is brilliant, the way it lets you define resources and infrastructure using your favorite coding language is awesome, I personally use Python. Sometimes what happens is that CDK takes over a lot of control and creates resources as it thinks is proper… Also, documentation lacks some advanced configuration.

For instance, I come across this [AWS documentation page](https://docs.aws.amazon.com/apigateway/latest/developerguide/integrating-api-with-aws-services-s3.html) to develop a proxy to S3 using API Gateway. I thought to reproduce the same in CDK, but I faced some issues in defining the integrations.

In this post, I’m going to show how I created the API Gateway, the challenges I faced, and how I solved them, with the hope it might help you too!

So let’s start from the beginning.

## Defining REST APIs

To define a REST API you can use the following snippet, in a single row, in CDK, you can define a new set of REST API

```python
my_apig = apig.RestApi(self, "ApigAndS3")
```

## Defining Resources

Now it’s time to define a couple of resources, to be clear our final goal is to create something like the following: `http://myapigateway/bucketName/item` where _bucketName_ and _item_ are placeholder the client will pass along with a request body. Whatever is passed in the body will be saved in _bucketName/item_. Of course, you need to own write permissions on the bucket defined by _bucketName_. Here again, a couple of lines define two resources. Awesome!

## Defining the integration

Here I started to sweat, as defining the integrations per se is not complicated

```python
bucket_integration = apig.AwsIntegration(service="s3", integration_http_method="PUT", path="{bucket}/{object}", region="eu-west-1", options=integration_options)
```

Is the _integration_options_ really hard to define, considering I got the error _apigateway Invalid mapping expression parameter specified: method.request.path._ many, many, times… I couldn’t find an answer online and even the AWS Post [here](https://aws.amazon.com/premiumsupport/knowledge-center/api-gateway-proxy-path-parameter-error/) added confusion.

First: what are integration options? Well in integration options you can define how API Gateway will integrate with the defined service, in particular, you can map URL/Body parameters with parameters for your integration. What we aim to do is to use the URL path parameters _bucketName/item_ to define the S3 path where to save the request body payload.

In the AWS console, you do something like this, very far from what you do in CDK

Image description

Instead in CDK, you will define something like

```python
integration_response = apig.IntegrationResponse(status_code="200")
integration_options = IntegrationOptions(request_parameters={        "integration.request.path.bucket":"method.request.path.bucketName",          "integration.request.path.object":"method.request.path.item",
    credentials_role=role,
    integration_responses=[integration_response]
})
```

As you can notice the correct path URL to be passed are _integration.request.path.bucket_ and _integration.request.path.object_ mapped to _method.request.path.bucketName_ and _method.request.path.item_.

What really helped me is the CLI, commands

```python
aws apigateway get-integration --rest-api-id abcd --resource-id 1234 --http-method POST
aws apigateway get-method --rest-api-id abcd --resource-id 1234 --http-method POST
```

## Final thoughts

CDK is really cool, the documentation needs to be expanded to care also for advanced scenarios, and be extensive to describe all you can actually do.

Use the CLI when in doubt… This always helps.

The full code for this mini-POC can be found [here](https://github.com/panilo/APIG-S3).
