
{"id":93,"date":"2025-06-09T12:57:40","date_gmt":"2025-06-09T11:57:40","guid":{"rendered":"https:\/\/blog.mkcloudai.com\/?p=93"},"modified":"2025-06-09T12:57:40","modified_gmt":"2025-06-09T11:57:40","slug":"%f0%9f%9a%80-going-serverless-deploying-a-restaurant-booking-api-with-lambda-and-api-gateway","status":"publish","type":"post","link":"https:\/\/blog.mkcloudai.com\/?p=93","title":{"rendered":"\ud83d\ude80 Going Serverless: Deploying a Restaurant Booking API with Lambda and API Gateway"},"content":{"rendered":"\n<p>After building scalable infrastructure using EC2, Terraform, and Secrets Manager, it&#8217;s time to go fully serverless. In this post, we\u2019ll migrate your app to use:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>\ud83e\udde0 <strong>AWS Lambda<\/strong> \u2014 run code without managing servers<\/li>\n\n\n\n<li>\ud83c\udf10 <strong>API Gateway<\/strong> \u2014 expose HTTPS endpoints<\/li>\n\n\n\n<li>\ud83d\udd10 <strong>Secrets Manager<\/strong> \u2014 keep secrets out of your code<\/li>\n\n\n\n<li>\ud83d\uddc3\ufe0f <strong>DynamoDB or RDS Proxy<\/strong> \u2014 handle your database layer<\/li>\n<\/ul>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h3 class=\"wp-block-heading\">\ud83d\udce6 Architecture Overview<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>Client \u2192 API Gateway \u2192 Lambda Functions \u2192 DB (DynamoDB or RDS via Proxy)\n                                   \u2193\n                             Secrets Manager<\/code><\/pre>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h3 class=\"wp-block-heading\">\u2705 Benefits of This Serverless Stack<\/h3>\n\n\n\n<figure class=\"wp-block-table\"><table class=\"has-fixed-layout\"><tbody><tr><th>Feature<\/th><th>Benefit<\/th><\/tr><tr><td>No server to manage<\/td><td>Pay-per-use compute<\/td><\/tr><tr><td>Autoscaling<\/td><td>Lambda scales on demand<\/td><\/tr><tr><td>Secure secrets<\/td><td>AWS Secrets Manager or Parameter Store<\/td><\/tr><tr><td>Low ops overhead<\/td><td>No patching, no EC2, no autoscaling setup<\/td><\/tr><tr><td>Fast deployment<\/td><td>Single command using CDK or SAM<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h3 class=\"wp-block-heading\">\ud83d\udd27 Step-by-Step: Deploy with AWS SAM (Serverless Application Model)<\/h3>\n\n\n\n<h3 class=\"wp-block-heading\">1. \ud83d\udee0 Install SAM CLI<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>brew install aws\/tap\/aws-sam-cli\nsam --version<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">2. \ud83d\udcc1 Project Structure<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>restaurant-booking-api\/\n\u251c\u2500\u2500 template.yaml        # SAM template (Infra as code)\n\u251c\u2500\u2500 app\/\n\u2502   \u251c\u2500\u2500 __init__.py\n\u2502   \u2514\u2500\u2500 handler.py       # Lambda function code\n\u251c\u2500\u2500 events\/              # Example test events\n\u2514\u2500\u2500 requirements.txt<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">3. \u270d\ufe0f Sample SAM Template (template.yaml)<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>AWSTemplateFormatVersion: '2010-09-09'\nTransform: AWS::Serverless-2016-10-31\nResources:\n  BookingAPI:\n    Type: AWS::Serverless::Function\n    Properties:\n      Handler: app.handler.lambda_handler\n      Runtime: python3.11\n      MemorySize: 512\n      Timeout: 10\n      Environment:\n        Variables:\n          DB_SECRET: \/myapp\/db-creds\n      Events:\n        ApiEvent:\n          Type: Api\n          Properties:\n            Path: \/bookings\n            Method: post<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">4. \ud83e\udde0 handler.py (Lambda Code)<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>import json, boto3, os\n\ndef lambda_handler(event, context):\n    secrets = boto3.client('secretsmanager')\n    response = secrets.get_secret_value(SecretId=os.environ&#91;'DB_SECRET'])\n    creds = json.loads(response&#91;'SecretString'])\n\n    booking = json.loads(event&#91;'body'])\n    # Connect to DB, store booking using creds\n    return {\n        \"statusCode\": 200,\n        \"body\": json.dumps({\"message\": \"Booking successful\"})\n    }<\/code><\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">5. \ud83d\ude80 Deploy to AWS<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>sam build\nsam deploy --guided<\/code><\/pre>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h3 class=\"wp-block-heading\">\ud83d\udd10 Storing DB Credentials in Secrets Manager<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>aws secretsmanager create-secret \\\n  --name \/myapp\/db-creds \\\n  --secret-string '{\"username\":\"admin\",\"password\":\"mypassword\"}'<\/code><\/pre>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h3 class=\"wp-block-heading\">\ud83d\udcca Monitoring with CloudWatch<\/h3>\n\n\n\n<p>Each Lambda execution gets its own logs under <strong>\/aws\/lambda\/<\/strong>. You can:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>Set up CloudWatch alarms for failure rates or latency<\/li>\n\n\n\n<li>Enable X-Ray tracing for distributed tracing<\/li>\n<\/ul>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n\n\n\n<h3 class=\"wp-block-heading\">\ud83c\udf0d Bonus: Custom Domain with API Gateway + ACM<\/h3>\n\n\n\n<pre class=\"wp-block-code\"><code>aws acm request-certificate \\\n  --domain-name api.mkcloudai.com \\\n  --validation-method DNS\n\n# Then link ACM to API Gateway via custom domain mappings.<\/code><\/pre>\n\n\n\n<hr class=\"wp-block-separator has-alpha-channel-opacity\"\/>\n","protected":false},"excerpt":{"rendered":"<p>After building scalable infrastructure using EC2, Terraform, and Secrets Manager, it&#8217;s time to go fully serverless. In this post, we\u2019ll [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"site-sidebar-layout":"default","site-content-layout":"","ast-site-content-layout":"","site-content-style":"default","site-sidebar-style":"default","ast-global-header-display":"","ast-banner-title-visibility":"","ast-main-header-display":"","ast-hfb-above-header-display":"","ast-hfb-below-header-display":"","ast-hfb-mobile-header-display":"","site-post-title":"","ast-breadcrumbs-content":"","ast-featured-img":"","footer-sml-layout":"","theme-transparent-header-meta":"","adv-header-id-meta":"","stick-header-meta":"","header-above-stick-meta":"","header-main-stick-meta":"","header-below-stick-meta":"","astra-migrate-meta-layouts":"default","ast-page-background-enabled":"default","ast-page-background-meta":{"desktop":{"background-color":"var(--ast-global-color-5)","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""},"tablet":{"background-color":"","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""},"mobile":{"background-color":"","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""}},"ast-content-background-meta":{"desktop":{"background-color":"var(--ast-global-color-4)","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""},"tablet":{"background-color":"var(--ast-global-color-4)","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""},"mobile":{"background-color":"var(--ast-global-color-4)","background-image":"","background-repeat":"repeat","background-position":"center center","background-size":"auto","background-attachment":"scroll","background-type":"","background-media":"","overlay-type":"","overlay-color":"","overlay-opacity":"","overlay-gradient":""}},"footnotes":""},"categories":[1],"tags":[],"class_list":["post-93","post","type-post","status-publish","format-standard","hentry","category-cloudfront"],"_links":{"self":[{"href":"https:\/\/blog.mkcloudai.com\/index.php?rest_route=\/wp\/v2\/posts\/93","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/blog.mkcloudai.com\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blog.mkcloudai.com\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blog.mkcloudai.com\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/blog.mkcloudai.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=93"}],"version-history":[{"count":1,"href":"https:\/\/blog.mkcloudai.com\/index.php?rest_route=\/wp\/v2\/posts\/93\/revisions"}],"predecessor-version":[{"id":94,"href":"https:\/\/blog.mkcloudai.com\/index.php?rest_route=\/wp\/v2\/posts\/93\/revisions\/94"}],"wp:attachment":[{"href":"https:\/\/blog.mkcloudai.com\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=93"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blog.mkcloudai.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=93"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blog.mkcloudai.com\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=93"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}