Developing AWS Lambdas and API Gateway v1
AWS Lambda connected to API Gateway is a cost-effective and scalable architecture for hosting APIs — but development requires specialized approaches since Lambda has no traditional host.
Background
Errthquake, a load and stress testing service, uses Lambda and API Gateway for its control API. The goal was an API that was reliable without requiring constant attention, because the test service itself is where most of the engineering effort goes.
API Gateway supports v1 and v2 request/response formats. v1 was chosen because v2 assumes your response will always be a JSON document — and file upload/download capabilities required v1's flexibility. Both the test service and Lambda functions are implemented in Go.
Lambda Handler Structure
A basic Go Lambda handler looks like this:
package main
import (
"context"
"github.com/aws/aws-lambda-go/events"
"github.com/aws/aws-lambda-go/lambda"
)
func HandleRequest(ctx context.Context, event *events.APIGatewayProxyRequest) (events.APIGatewayProxyResponse, error) {
contentResponse := events.APIGatewayProxyResponse{
StatusCode: 200,
Headers: map[string]string{"Content-Type": "application/json"},
Body: "{\"message\":\"hello world\"}",
}
return contentResponse, nil
}
func main() {
lambda.Start(HandleRequest)
}
Local Development Architecture
A three-file structure separates concerns cleanly:
bootstrap.go— Initializes the Lambda runtimelambda.go— Contains business logic (HandleRequestfunction)exec.go— Local testing utility accepting JSON API Gateway v1 payloads
exec.go deserializes JSON into APIGatewayProxyRequest objects and serializes responses back to JSON — enabling full testing without any AWS infrastructure.
Deployment
Lambda supports x86 and ARM 64-bit architectures. Build for the target architecture:
GOARCH=arm64 GOOS=linux go build -o bootstrap -tags lambda.norpc bootstrap.go lambda.go
zip -FS my-api-lambda.zip bootstrap
aws lambda update-function-code \
--function-name my-api-lambda \
--zip-file fileb://$PWD/my-api-lambda.zip
Match the GOARCH value to the architecture you configured for the Lambda function in AWS (arm64 for Graviton, amd64 for x86).