API Gateway: Mapping Path Segments to SQS Message
Given an API Gateway endpoint such as POST - /{UserId}/{MessageId}/read
and a requirement to push a message to SQS using just the values contained within the request path. We can create a Integration Request template that pulls these values and creates an SQS message with a JSON body containing these values.
Within the CloudFormation template where we have defined our API in Swagger/OpenAPI we can use the following request template to extract the UserId
and MessageId
and send a message to an SQS queue such as this:
{
"UserId": "User1",
"MessageId": "6c7c614a-eadc-4d5b-984b-49254627d275"
}
requestTemplates:
application/json:
Fn::Sub: |
#set ($UserId = $input.params('UserId'))
#set ($MessageId = $input.params('MessageId'))
#set ($messageContent = "{ 'UserId': '$UserId', 'MessageId': '$MessageId' }")
Action=SendMessage&QueueUrl=$util.urlEncode('${ReadMessageQueue}')&MessageBody=$messageContent
These templates are based on Apaches Velocity Template Language or VTL.
Just for completeness the full API Gateway resource definition in CloudFormation:
APIGateway:
Type: AWS::ApiGateway::RestApi
Properties:
Name: "Message System"
EndpointConfiguration:
Types:
- REGIONAL
Policy:
- !Ref "AWS::NoValue"
Body:
swagger: '2.0'
info:
title: !Ref AWS::StackName
paths:
/{UserId}/{MessageId}/read:
post:
parameters:
- in: path
name: UserId
required: true
type: string
description: User ID
- in: path
name: MessageId
required: true
type: string
description: Message UUID
consumes:
- application/json
produces:
- application/json
responses:
'200':
description: 200 response
schema:
$ref: '#/definitions/Empty'
x-amazon-apigateway-integration:
credentials: !GetAtt APIGatewayRole.Arn
uri: !Sub "arn:aws:apigateway:${AWS::Region}:sqs:path//"
responses:
default:
statusCode: '200'
requestParameters:
integration.request.header.Content-Type: '''application/x-www-form-urlencoded'''
requestTemplates:
application/json:
Fn::Sub: |
#set ($UserId = $input.params('UserId'))
#set ($MessageId = $input.params('MessageId'))
#set ($messageContent = "{ 'UserId': '$UserId', 'MessageId': '$MessageId' }")
Action=SendMessage&QueueUrl=$util.urlEncode('${ReadMessageQueue}')&MessageBody=$messageContent
passthroughBehavior: never
httpMethod: POST
type: aws
definitions:
Empty:
type: object
title: Empty Schema