<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0" xmlns:itunes="http://www.itunes.com/dtds/podcast-1.0.dtd" xmlns:googleplay="http://www.google.com/schemas/play-podcasts/1.0"><channel><title><![CDATA[The Cloud Engineers]]></title><description><![CDATA[Learn directly from an AWS Senior Solutions Architect through hands-on projects, real-world insights, and practical career guidance designed to help you build your cloud skills and land your first cloud role.]]></description><link>https://blog.thecloudengineers.com</link><image><url>https://substackcdn.com/image/fetch/$s_!Ka2m!,w_256,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F5c6f36c3-e29e-40f9-ab14-7fc0e81d82d9_759x759.png</url><title>The Cloud Engineers</title><link>https://blog.thecloudengineers.com</link></image><generator>Substack</generator><lastBuildDate>Mon, 14 Sep 2026 01:59:30 GMT</lastBuildDate><atom:link href="https://blog.thecloudengineers.com/feed" rel="self" type="application/rss+xml"/><copyright><![CDATA[Lefteris Karageorgiou]]></copyright><language><![CDATA[en]]></language><webMaster><![CDATA[thecloudengineers@substack.com]]></webMaster><itunes:owner><itunes:email><![CDATA[thecloudengineers@substack.com]]></itunes:email><itunes:name><![CDATA[Lefteris Karageorgiou]]></itunes:name></itunes:owner><itunes:author><![CDATA[Lefteris Karageorgiou]]></itunes:author><googleplay:owner><![CDATA[thecloudengineers@substack.com]]></googleplay:owner><googleplay:email><![CDATA[thecloudengineers@substack.com]]></googleplay:email><googleplay:author><![CDATA[Lefteris Karageorgiou]]></googleplay:author><itunes:block><![CDATA[Yes]]></itunes:block><item><title><![CDATA[Building a Multi-Step App with Lambda Durable Functions]]></title><description><![CDATA[A hands-on guide to building a resilient customer onboarding workflow with AWS Lambda durable functions.]]></description><link>https://blog.thecloudengineers.com/p/building-a-multi-step-app-with-lambda</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/building-a-multi-step-app-with-lambda</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 09 Sep 2026 09:31:03 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/7005371a-8ddb-4536-a1dc-fe7b7b463c56_1733x907.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>Building multi-step applications on AWS has always required careful thought around state management, error handling, and coordination between services. If you&#8217;ve built workflows before, you know the drill. You end up writing retry logic, checkpointing progress in DynamoDB, guarding against duplicate executions, and managing infrastructure that has nothing to do with your actual business logic.</p><p>AWS Lambda durable functions change that. Launched at re:Invent 2025, durable functions extend the familiar Lambda programming model with built-in capabilities to checkpoint progress, automatically recover from failures, and suspend execution for up to one year, all without incurring compute charges during waits.</p><p>In this post, I&#8217;ll walk you through building a real multi-step application using Lambda durable functions. We&#8217;ll build a <strong>customer onboarding workflow</strong> that validates user data, sends a verification email, waits for the user to confirm, and then provisions their account. By the end, you&#8217;ll understand the core concepts and have working code you can adapt for your own use cases.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>What Are Lambda Durable Functions?</h2><p>At their core, durable functions are regular Lambda functions. Same event handler, same integrations, same deployment tools. The difference? When you enable durable execution on a function, you get access to a set of <strong>durable operations</strong>, primitives like <code>step()</code>, <code>wait()</code>, and <code>waitForCallback()</code>, that automatically handle checkpointing and replay.</p><p>Here&#8217;s the key mental model:</p><ol><li><p>Your function executes step by step</p></li><li><p>Each durable operation creates a <strong>checkpoint</strong> and the result is persisted automatically</p></li><li><p>If a failure occurs, Lambda re-invokes your function from the beginning</p></li><li><p>During replay, completed steps are <strong>skipped</strong> and their stored results are returned instantly</p></li><li><p>Execution resumes from exactly where it left off</p></li></ol><p>This means you write sequential, readable code while the runtime handles all the complexity of state management and failure recovery underneath.</p><h2>The Use Case: Customer Onboarding</h2><p>Let&#8217;s build something practical. Our customer onboarding workflow has the following steps:</p><ol><li><p><strong>Validate</strong> the incoming registration data</p></li><li><p><strong>Create</strong> a user profile in our database</p></li><li><p><strong>Send</strong> a verification email with a confirmation link</p></li><li><p><strong>Wait</strong> for the user to click the link (up to 24 hours)</p></li><li><p><strong>Provision</strong> the user&#8217;s account (or expire the registration)</p></li><li><p><strong>Send</strong> a welcome email</p></li></ol><p>This is a perfect fit for durable functions because it involves:</p><ul><li><p>Multiple sequential steps that depend on each other</p></li><li><p>A long wait for an external event (email confirmation)</p></li><li><p>Error handling at each stage</p></li><li><p>The need to resume reliably after the wait</p></li></ul><p>Without durable functions, you&#8217;d need DynamoDB to store state, a separate mechanism to handle the callback, retry logic for each step, and idempotency guards. With durable functions, it&#8217;s just code.</p><h2>Writing the Workflow</h2><p>Let&#8217;s write the actual onboarding logic. This is where durable functions shine. The code reads like a simple script, but it&#8217;s fully fault-tolerant.</p><pre><code><code>from aws_durable_execution_sdk_python import (
    DurableContext,
    StepContext,
    durable_execution,
    durable_step,
)
from aws_durable_execution_sdk_python.config import (
    CallbackConfig,
    Duration,
    StepConfig,
)
from aws_durable_execution_sdk_python.retries import (
    RetryStrategyConfig,
    create_retry_strategy,
)

import boto3
import uuid

dynamodb = boto3.resource("dynamodb")
ses = boto3.client("ses")
users_table = dynamodb.Table("Users")


@durable_step
def validate_registration(ctx: StepContext, event: dict) -&gt; dict:
    """Validate incoming registration data."""
    email = event.get("email")
    name = event.get("name")

    if not email or "@" not in email:
        raise ValueError(f"Invalid email: {email}")
    if not name or len(name) &lt; 2:
        raise ValueError(f"Invalid name: {name}")

    ctx.logger.info(f"Registration validated for {email}")
    return {"email": email, "name": name, "user_id": str(uuid.uuid4())}


@durable_step
def create_user_profile(ctx: StepContext, user: dict) -&gt; dict:
    """Create user profile in DynamoDB."""
    users_table.put_item(
        Item={
            "user_id": user["user_id"],
            "email": user["email"],
            "name": user["name"],
            "status": "pending_verification",
        }
    )
    ctx.logger.info(f"Profile created for user {user['user_id']}")
    return user


@durable_step
def send_verification_email(
    ctx: StepContext, callback_id: str, user: dict
) -&gt; dict:
    """Send verification email with the callback link."""
    verification_link = (
        f"https://api.example.com/verify?callback_id={callback_id}"
    )
    ses.send_email(
        Source="noreply@example.com",
        Destination={"ToAddresses": [user["email"]]},
        Message={
            "Subject": {"Data": "Verify your email"},
            "Body": {
                "Html": {
                    "Data": f"&lt;p&gt;Hi {user['name']},&lt;/p&gt;"
                    f"&lt;p&gt;Click &lt;a href='{verification_link}'&gt;here&lt;/a&gt; "
                    f"to verify your email.&lt;/p&gt;"
                }
            },
        },
    )
    ctx.logger.info(f"Verification email sent to {user['email']}")
    return {"email_sent": True}


@durable_step
def provision_account(ctx: StepContext, user: dict) -&gt; dict:
    """Provision the user's account after verification."""
    users_table.update_item(
        Key={"user_id": user["user_id"]},
        UpdateExpression="SET #s = :s",
        ExpressionAttributeNames={"#s": "status"},
        ExpressionAttributeValues={":s": "active"},
    )
    ctx.logger.info(f"Account provisioned for {user['user_id']}")
    return {**user, "status": "active"}


@durable_step
def send_welcome_email(ctx: StepContext, user: dict) -&gt; None:
    """Send welcome email to the newly verified user."""
    ses.send_email(
        Source="noreply@example.com",
        Destination={"ToAddresses": [user["email"]]},
        Message={
            "Subject": {"Data": f"Welcome, {user['name']}!"},
            "Body": {
                "Html": {
                    "Data": f"&lt;p&gt;Hi {user['name']},&lt;/p&gt;"
                    f"&lt;p&gt;Your account is now active. Welcome aboard!&lt;/p&gt;"
                }
            },
        },
    )
    ctx.logger.info(f"Welcome email sent to {user['email']}")


@durable_execution
def lambda_handler(event: dict, context: DurableContext) -&gt; dict:
    try:
        # Step 1: Validate the registration
        user = context.step(validate_registration(event))
        context.logger.info(f"User validated: {user['email']}")

        # Step 2: Create user profile
        retry_config = RetryStrategyConfig(max_attempts=3, backoff_rate=2.0)
        user = context.step(
            create_user_profile(user),
            config=StepConfig(
                retry_strategy=create_retry_strategy(retry_config)
            ),
        )

        # Step 3: Create a callback and send the verification email
        callback = context.create_callback(
            name="email-verification",
            config=CallbackConfig(timeout=Duration.from_hours(24)),
        )
        context.step(
            send_verification_email(callback.callback_id, user)
        )

        # Step 4: Wait for the user to click the verification link
        # Execution suspends here &#8212; no compute charges while waiting
        verification_result = callback.result()
        context.logger.info(f"Callback received: {verification_result}")

        if not verification_result or not verification_result.get("verified"):
            return {
                "user_id": user["user_id"],
                "status": "verification_failed",
            }

        # Step 5: Provision the account
        active_user = context.step(
            provision_account(user),
            config=StepConfig(
                retry_strategy=create_retry_strategy(retry_config)
            ),
        )

        # Step 6: Send welcome email
        context.step(send_welcome_email(active_user))

        return {
            "user_id": active_user["user_id"],
            "status": "active",
            "email": active_user["email"],
        }

    except ValueError as e:
        context.logger.error(f"Validation error: {e}")
        return {"status": "validation_failed", "error": str(e)}
    except Exception as e:
        context.logger.error(f"Onboarding failed: {e}")
        raise
</code></code></pre><p>Let&#8217;s break down what&#8217;s happening:</p><ol><li><p><strong>Each step is decorated with </strong><code>@durable_step</code>. This tells the SDK to checkpoint the result. If the function is replayed, completed steps return their stored result instantly.</p></li><li><p><strong>The </strong><code>@durable_execution</code><strong> decorator</strong> wraps the main handler and provides the <code>DurableContext</code>. This context is your gateway to all durable operations.</p></li><li><p><code>create_callback()</code> creates a callback token with a 24-hour timeout. We pass the <code>callback_id</code> into the verification email as a link parameter. When the user clicks the link, our API Gateway endpoint calls <code>SendDurableExecutionCallbackSuccess</code> with the callback ID, and execution resumes.</p></li><li><p><code>callback.result()</code> is where execution suspends. The function terminates, no compute charges accumulate, and Lambda waits for the callback signal. This could take minutes or hours.</p></li><li><p><strong>Retry strategies</strong> are configured per step. If <code>create_user_profile</code> or <code>provision_account</code> fails due to a transient DynamoDB error, the step retries automatically with exponential backoff.</p></li><li><p><strong>Error handling</strong> distinguishes between terminal errors (invalid registration data &#8594; immediate failure) and transient errors (DynamoDB throttling &#8594; automatic retry within the step).</p></li></ol><h2>Handling the Callback</h2><p>When the user clicks the verification link, you need an API Gateway endpoint that sends the callback signal to Lambda. Here&#8217;s what that looks like:</p><pre><code><code>import boto3
import json

lambda_client = boto3.client("lambda")


def verification_handler(event, context):
    """API Gateway handler for the email verification link."""
    callback_id = event["queryStringParameters"]["callback_id"]

    lambda_client.send_durable_execution_callback_success(
        CallbackId=callback_id,
        Result=json.dumps({"verified": True}).encode(),
    )

    return {
        "statusCode": 200,
        "body": json.dumps({"message": "Email verified successfully!"}),
    }</code></code></pre><p>That&#8217;s it. One API call resumes the entire onboarding workflow from exactly where it left off.</p><h2>Best Practices</h2><p>After building several durable function workflows, here are the patterns I&#8217;d recommend:</p><h3>1. Always Use Lambda Versions in Production</h3><p>When you deploy a durable function, use explicit versions (not <code>$LATEST</code>). If an execution is suspended waiting for a callback, and you deploy a code update, the replayed invocation will use the version that started the execution. This ensures deterministic replay and prevents inconsistencies.</p><h3>2. Keep Steps Focused and Idempotent</h3><p>Each step should do one thing. If a step is retried, it runs the same code again, make sure that&#8217;s safe. For example, use conditional writes in DynamoDB (<code>attribute_not_exists</code>) to avoid creating duplicate records.</p><h3>3. Use Retry Strategies Wisely</h3><p>Not every step needs retries. Validation steps should fail fast. Steps that call external APIs or databases should have retries with exponential backoff. Configure these per-step:</p><pre><code><code>retry_config = RetryStrategyConfig(
    max_attempts=5,
    backoff_rate=2.0,
)
context.step(
    my_step(data),
    config=StepConfig(retry_strategy=create_retry_strategy(retry_config)),
)
</code></code></pre><h3>4. Use <code>context.logger</code> for Logging</h3><p>The durable context logger suppresses duplicate logs during replay. If you use <code>print()</code> or a standard logger, you&#8217;ll see duplicate log entries every time the function is replayed.</p><h3>5. Design for Replay</h3><p>Your code runs from the beginning on every replay. Avoid side effects outside of durable steps, anything not wrapped in <code>context.step()</code> will execute again on every replay. This includes things like incrementing counters, publishing messages, or writing to databases.</p><h2>When to Use Durable Functions vs. Step Functions</h2><p>This is the question everyone asks. Here&#8217;s my take:</p><p><strong>Choose durable functions when:</strong></p><ul><li><p>Your workflow orchestrates Lambda functions (not other AWS services directly)</p></li><li><p>You want to write and test workflows in your programming language</p></li><li><p>You have long waits (hours/days) and want zero-cost suspension</p></li><li><p>Your team is already comfortable with Lambda tooling (SAM, CDK)</p></li></ul><p><strong>Choose Step Functions when:</strong></p><ul><li><p>Your workflow integrates multiple AWS services directly (DynamoDB, SQS, ECS, etc.) via native SDK integrations</p></li><li><p>You need visual debugging and the execution console for production observability</p></li><li><p>Non-engineers need to understand and review the workflow</p></li><li><p>You need the compliance audit trail that Step Functions execution history provides</p></li></ul><p>They&#8217;re not mutually exclusive. Many architectures use both: durable functions for code-heavy Lambda chains, Step Functions for multi-service orchestration.</p><h2>Wrapping Up</h2><p>Lambda durable functions bring a refreshing simplicity to building multi-step applications. You write sequential code in your preferred language, and the runtime handles checkpointing, retries, and suspension transparently. No external state stores, no retry libraries, no orchestration services to manage.</p><p>The customer onboarding workflow we built in this post is a common pattern, but the same approach applies to order processing, payment flows, AI agent orchestration, approval workflows, and any multi-step process that needs to be resilient.</p><p>If you want to dive deeper, here are some resources:</p><ul><li><p><a href="https://docs.aws.amazon.com/lambda/latest/dg/durable-functions.html">Lambda Durable Functions Documentation</a></p></li><li><p><a href="https://docs.aws.amazon.com/lambda/latest/dg/durable-functions.html">AWS Durable Execution SDK Developer Guide</a></p></li><li><p><a href="https://aws.amazon.com/blogs/compute/building-fault-tolerant-long-running-application-with-aws-lambda-durable-functions">Building Fault-Tolerant Applications with Lambda Durable Functions</a></p></li><li><p><a href="https://aws.amazon.com/blogs/compute/best-practices-for-lambda-durable-functions-using-a-fraud-detection-example/">Best Practices for Lambda Durable Functions</a></p></li></ul><p>Happy building!</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[Top 5 AI Coding Assistants for Building Cloud Projects]]></title><description><![CDATA[Choose one tool and it will turn you from a solo developer into an engineering team.]]></description><link>https://blog.thecloudengineers.com/p/top-5-ai-coding-assistants-for-building</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/top-5-ai-coding-assistants-for-building</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 02 Sep 2026 09:30:42 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/582796c0-20b9-429e-8a13-2ee82247bfcf_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<h2>The Shift You Can&#8217;t Ignore</h2><p>A year ago, AI coding assistants were autocomplete on steroids. You&#8217;d type a function signature, and the tool would guess the body. Useful but fundamentally passive.</p><p>That era is over.</p><p>The tools available today are <strong>agents</strong>. They don&#8217;t wait for you to type. They read your project, reason about what needs to happen, make a plan, write the code, run the tests, fix the failures, and come back with a working result. Some of them do this in cloud sandboxes while you&#8217;re reviewing a different feature.</p><p>If you&#8217;re building cloud projects, for example deploying infrastructure, writing Lambda functions, building APIs, configuring services, these tools don&#8217;t just save time. They change the kind of projects you can take on alone.</p><p>Here are five worth knowing, how they differ, and the protocol that connects them all.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>1. Claude Code</h2><p><strong>What it is</strong>: Anthropic&#8217;s agentic coding tool, available as a CLI, a VS Code extension, a JetBrains plugin, and a standalone desktop app.</p><p><strong>Why it matters for cloud projects</strong>: Claude Code isn&#8217;t just an editor feature but a layered agentic system. It separates <strong>memory</strong>, <strong>hooks</strong>, <strong>skills</strong>, <strong>subagents</strong>, and <strong>MCP</strong> into distinct layers, each changing what the model can see or do.</p><p>When you&#8217;re building a serverless API, you don&#8217;t just ask Claude Code to &#8220;write a Lambda function.&#8221; You give it a goal: &#8220;build an API Gateway endpoint that takes a PDF, extracts text with Textract, summarizes it with Bedrock, and stores the result in DynamoDB&#8221; and it plans the approach, writes the handler, generates the IAM policy, creates the SAM template, and runs <code>sam build</code> to verify it compiles.</p><p>The <strong>subagent</strong> capability is where it gets powerful for larger projects. You can spin up multiple Claude Code agents working on different parts of your stack in parallel, one on the frontend, one on the backend, one on the infrastructure, each with its own context window and working memory.</p><p><strong>Standout feature</strong>: <strong>Skills</strong>: reusable instruction sets you can create and share. Write a skill that encodes your team&#8217;s CDK patterns, IAM guardrails, or naming conventions, and every future Claude Code session follows them automatically. It&#8217;s institutional knowledge made executable.</p><h2>2. Kiro</h2><p><strong>What it is</strong>: Amazon&#8217;s agentic IDE, built on top of VS Code with Bedrock models powering the agents.</p><p><strong>Why it matters for cloud projects</strong>: Kiro takes a fundamentally different approach from every other tool on this list. Where others start with code, Kiro starts with <strong>specs</strong>.</p><p>When you describe a feature, Kiro doesn&#8217;t immediately generate code. It first writes a <strong>requirements document</strong>, then a <strong>technical design</strong>, then breaks everything into a <strong>numbered task list</strong>. Only then does it start writing code, and it does so against the spec, not just the prompt. This spec-driven development means the agent can implement more complex features in fewer shots because it has explicit documentation of what it&#8217;s building and why.</p><p>For cloud projects, this changes the game. Instead of &#8220;write me a Step Functions workflow,&#8221; you describe the business requirement (&#8221;process incoming invoices, classify them, route high-value ones for approval&#8221;). Kiro generates the spec, designs the architecture (which Step Functions states, which Lambda functions, what DynamoDB schema), and then implements each task in sequence.</p><p><strong>Standout feature</strong>: <strong>Parallel agents with specs</strong>: Kiro can run multiple agents simultaneously, each working on a different task from the spec. Property-based tests catch edge cases that unit tests miss. The spec acts as the contract between agents, so they don&#8217;t step on each other.</p><h2>3. Cursor</h2><p><strong>What it is</strong>: An AI-native IDE (forked from VS Code) that made &#8220;agent mode&#8221; mainstream.</p><p><strong>Why it matters for cloud projects</strong>: Cursor pioneered the idea that your IDE should have an agent window alongside your file tree. Since Cursor 3.0, the <strong>Agents Window</strong> lets you launch multiple agents, each in its own worktree, each with its own model and mode. One agent can be planning a refactor with Opus while another implements a different feature in parallel.</p><p>The <strong>Cloud Agents</strong> feature (Cursor 3.5) is the headline for cloud builders. These agents run in isolated cloud VMs with full terminal, browser, and desktop access. They can work across multiple repos in parallel and report results back to your IDE asynchronously. This means you can kick off an agent to set up a complete CI/CD pipeline in one repo, deploy a CloudFormation stack in another, and review both results when they&#8217;re done, without your local machine doing any of the work.</p><p><strong>Standout feature</strong>: <strong>Background agents in cloud VMs</strong>: fire off complex infrastructure tasks (Terraform plans, CDK deployments, integration test suites) and they run in the cloud while you keep coding locally. You review the output when it&#8217;s ready.</p><h2>4. Codex</h2><p><strong>What it is</strong>: OpenAI&#8217;s coding agent, now powered by GPT-5.2-Codex and running as both an in-IDE tool and a standalone app.</p><p><strong>Why it matters for cloud projects</strong>: Codex has evolved from a code completion model into a full autonomous agent. The latest version can operate your computer alongside you, meaning it doesn&#8217;t just write code, it interacts with terminals, browsers, and cloud consoles.</p><p>For cloud builders, the most relevant capability is <strong>long-horizon work</strong>. Codex is optimized for tasks that span many files and many steps, exactly what cloud projects demand. A migration from one database to another, a refactor of a monolith into microservices, converting CloudFormation templates to CDK, these are multi-hour, multi-file tasks that Codex can handle with its context compaction and improved handling of large code changes.</p><p>The Codex app supports coordinating <strong>teams of agents</strong> across the full lifecycle: designing, building, shipping, and maintaining software. You can assign one agent to write the Lambda functions, another to write the tests, and a third to configure the deployment pipeline, and they coordinate through shared context.</p><p><strong>Standout feature</strong>: <strong>Full lifecycle coordination</strong>: from design to deployment to maintenance, with agents that can learn from previous actions and remember your preferences across sessions.</p><h2>5. GitHub Copilot</h2><p><strong>What it is</strong>: GitHub&#8217;s AI pair programmer, now with full agent mode and deep GitHub integration.</p><p><strong>Why it matters for cloud projects</strong>: Copilot&#8217;s advantage isn&#8217;t just the model, it&#8217;s the <strong>platform integration</strong>. Copilot lives inside the GitHub ecosystem: pull requests, issues, code review, Actions workflows, and the security graph. When you ask Copilot to work in agent mode, it can create branches, open PRs, run CI checks, and iterate on failures, all within the GitHub flow your team already uses.</p><p>The agent mode is genuinely agentic: it executes multi-step workflows independently, chooses appropriate tools based on context, and iterates based on feedback and results. For cloud projects, this means you can describe an infrastructure change, Copilot writes the Terraform, opens a PR, the CI pipeline runs <code>terraform plan</code>, Copilot reads the plan output, and fixes any issues, all before you review.</p><p><strong>Standout feature</strong>: <strong>Agent Skills</strong>: reusable, domain-specific bundles of knowledge and tool usage that Copilot loads automatically when relevant. You can create skills for your team&#8217;s AWS patterns, security policies, or deployment conventions. Skills compose with MCP servers, so a skill can both encode prompting logic <em>and</em> call external tools.</p><h2>The Thread That Connects Them: MCP and Skills</h2><p>You&#8217;ve probably noticed two terms recurring across all five tools: <strong>MCP</strong> and <strong>Skills</strong>. This isn&#8217;t a coincidence, they represent the two layers that are standardizing how AI coding agents work.</p><h3>MCP &#8212; Model Context Protocol</h3><p>MCP is an open protocol that lets any AI agent connect to any external tool through a single standardized interface. Think of it as USB-C for AI: instead of writing a custom integration for every tool your agent needs to talk to, you expose the tool once as an MCP server, and any MCP-aware agent can use it.</p><p>For cloud builders, this is transformative. An MCP server for AWS means your coding agent can query CloudWatch logs, read DynamoDB tables, check deployment status, or fetch secrets from Secrets Manager, all through the same protocol, regardless of whether you&#8217;re using Claude Code, Kiro, Cursor, Codex, or Copilot.</p><p>MCP servers are already available for AWS services, databases, monitoring tools, and CI/CD platforms. The ecosystem is growing fast because the investment is write-once: build an MCP server for your internal tool, and every AI coding agent your team uses can immediately access it.</p><h3>Skills &#8212; Portable Knowledge</h3><p>Skills take different forms across tools (Claude Code calls them &#8220;skills,&#8221; Copilot calls them &#8220;agent skills,&#8221; Kiro uses &#8220;specs&#8221;), but the concept is the same: <strong>reusable instruction sets that encode how your team builds software</strong>.</p><p>A skill might encode:</p><ul><li><p>Your team&#8217;s CDK patterns and naming conventions</p></li><li><p>Security guardrails (no wildcard IAM policies, encryption at rest required)</p></li><li><p>Architecture preferences (EventBridge over SNS for event routing, DynamoDB over RDS for session storage)</p></li><li><p>Deployment standards (blue-green only, canary for Lambda)</p></li></ul><p>Skills are the bridge between &#8220;AI that writes code&#8221; and &#8220;AI that writes code <em>the way your team writes code</em>.&#8221; Without skills, every agent session starts from zero. With skills, institutional knowledge persists.</p><h2>The Bottom Line</h2><p>These five tools aren&#8217;t competing to be the best autocomplete. They&#8217;re competing to be the best <strong>engineering partner</strong>, one that understands your cloud architecture, follows your team&#8217;s standards, connects to your infrastructure, and works autonomously on complex tasks while you focus on the decisions that matter.</p><p>The advice? Don&#8217;t pick one and ignore the rest. Try them on a real project. The cloud space moves fast, and the tool that fits your workflow today might not be the one you expected.</p><p>Start building. The agents are ready.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[How to Build Real-World Cloud Experience Recruiters Actually Care About]]></title><description><![CDATA[Stop collecting certifications. Start building proof.]]></description><link>https://blog.thecloudengineers.com/p/how-to-build-real-world-cloud-experience</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/how-to-build-real-world-cloud-experience</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 26 Aug 2026 13:31:18 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/2f7f1a86-2f76-4e4c-a547-0d8b92194eb8_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>Every week I get some version of the same message:</p><blockquote><p>&#8220;I have three AWS certifications, but I keep getting rejected. What am I doing wrong?&#8221;</p></blockquote><p>Here&#8217;s the hard truth nobody tells you: <strong>certifications get you noticed, but they don&#8217;t get you hired.</strong> Recruiters and hiring managers have seen thousands of certified candidates who freeze the moment you ask them to design a real system or explain a decision they actually made.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p>What separates the people who get offers from the people who get ghosted isn&#8217;t another badge. It&#8217;s <strong>real-world experience</strong> &#8212; proof that you can take a problem, build a solution, and make it production-ready.</p><p>The good news? You don&#8217;t need a job to build that experience. You can manufacture it yourself. And you only need to follow <strong>three steps</strong>.</p><h2>Step 1: Learn the Cloud Fundamentals</h2><p>Before you build anything, you need a strong foundation. Not a surface-level &#8220;I watched a course once&#8221; understanding &#8212; a genuine working grasp of the core building blocks that every cloud system is made of:</p><ul><li><p><strong>Compute</strong> &#8212; how and where your code runs (EC2, Lambda, containers)</p></li><li><p><strong>Networking</strong> &#8212; VPCs, subnets, routing, load balancing, how traffic actually flows</p></li><li><p><strong>Security</strong> &#8212; encryption, security groups, the shared responsibility model</p></li><li><p><strong>Storage</strong> &#8212; object vs. block vs. file, and when to use each (S3, EBS, EFS)</p></li><li><p><strong>Databases</strong> &#8212; relational vs. NoSQL, and the trade-offs (RDS, DynamoDB)</p></li><li><p><strong>Identity &amp; Access Management</strong> &#8212; IAM roles, policies, and least-privilege access</p></li></ul><p>Here&#8217;s something most people don&#8217;t realize:</p><blockquote><p><strong>Only 10 AWS services account for roughly 90% of all interview questions.</strong></p></blockquote><p>You don&#8217;t need to learn all 200+ AWS services. You need to go <em>deep</em> on the handful that come up again and again &#8212; compute, storage, networking, databases, IAM, and a few messaging and monitoring services. Master those, and you&#8217;ve covered the vast majority of what any interviewer will throw at you.</p><p>Depth beats breadth. Every time.</p><h2>Step 2: Build Projects That Solve Real Problems</h2><p>This is where most people go wrong. They follow a tutorial, deploy a &#8220;Hello World&#8221; app, and call it a project. Recruiters see straight through that.</p><p>Instead: <strong>identify a real problem, then apply your fundamentals to solve it.</strong></p><p>The problem doesn&#8217;t have to be huge. It just has to be <em>real</em>:</p><ul><li><p>A small business that needs a way to collect and process customer feedback</p></li><li><p>A personal expense tracker that ingests bank exports and visualizes spending</p></li><li><p>An image-processing pipeline that resizes and tags photos automatically</p></li><li><p>A URL shortener that has to scale and stay cheap</p></li></ul><p>Then build it end-to-end using the fundamental services from Step 1 &#8212; compute, storage, a database, IAM, and the networking to tie it together.</p><p>Why does this matter so much?</p><blockquote><p><strong>Interviewers look for impact, not just technical knowledge.</strong></p></blockquote><p>When you can say <em>&#8220;I built a system that solved X problem for Y users, and here&#8217;s the decision I made and why,&#8221;</em> you&#8217;re speaking the language hiring managers care about. You&#8217;re no longer a candidate reciting service names &#8212; you&#8217;re an engineer who ships.</p><p>And here&#8217;s the multiplier:</p><blockquote><p><strong>One impactful, real-world project can elevate your profile above the entire competition.</strong></p></blockquote><p>While everyone else lists certifications, you&#8217;ll have a working system, a GitHub repo, an architecture diagram, and a story. That&#8217;s what gets you remembered.</p><h2>Step 3: Optimize With Well-Architected Principles</h2><p>A working project is good. A <em>well-architected</em> project is what makes recruiters lean in.</p><p>Once your solution works, take it further. Improve it across the five pillars of the AWS Well-Architected Framework:</p><ul><li><p><strong>Operational Excellence</strong> &#8212; automate deployments, add monitoring and logging</p></li><li><p><strong>Security</strong> &#8212; tighten IAM to least privilege, encrypt data at rest and in transit</p></li><li><p><strong>Reliability</strong> &#8212; handle failures gracefully, add retries, remove single points of failure</p></li><li><p><strong>Performance Efficiency</strong> &#8212; right-size resources, add caching, choose the right compute</p></li><li><p><strong>Cost Optimization</strong> &#8212; cut waste, use the right pricing model, make it cheap to run</p></li></ul><p>This step is what transforms a hobby project into something that looks like it belongs in production. When you can walk an interviewer through <em>how you made your solution more scalable, secure, reliable, performant, and cost-efficient</em> &#8212; and explain the trade-offs you weighed &#8212; you demonstrate exactly the kind of judgment companies pay senior salaries for.</p><p>That&#8217;s the difference between &#8220;I can use AWS&#8221; and &#8220;I can architect on AWS.&#8221;</p><h2>Putting It All Together</h2><p>Real-world experience isn&#8217;t something you have to wait for a job to give you. You build it yourself, in three steps:</p><ol><li><p><strong>Learn the fundamentals</strong> &#8212; go deep on the core services that actually matter.</p></li><li><p><strong>Build projects that solve real problems</strong> &#8212; and lead with impact, not tech.</p></li><li><p><strong>Optimize with Well-Architected principles</strong> &#8212; turn your project into production-grade proof.</p></li></ol><p>Do this, and you stop looking like &#8220;another certified candidate&#8221; and start looking like an engineer who&#8217;s already doing the job.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div>]]></content:encoded></item><item><title><![CDATA[Observability for Serverless Without the Bill Shock]]></title><description><![CDATA[How to actually see what your serverless app is doing without CloudWatch quietly becoming your biggest line item.]]></description><link>https://blog.thecloudengineers.com/p/observability-for-serverless-without</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/observability-for-serverless-without</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 19 Aug 2026 09:30:38 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/d3a807d7-d6ba-4e0d-a9eb-4964d68adb67_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>Here&#8217;s a story every serverless team eventually lives through. You ship a Lambda-based system, it works beautifully, and you feel great. Then the monthly bill arrives and there&#8217;s a line item that makes you squint: <strong>CloudWatch</strong>. Sometimes it&#8217;s bigger than the Lambda compute it&#8217;s supposed to be observing.</p><p>Observability is non-negotiable. You cannot run a distributed serverless system blind. But in serverless, the very thing that gives you visibility is metered, and the defaults are quietly expensive. The goal isn&#8217;t to log less and fly blind. It&#8217;s to be <strong>deliberate</strong>: capture what you need, drop what you don&#8217;t, and design your observability the same way you design everything else, with cost as a first-class constraint.</p><p>Let&#8217;s break down the three pillars &#8212; logs, metrics, and traces &#8212; where each one silently runs up the bill, and how to get production-grade visibility without the shock.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>Why Serverless Observability Is Different</h2><p>In a traditional server, you SSH in, tail a log, and watch. In serverless, there&#8217;s nothing to SSH into. Your system is dozens of ephemeral functions, queues, and managed services, each emitting its own telemetry. Visibility has to be <em>designed in</em>, not bolted on.</p><p>And every signal has a price:</p><ul><li><p><strong>Logs</strong> are billed for ingestion <em>and</em> storage and Lambda makes it trivially easy to emit enormous volumes.</p></li><li><p><strong>Metrics</strong> are cheap by default but get expensive the moment you reach for high-cardinality custom metrics.</p></li><li><p><strong>Traces</strong> are sampled for a reason trace everything at scale and the cost climbs fast.</p></li></ul><p>The three pillars are your toolkit. Knowing when to reach for each, and when <em>not</em> to, is the whole game.</p><h2>Pillar 1: Logs &#8212; Where the Bill Usually Hides</h2><p>Logs are the number one source of surprise CloudWatch bills. The culprit is almost always <strong>volume</strong>: verbose logging left on in production, giant payloads dumped into logs, and infinite retention.</p><p>Three habits fix most of it:</p><ol><li><p><strong>Log structured JSON, not strings.</strong> Structured logs are queryable, filterable, and far more useful per byte. One rich JSON line beats ten <code>print</code> statements.</p></li><li><p><strong>Log at the right level.</strong> <code>DEBUG</code> is for development. In production, log <code>INFO</code> for the meaningful events and <code>ERROR</code> for failures and make the level configurable per environment so you&#8217;re not redeploying to change it.</p></li><li><p><strong>Set a retention policy. Always.</strong> By default, CloudWatch Logs keep your data <em>forever</em> and you pay for that storage forever. Almost no one needs 90-day-old function logs. Set retention to something sane (7, 14, 30 days) on every log group.</p></li></ol><p>A structured log line looks like this &#8212; one line, fully queryable in CloudWatch Logs Insights:</p><pre><code><code>{
  "level": "INFO",
  "event": "cv_enhanced",
  "requestId": "abc-123",
  "durationMs": 842,
  "inputTokens": 310,
  "outputTokens": 190
}
</code></code></pre><p>The single highest-leverage change most teams can make: <strong>turn off debug logging in production and set log retention.</strong> That one afternoon of work often cuts the CloudWatch bill more than any other single action.</p><h2>Pillar 2: Metrics &#8212; Cheap by Default, Expensive When Careless</h2><p>Metrics answer &#8220;how is the system behaving <em>overall</em>?&#8221; such as invocation counts, error rates, duration, throttles. The good news: Lambda emits the essential ones <strong>for free</strong>, and they&#8217;re your first line of defense.</p><p>Where cost sneaks in is <strong>custom metrics</strong>, and specifically <strong>cardinality</strong>. Every unique combination of dimensions on a custom metric is billed separately. Add a <code>customerId</code> dimension to a metric and you don&#8217;t have one metric but one <em>per customer</em>. That&#8217;s how a &#8220;small&#8221; custom metric becomes a four-figure line item.</p><p>Keep metrics affordable:</p><ol><li><p><strong>Lean on the free built-ins first.</strong> Errors, duration, throttles, and concurrency are already there. Build your core dashboards and alarms on these before adding anything custom.</p></li><li><p><strong>Guard your cardinality.</strong> Never put unbounded values (user IDs, request IDs, email addresses) into metric dimensions. Those belong in logs, not metrics.</p></li><li><p><strong>Emit metrics from logs where you can.</strong> Deriving metrics from structured log fields avoids a separate metric-publishing cost and keeps your telemetry in one place.</p></li></ol><p>Metrics tell you <em>that</em> something is wrong. For <em>why</em>, you need the third pillar.</p><h2>Pillar 3: Traces &#8212; Powerful, and Worth Sampling</h2><p>A trace follows a single request across every hop: API Gateway &#8594; Lambda &#8594; Bedrock &#8594; DynamoDB and shows you exactly where the time (or the failure) went. In an async, event-driven system, this is the difference between &#8220;it&#8217;s slow somewhere&#8221; and &#8220;it&#8217;s this DynamoDB call, right here.&#8221;</p><p>Tracing tools (like AWS X-Ray) are indispensable for debugging distributed flows. But tracing every single request at high volume gets expensive and rarely adds insight.</p><p>Use tracing wisely:</p><ol><li><p><strong>Sample, don&#8217;t capture everything.</strong> A small percentage of requests is usually enough to understand behavior and catch anomalies. Reserve full capture for when you&#8217;re actively hunting a problem.</p></li><li><p><strong>Propagate a correlation ID.</strong> Pass a single request ID through every hop, including across queues and events, and log it everywhere. This is the cheapest, highest-value tracing habit, and it works even where full tracing doesn&#8217;t reach.</p></li><li><p><strong>Trace the boundaries that matter.</strong> Focus tracing on the hops most likely to hurt: external API calls, model invocations, and database access. Those are where latency and failures actually live.</p></li></ol><h2>A Practical, Cost-Aware Setup</h2><p>If you want a default posture that gives strong visibility on a small budget, start here:</p><ol><li><p><strong>Structured JSON logging</strong> at <code>INFO</code> in production, <code>DEBUG</code> only in dev.</p></li><li><p><strong>Log retention</strong> set explicitly on every log group (7&#8211;30 days).</p></li><li><p><strong>Dashboards and alarms</strong> built on the free Lambda metrics &#8212; errors, duration (p95, not just average), and throttles.</p></li><li><p><strong>Custom metrics</strong> only for a handful of true business KPIs, with strict low cardinality.</p></li><li><p><strong>Tracing enabled with sampling</strong>, plus a <strong>correlation ID</strong> threaded through every function and event.</p></li><li><p><strong>A billing alarm on CloudWatch spend itself</strong> so your observability can never surprise you again.</p></li></ol><p>That setup catches real problems fast and keeps the observability bill proportional to the value it delivers.</p><h2>Conclusion</h2><p>Observability isn&#8217;t optional in serverless. You&#8217;re operating a distributed system, and you need to see it. But &#8220;see everything, forever, at full fidelity&#8221; is a choice that quietly wrecks your bill without making you meaningfully wiser. The fundamentals hold here just like everywhere else: capture what matters, drop what doesn&#8217;t, and treat cost as a design constraint from the start.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[So You Want to Be a Solutions Architect: What the Role Really Involves]]></title><description><![CDATA[The skills, the day-to-day, and how to actually get there.]]></description><link>https://blog.thecloudengineers.com/p/so-you-want-to-be-a-solutions-architect</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/so-you-want-to-be-a-solutions-architect</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 12 Aug 2026 09:30:26 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/2caea799-1803-4a06-a22f-e70b1d455710_1729x910.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>Solutions Architect might be the most misunderstood title in tech. Ask ten engineers what an SA does and you&#8217;ll get ten answers: &#8220;they draw diagrams,&#8221; &#8220;they&#8217;re pre-sales,&#8221; &#8220;they&#8217;re just senior engineers who stopped coding.&#8221; None of these are quite right, and the gap between the perception and the reality is exactly why so many talented engineers either avoid the role or struggle when they step into it.</p><p>I&#8217;ve spent four years as a Solutions Architect at AWS, working alongside hundreds of customers. Before that, I was a Software Engineer building and shipping production systems. So I&#8217;ve lived on both sides of the whiteboard. This article is the honest breakdown I wish someone had given me: what the role actually involves, the skills that matter, and a practical path to get there.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>What a Solutions Architect Actually Does</h2><p>Strip away the title and an SA does one thing: <strong>translates business problems into technical solutions, and technical realities into business decisions.</strong> You sit at the intersection.</p><p>On a typical week, that looks like:</p><ul><li><p><strong>Discovery.</strong> Sitting with a customer or team to understand what they&#8217;re <em>actually</em> trying to achieve. The best SAs are relentless about the &#8220;why&#8221; behind the &#8220;what.&#8221;</p></li><li><p><strong>Design.</strong> Producing an architecture that balances the four forces you&#8217;re always juggling: <strong>scalability, performance, cost, and operational simplicity.</strong> There&#8217;s rarely a &#8220;correct&#8221; answer, only trade-offs you can defend.</p></li><li><p><strong>Communication.</strong> Writing the doc. Presenting to stakeholders who range from hands-on engineers to VPs who just want to know the risk and the cost. Translating up and down the stack.</p></li><li><p><strong>Enablement.</strong> Helping teams build the thing by reviewing their approach, unblocking them, and handing off enough context that they own it after you leave.</p></li></ul><p>Notice what&#8217;s <em>not</em> on that list: writing production code all day. That surprises people. Which brings us to the biggest misconceptions.</p><h2>The Misconceptions, Corrected</h2><p><strong>&#8220;SAs don&#8217;t code.&#8221;</strong> False. You may not ship production features, but you build proofs of concept, reference implementations, and demos constantly. If you can&#8217;t open an editor and prove an idea works, your credibility evaporates. The coding shifts from <em>building the product</em> to <em>proving the pattern.</em></p><p><strong>&#8220;It&#8217;s just a senior engineer role.&#8221;</strong> Not quite. Seniority in engineering rewards depth, going deep on a system and owning it. SA work rewards <em>breadth and translation</em>, being conversant across many services, and turning ambiguity into a defensible design others can execute. Different muscle.</p><p><strong>&#8220;It&#8217;s a sales job.&#8221;</strong> In a vendor context (like AWS), there&#8217;s a commercial dimension. You&#8217;re helping customers succeed, which supports adoption. But the technical bar is real; you can&#8217;t hand-wave. And plenty of SA roles exist entirely inside product companies with zero sales involvement.</p><h2>The Skills That Actually Matter</h2><p>Here&#8217;s where I&#8217;d tell my younger self to invest. In order of how much they move the needle:</p><ol><li><p><strong>Communication, especially writing.</strong> This is the single most underrated skill in the role. If you can write a crisp one-pager that a VP and a staff engineer both understand, you will outperform architects with deeper technical knowledge who can&#8217;t. Learn to write.</p></li><li><p><strong>Trade-off reasoning.</strong> Anyone can list AWS services. The value is in knowing <em>when not</em> to use one. &#8220;Do we even need Lambda here, or is a direct API Gateway integration cleaner?&#8221; That instinct, reaching for the simplest thing that works, is the core of the job.</p></li><li><p><strong>Breadth over depth.</strong> You need working knowledge across compute, storage, networking, data, security, and cost. But have two or three areas where you go genuinely deep. Breadth earns you the conversation; depth earns you trust.</p></li><li><p><strong>Cost fluency.</strong> Being able to reason about what an architecture <em>costs,</em> and redesign it when the bill doesn&#8217;t justify the elegance, separates architects who get invited back from those who don&#8217;t.</p></li><li><p><strong>Empathy and listening.</strong> The best design is worthless if it solves the wrong problem. Discovery is a listening skill before it&#8217;s a technical one.</p></li></ol><h2>Solutions Architect vs. Senior Engineer: Which Path Is Yours?</h2><p>Both are excellent, senior, well-compensated paths. The question is what energizes you.</p><p><strong>Lean Solutions Architect if you:</strong></p><ul><li><p>Enjoy variety like new problems, new domains, new people, constantly</p></li><li><p>Like the moment a diagram makes a room go &#8220;oh, <em>now</em> I get it&#8221;</p></li><li><p>Are energized by ambiguity and translation, not annoyed by it</p></li><li><p>Want breadth across the stack more than mastery of one system</p></li></ul><p><strong>Lean Senior/Staff Engineer if you:</strong></p><ul><li><p>Get satisfaction from owning and perfecting a system over time</p></li><li><p>Prefer depth and craft over breadth and context-switching</p></li><li><p>Want your primary output to be shipped, running code</p></li><li><p>Find long meetings and stakeholder management draining rather than fun</p></li></ul><p>Neither is &#8220;more technical&#8221; or &#8220;more senior.&#8221; They&#8217;re different shapes of the same seniority.</p><h2>A Practical Path to Get There</h2><p>If the role sounds like you, here&#8217;s how to move toward it from an engineering seat &#8212; starting today, without waiting for a title change:</p><ol><li><p><strong>Start architecting where you are.</strong> Volunteer for the design docs. Own the &#8220;how should we build this?&#8221; conversation on your team. You don&#8217;t need permission to think like an architect.</p></li><li><p><strong>Write in public and internally.</strong> Publish design write-ups, share trade-off analyses, document decisions. This builds the exact muscle the role demands and creates visible evidence you can do it.</p></li><li><p><strong>Go broad deliberately.</strong> If you&#8217;re a backend engineer, spend a quarter getting genuinely comfortable with networking or data. Fill the gaps in your T-shape.</p></li><li><p><strong>Get in front of stakeholders.</strong> Ask to present your team&#8217;s design to another team or to leadership. Reps at translating technical detail to a mixed audience are gold.</p></li><li><p><strong>Build reference implementations.</strong> Take a common pattern and build a clean, well-documented example. This is exactly the kind of artifact SAs produce &#8212; and a portfolio piece that proves the skill.</p></li><li><p><strong>Certifications help as a floor, not a ceiling.</strong> The AWS Solutions Architect certifications signal breadth and are worth having. But they get you <em>considered</em>, not hired. The design thinking and communication get you hired.</p></li></ol><h2>Conclusion</h2><p>Being a Solutions Architect isn&#8217;t about knowing every service or drawing the prettiest diagram. It&#8217;s about turning ambiguous business problems into defensible technical solutions and being able to explain those solutions to anyone in the room. The fundamentals are the same ones that make any great engineer: reach for simplicity, understand the trade-offs, and always design for the real problem, not the fun one.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[Building Your First GenAI Serverless Project to Enhance Your CV]]></title><description><![CDATA[A weekend project that shows you can ship AI on AWS and makes your resume impossible to ignore.]]></description><link>https://blog.thecloudengineers.com/p/building-your-first-genai-serverless</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/building-your-first-genai-serverless</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 05 Aug 2026 09:30:30 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/4db87fc7-7e4a-4961-b074-7661c9bc621a_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>Everyone tells you to &#8220;build projects&#8221; to stand out. But most portfolio projects are the same tired to-do app or a static site that says nothing about you as an engineer. In 2026, a fast way to make a hiring manager stop scrolling is to show you can <strong>ship a real-world project</strong>, like the serverless GenAI application we'll build in this article.</p><p>The good news: you don&#8217;t need a GPU cluster, an ML degree, or months of work. With <strong>AWS Lambda and Amazon Bedrock</strong>, you can build a genuinely useful GenAI app in an afternoon which is fully serverless, pay-per-request, and free-tier friendly.</p><p>So let&#8217;s design one. We&#8217;ll build a tool that <em>enhances your CV.</em> You give it a job description and your rough resume bullets, and the app rewrites them into sharp, tailored, results-oriented bullet points using a foundation model. It&#8217;s useful, it&#8217;s self-referential, and it demonstrates the full serverless-GenAI stack.</p><p>This article is about the <em>thinking</em> behind the project, the architecture, the decisions, and the career payoff. No code walls, just the blueprint you need to go build it.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>The Idea: A Serverless AI CV Enhancer</h2><p>The concept is simple. A user pastes in two things:</p><ol><li><p>The <strong>job description</strong> they&#8217;re targeting.</p></li><li><p>Their <strong>current resume bullets</strong> rough, honest, unpolished.</p></li></ol><p>The app sends both to a foundation model with a carefully written instruction: rewrite these bullets to be sharp, quantified, and tailored to this specific role. Seconds later, the user gets back stronger bullets they can drop straight into their CV.</p><p>Why this project works so well as a portfolio piece:</p><ul><li><p><strong>It&#8217;s genuinely useful.</strong> You&#8217;ll actually use it. That authenticity comes through when you talk about it.</p></li><li><p><strong>It&#8217;s self-referential.</strong> &#8220;I built the tool that wrote the bullet point describing this tool&#8221; is a hook interviewers remember.</p></li><li><p><strong>It touches the whole modern stack.</strong> API, compute, a foundation model, and a database &#8212; the complete shape of a real GenAI application, in miniature.</p></li></ul><h2>The Architecture</h2><p>We&#8217;re keeping this deliberately simple. Four managed building blocks, all serverless, nothing to patch or babysit:</p><pre><code><code>Client  &#8594;  API Gateway  &#8594;  Lambda  &#8594;  Amazon Bedrock
                              &#9474;
                              &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#8594;  DynamoDB (history)
</code></code></pre><ul><li><p><strong>Amazon API Gateway</strong>: the front door. It exposes a single endpoint your app (or a <code>curl</code> command) can call.</p></li><li><p><strong>AWS Lambda</strong>: the brain. It receives the request, assembles the instruction for the model, calls Bedrock, and stores the result. It runs only when called, and you pay only for those milliseconds.</p></li><li><p><strong>Amazon Bedrock</strong>: the intelligence. This is AWS&#8217;s managed gateway to foundation models (like Claude). You call an API; AWS handles the model hosting, scaling, and infrastructure entirely.</p></li><li><p><strong>Amazon DynamoDB</strong>: the memory. It stores each enhancement so users have a history and so you have a reason to talk about data modeling in interviews.</p></li></ul><p>The beauty of this design is what&#8217;s <em>absent</em>: no servers, no containers, no idle cost, nothing to keep patched. When no one&#8217;s using it, you pay essentially nothing.</p><h2>The Real Product Is the Prompt</h2><p>Here&#8217;s the insight that separates a good GenAI project from a toy: <strong>most of the quality lives in how you instruct the model, not in the plumbing.</strong></p><p>The plumbing like API, function, database is standard serverless work. What makes <em>this</em> app good is a well-structured instruction to the model: telling it to act as an expert resume writer, to use strong action verbs, to quantify impact where plausible, to tailor to the target role, and to return clean output. That instruction is your product. Iterating on it, testing it against real job descriptions, tightening the wording, is where you&#8217;ll spend your most valuable time.</p><p>This is worth internalizing, because it reframes what &#8220;AI engineering&#8221; often means in practice: it&#8217;s less about training models and more about <strong>integrating them well and instructing them precisely.</strong></p><h2>See It In Action</h2><p>Once you build and deploy the application, using it is as simple as sending your target role and your rough bullets. Feed it something honest and unpolished like:</p><blockquote><ul><li><p>Worked on the payments service</p></li><li><p>Helped with the migration to Lambda</p></li><li><p>Fixed bugs in the API</p></li></ul></blockquote><p>...and it returns something tailored and sharp:</p><blockquote><ul><li><p>Architected and shipped a payments service processing millions of daily transactions on AWS</p></li><li><p>Led migration of the core API to a serverless Lambda architecture, cutting infrastructure cost significantly</p></li><li><p>Improved reliability by resolving critical API defects and adding integration test coverage</p></li></ul></blockquote><p>Same you but sharper story. A quick note on integrity: use this to <em>articulate</em> real work more effectively, not to invent it. The goal is to describe what you genuinely did in the strongest honest terms.</p><h2>How to Level It Up (and Talk About It)</h2><p>The base project is enough to ship. But each of these additions gives you another thing to discuss in an interview, pick based on what you want to signal:</p><ol><li><p><strong>Add a simple frontend.</strong> A one-page static site that calls your API turns this into a full-stack demo you can link to from your CV.</p></li><li><p><strong>Add streaming responses.</strong> Have the enhanced bullets appear word by word instead of all at once. It signals you care about user experience, not just the happy path.</p></li><li><p><strong>Add observability.</strong> Structured logging and request tracing across the whole flow. This is the difference between a demo and something production-minded.</p></li><li><p><strong>Add richer history.</strong> Let users query their past enhancements by date. A clean excuse to demonstrate access-pattern-first data modeling in DynamoDB.</p></li></ol><h2>What This Project Actually Signals</h2><p>When this lands on your CV as &#8220;Built a serverless GenAI application on AWS (Lambda, Bedrock, API Gateway, DynamoDB),&#8221; here&#8217;s what a hiring manager reads between the lines:</p><ul><li><p>You can integrate <strong>foundation models</strong> into real applications a high demand skill of the moment.</p></li><li><p>You understand <strong>serverless architecture</strong> and event-driven design, not just in theory.</p></li><li><p>You can <strong>ship end to end</strong>, from idea to API to persistence.</p></li></ul><p>That&#8217;s a lot of signal from an afternoon of work.</p><h2>Conclusion</h2><p>The barrier to building with GenAI has never been lower. A managed function, a Bedrock call, and a simple database are enough to build something genuinely useful  and genuinely impressive on a CV. The fundamentals still apply: keep it simple, scope your permissions tightly, watch your cost, and design around the real problem.</p><p>So this weekend, don&#8217;t build another to-do app. Design and ship the CV enhancer, then put it on the very CV it enhances. Then tell me how it goes.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[How Writing in Public Accelerated My Cloud Career (And How to Start)]]></title><description><![CDATA[The highest-leverage career move most engineers never make.]]></description><link>https://blog.thecloudengineers.com/p/how-writing-in-public-accelerated</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/how-writing-in-public-accelerated</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 29 Jul 2026 09:30:20 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/0dfc4dc8-8e21-4b3c-9bee-9635d3783b76_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>Here&#8217;s a career truth that took me too long to learn: <strong>being good at your job is necessary, but it isn&#8217;t enough to advance quickly.</strong> The engineers who move fastest aren&#8217;t always the most technically brilliant, they&#8217;re the ones whose work is <em>visible.</em> And the single highest-leverage way to make your work visible is to write about it in public.</p><p>I know, because it changed my trajectory. Writing this newsletter, publishing what I learn, and sharing it openly opened doors I didn&#8217;t know existed, such as speaking opportunities, connections with people I admired, and a reputation that arrives in the room before I do. This article is the practical case for doing the same, and a no-excuses playbook to start.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>Why Writing in Public Works (The Mechanics)</h2><p>This isn&#8217;t motivational fluff. There are concrete, compounding mechanisms at play:</p><ul><li><p><strong>It compounds while you sleep.</strong> A good article you wrote two years ago is still working for you today &#8212; being read, shared, and building your reputation. Almost nothing else in a career compounds like published work.</p></li><li><p><strong>It forces clarity.</strong> You don&#8217;t truly understand something until you can explain it simply. Writing exposes the gaps in your knowledge and closes them. You learn the topic <em>twice</em> &#8212; once to do it, once to explain it.</p></li><li><p><strong>It builds a surface area for luck.</strong> Opportunities can&#8217;t find you if you&#8217;re invisible. Every article is another door people can knock on. Jobs, collaborations, and invitations find people who are <em>findable.</em></p></li><li><p><strong>It&#8217;s proof of skill that outlasts any r&#233;sum&#233;.</strong> &#8220;I understand event-driven architectures&#8221; is a claim. A clear article explaining a real trade-off is <em>evidence.</em> Evidence wins.</p></li></ul><h2>The Objections (And Why They&#8217;re Wrong)</h2><p>Almost everyone talks themselves out of starting. Let&#8217;s kill the four excuses head-on:</p><p><strong>&#8220;I&#8217;m not an expert.&#8221;</strong> You don&#8217;t need to be. You need to be one step ahead of your reader. The person who learned something last month explains it <em>better</em> to a beginner than the expert who forgot what confusion feels like. Write from where you are.</p><p><strong>&#8220;It&#8217;s all been written already.&#8221;</strong> It hasn&#8217;t been written by <em>you</em>, with <em>your</em> examples, in <em>your</em> voice. Your specific angle like the mistake you made, the trade-off you hit in production is what makes it worth reading.</p><p><strong>&#8220;I don&#8217;t have time.&#8221;</strong> You don&#8217;t need much. A useful post can be 400 words about one thing you figured out this week. Consistency at small scale beats a heroic effort you never repeat.</p><p><strong>&#8220;What if I&#8217;m wrong?&#8221;</strong> You will be, occasionally. That&#8217;s fine becayse the internet corrects you, you learn, you get better. The cost of a public mistake is far lower than the cost of staying invisible for years.</p><h2>How to Actually Start</h2><p>Here&#8217;s the playbook how to start:</p><ol><li><p><strong>Pick a lane, loosely.</strong> Write about the thing you&#8217;re already doing at work. For me it&#8217;s cloud and serverless. You don&#8217;t need a grand content strategy but a topic you touch every day so you never run out of material.</p></li><li><p><strong>Start with what you just learned.</strong> The best first article is &#8220;here&#8217;s a problem I hit this week and how I solved it.&#8221; It&#8217;s authentic, it&#8217;s useful, and you already have the material in your head.</p></li><li><p><strong>Choose the lowest-friction platform.</strong> Don&#8217;t build a custom blog first, that&#8217;s procrastination in disguise. Start where writing is free and distribution is built in: a newsletter platform like LinkedIn, Medium, or Dev.to. Reduce every barrier between you and <em>publish.</em></p></li><li><p><strong>Commit to a cadence you can actually keep.</strong> I write every Wednesday. The specific rhythm matters less than the promise you keep to yourself. Weekly is great; even monthly beats sporadic. The cadence is what turns one article into a body of work.</p></li><li><p><strong>Write like you talk.</strong> Drop the corporate voice. Explain it the way you&#8217;d explain it to a colleague at lunch. Clarity and personality beat polish.</p></li><li><p><strong>Ship before it&#8217;s perfect.</strong> Your first posts will make you cringe later and that&#8217;s a sign you&#8217;ve grown, not a reason to have waited. Hit publish. Iterate in public.</p></li></ol><h2>What to Expect (A Realistic Timeline)</h2><p>Let me set honest expectations, because unrealistic ones are why people quit:</p><ul><li><p><strong>Weeks 1&#8211;4:</strong> Almost no one reads it. This is normal. You&#8217;re building the <em>habit,</em> not the audience yet.</p></li><li><p><strong>Months 2&#8211;3:</strong> You get better and faster at writing. The occasional comment or share appears. The compounding hasn&#8217;t kicked in so <strong>keep going</strong>.</p></li><li><p><strong>Months 4&#8211;12:</strong> A back catalog accumulates. Search and shares start bringing readers you never reached directly. People begin to <em>recognize your name.</em></p></li><li><p><strong>Beyond a year:</strong> This is where the doors open &#8212; speaking invitations, inbound opportunities, conversations with people you respect. Not because you got lucky, but because you became findable and stayed consistent.</p></li></ul><p>The engineers who win at this aren&#8217;t more talented. They just didn&#8217;t quit in month two.</p><h2>Conclusion</h2><p>Writing in public is the rare career move with almost no downside and enormous, compounding upside. It sharpens your thinking, builds your reputation while you sleep, and turns your everyday work into a body of evidence that advances your career on your behalf.</p><p>You don&#8217;t need to be an expert. You don&#8217;t need a perfect platform. You don&#8217;t need much time. You need one topic, a cadence you can keep, and the willingness to hit publish before you feel ready.</p><p>Start this week. Write 400 words about one thing you figured out. Your future career will thank you. I promise mine did.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[DynamoDB Single-Table Design: The Pattern Everyone Fears (Explained Simply)]]></title><description><![CDATA[Why one table beats five and how to design it without losing your mind.]]></description><link>https://blog.thecloudengineers.com/p/dynamodb-single-table-design-the</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/dynamodb-single-table-design-the</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 22 Jul 2026 09:31:15 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/6e80e50f-be02-494d-86f7-e2fec6d43ca0_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>The first time I saw a DynamoDB single-table design, I closed the tab.</p><p>One table holding users, orders, products, and reviews. All mixed together, with cryptic keys like <code>USER#123</code> and <code>ORDER#456</code> sitting in the same partition? It looked insane.</p><p>It looked insane because I was thinking in <strong>relational terms</strong>. Once I flipped the mental model, <em>design for access patterns, not entities,</em> it clicked. Here&#8217;s the version of this pattern I wish someone had shown me on day one.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>Why We Fear It: The Relational Hangover</h2><p>SQL trains us to normalize. One table per entity, JOINs at query time, let the database figure out the rest. It&#8217;s a beautiful model and it&#8217;s the exact instinct that makes single-table design feel wrong.</p><p>DynamoDB has no JOINs. Every relationship you&#8217;d resolve with a JOIN in SQL becomes either multiple round-trips or a modeling decision you make <em>up front</em>. The fear isn&#8217;t irrational. It&#8217;s a paradigm mismatch. Name it, and it stops being scary.</p><h2>The One Rule That Changes Everything: Access Patterns First</h2><p>Here&#8217;s the shift: <strong>you list your queries before you design your table.</strong></p><p>In SQL you model the data and figure out queries later. In DynamoDB you do the opposite. Take a simple e-commerce app and write down what it needs:</p><ol><li><p>Get a user by ID</p></li><li><p>Get all orders for a user</p></li><li><p>Get a single order with its line items</p></li><li><p>Get all products in a category</p></li></ol><p>If you can&#8217;t list your access patterns, you&#8217;re not ready to model. That discipline is exactly what scares people but it&#8217;s also the superpower. You design for <em>what your app actually does</em>, nothing more.</p><h2>PK, SK, and the Item Collection</h2><p>Two concepts do most of the work:</p><ul><li><p><strong>Partition Key (PK):</strong> determines where an item lives.</p></li><li><p><strong>Sort Key (SK):</strong> orders items <em>within</em> a partition.</p></li></ul><p>The key insight: <strong>items sharing the same PK form an &#8220;item collection&#8221; and are stored together.</strong> One query can retrieve the whole collection. That&#8217;s how you replace a JOIN, you co-locate related data on purpose.</p><h2>A Worked Example</h2><p>Here&#8217;s an actual single-table layout for the e-commerce app:</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="https://substackcdn.com/image/fetch/$s_!O3AM!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!O3AM!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png 424w, https://substackcdn.com/image/fetch/$s_!O3AM!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png 848w, https://substackcdn.com/image/fetch/$s_!O3AM!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png 1272w, https://substackcdn.com/image/fetch/$s_!O3AM!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!O3AM!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png" width="1366" height="530" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/e2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:530,&quot;width&quot;:1366,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:95998,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/206408053?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!O3AM!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png 424w, https://substackcdn.com/image/fetch/$s_!O3AM!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png 848w, https://substackcdn.com/image/fetch/$s_!O3AM!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png 1272w, https://substackcdn.com/image/fetch/$s_!O3AM!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fe2dc1f7e-05fd-411c-8cc3-602d54c6f03a_1366x530.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>Now watch the access patterns fall out:</p><ul><li><p><strong>Get user 123:</strong><br><code>PK = USER#123 AND SK = PROFILE</code></p></li><li><p><strong>Get all orders for user 123:</strong><br><code>PK = USER#123 AND begins_with(SK, "ORDER#")<br></code>One query, no JOIN, no second round-trip.</p></li><li><p><strong>Get order 555 with its items:<br></strong><code>PK = ORDER#555<br></code>The order and every line item come back together.</p></li></ul><p>The cryptic keys aren&#8217;t chaos. They&#8217;re a query language you designed on purpose.</p><h2>GSI Overloading: The Advanced Bit, Made Simple</h2><p>Some queries go against the grain of your PK/SK like &#8220;get all orders with status SHIPPED.&#8221; Your main keys can&#8217;t answer that.</p><p>The solution is a Global Secondary Index built on <strong>generic attributes</strong> (<code>GSI1PK</code>, <code>GSI1SK</code>) that you reuse across entities. Point <code>GSI1PK</code> at the status, and one index can serve several &#8220;sideways&#8221; queries. Don&#8217;t worry about mastering this on day one, it&#8217;s the last 20% you grow into once the basics feel natural.</p><h2>When NOT to Use Single-Table Design</h2><p>I draw boundaries, because the pattern isn&#8217;t free:</p><ul><li><p><strong>Evolving access patterns.</strong> Early-stage products whose queries change weekly,  multiple tables are easier to refactor.</p></li><li><p><strong>Ad-hoc analytics.</strong> DynamoDB is for known patterns. Offload analytics to S3 + Athena.</p></li><li><p><strong>Small apps.</strong> Sometimes the operational simplicity of separate tables beats query efficiency.</p></li><li><p><strong>Team unfamiliarity.</strong> The real cost is the learning curve, not the technology.</p></li></ul><h2>The Cost &amp; Performance Payoff</h2><p>This is where it earns its place in a scalable, cost-efficient stack:</p><ul><li><p><strong>Fewer tables</strong> to provision, monitor, and pay for.</p></li><li><p><strong>One query instead of N round-trips</strong> means lower latency <em>and</em> fewer read capacity units consumed.</p></li><li><p><strong>Item collections</strong> keep related data on one partition, giving you predictable single-digit-millisecond reads at scale.</p></li></ul><h2>Where to Start</h2><p>Don&#8217;t boil the ocean. Pick one feature in your app. List its queries. Model <em>just that</em> as a single table. Once you&#8217;ve watched a JOIN disappear into a single <code>Query</code> call, the fear is gone for good, and you&#8217;ll never look at those <code>USER#123</code> keys the same way again.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[I Asked 20 Hiring Managers What They Look For in Cloud Interviews - Here's What They Told Me]]></title><description><![CDATA[Why technical skill gets you into the room but storytelling and impact get you the offer.]]></description><link>https://blog.thecloudengineers.com/p/i-asked-20-hiring-managers-what-they</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/i-asked-20-hiring-managers-what-they</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 15 Jul 2026 09:30:29 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/052a43b6-279e-4dc4-80b8-0987a5db2acf_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>If you&#8217;ve ever walked out of a cloud engineering interview thinking <em>&#8220;I answered everything correctly&#8230; so why didn&#8217;t I get the offer?&#8221;</em> then this article is for you.</p><p>Over the past few months, I spoke with 20 hiring managers across startups, scale-ups, and large enterprises who regularly interview for Cloud Engineer, DevOps, SRE, and Solutions Architect roles. I asked them a simple question: <strong>&#8220;When two candidates have the same technical skills, what makes you say yes to one and no to the other?&#8221;</strong></p><p>The answers were remarkably consistent. And almost none of them were about knowing more AWS services.</p><p>Here&#8217;s what they&#8217;re actually looking for.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>The #1 theme: candidates who tell stories, not spec sheets</h2><p>Nineteen of the twenty managers used some version of the same phrase: <em>&#8220;I want to understand how they think.&#8221;</em></p><p>The weakest candidates answer questions like they&#8217;re reciting documentation. Ask them how they&#8217;d design a highly available system and you get a list: <em>&#8220;Multi-AZ, Auto Scaling, load balancer, RDS with a read replica.&#8221;</em> All correct. All forgettable.</p><p>The strongest candidates answer with a <strong>story that has a shape</strong>:</p><ul><li><p><strong>Context</strong>: what was the situation and the constraint?</p></li><li><p><strong>Decision</strong>: what did you choose, and critically, <em>what did you choose not to do?</em></p></li><li><p><strong>Impact</strong>: what changed as a result, measured in numbers?</p></li></ul><p>Managers don&#8217;t just want to know that you <em>can</em> use CloudFront. They want to know that you understood <em>why</em> it was the right call over the three other options you considered, and what it did for the business.</p><blockquote><p><em>&#8220;Anyone can list services. I&#8217;m hiring the person who can tell me why they picked one over another and what it cost them when they got it wrong.&#8221;</em> &#8212; Engineering Manager, fintech scale-up</p></blockquote><h2>Why storytelling wins (even for deeply technical questions)</h2><p>There&#8217;s a misconception that storytelling is only for behavioural rounds. It isn&#8217;t. The best technical answers are <em>also</em> stories, because storytelling is really just <strong>structured reasoning made visible</strong>.</p><p>When you narrate your thinking as a story, you demonstrate four things at once that a bullet-point answer never can:</p><ol><li><p><strong>Judgment</strong>: you weighed trade-offs, not just memorized the &#8220;right&#8221; answer.</p></li><li><p><strong>Ownership</strong>: you were close enough to the outcome to know what actually happened.</p></li><li><p><strong>Communication</strong>: you can explain a complex system to a stakeholder who isn&#8217;t in the weeds.</p></li><li><p><strong>Self-awareness</strong>: you know where it went wrong and what you learned.</p></li></ol><p>Those four qualities are exactly what separates a mid-level engineer from a senior one. And they&#8217;re impossible to fake with a list of services.</p><h2>Impact is the word that closes the interview</h2><p>The second theme was even blunter. When I asked what makes an answer <em>land</em>, managers kept coming back to one word: <strong>impact.</strong></p><p>Engineers love to talk about <em>what they built</em>. Hiring managers want to know <em>what changed because you built it</em>.</p><p>Compare these two answers to <em>&#8220;Tell me about a system you optimized.&#8221;</em></p><p>&#10060; <strong>Without impact:</strong></p><blockquote><p>&#8220;I migrated our batch jobs from EC2 to Lambda and set up EventBridge to trigger them on a schedule.&#8221;</p></blockquote><p>&#9989; <strong>With impact:</strong></p><blockquote><p>&#8220;Our nightly batch jobs were running on a fleet of always-on EC2 instances that cost us about $4,000/month but were only active two hours a day. I moved them to Lambda triggered by EventBridge on a schedule. That cut the compute bill for that workload by roughly 80%, around $38k/year, and eliminated the on-call pages we used to get when an instance failed overnight.&#8221;</p></blockquote><p>Same technical work. Completely different signal. The second answer tells the manager: <em>this person understands that engineering exists to serve the business.</em></p><p><strong>A simple rule:</strong> every technical story you tell should end with a number, a saved hour, or a problem that stopped happening.</p><h2>A worked example: how to turn a flat answer into a winning one</h2><p>Let&#8217;s take a classic cloud interview question and walk through the transformation.</p><p><strong>The question:</strong> <em>&#8220;Tell me about a time you improved the reliability of a system.&#8221;</em></p><h3>The flat answer (what most candidates say)</h3><blockquote><p>&#8220;We were having downtime issues, so I added a load balancer and put the service across multiple Availability Zones. After that it was more reliable.&#8221;</p></blockquote><p>It&#8217;s not <em>wrong</em>. But it has no context, no trade-off, and no measurable outcome. The manager learns almost nothing about how you think.</p><h3>The storytelling + impact answer (using Context &#8594; Decision &#8594; Impact)</h3><blockquote><p><strong>Context:</strong> &#8220;We ran a customer-facing checkout API on a single EC2 instance in one Availability Zone. It was fine until we had two outages in one quarter, once from an AZ disruption and once from a bad deploy, and each one took checkout down for about 40 minutes. For an e-commerce product, that&#8217;s direct lost revenue, and it was eroding trust with the business team.</p><p><strong>Decision:</strong> &#8220;I proposed moving to an Auto Scaling group across three AZs behind an Application Load Balancer, with health checks that pulled unhealthy instances out automatically. I deliberately <em>didn&#8217;t</em> go straight to containers or a full EKS setup, even though it was tempting, the team had no Kubernetes experience, and I didn&#8217;t want to trade one reliability risk for a bigger operational one. The ALB-plus-ASG approach solved 90% of the problem with 10% of the complexity.</p><p><strong>Impact:</strong> &#8220;After the change, we went from two multi-outage quarters to zero customer-facing checkout outages over the next nine months. Deploys became safe because we could roll instances one at a time. And because Auto Scaling replaced failed instances automatically, our overnight on-call pages for that service dropped to essentially zero, which the on-call team definitely noticed.&#8221;</p></blockquote><p>Notice what that answer does:</p><ul><li><p>It <strong>quantifies the pain</strong> before the fix (two outages, 40 minutes each, lost revenue).</p></li><li><p>It shows a <strong>deliberate trade-off</strong> (ALB + ASG <em>instead of</em> Kubernetes), proof of judgment.</p></li><li><p>It closes with <strong>measurable impact</strong> across three dimensions: reliability, deploy safety, and team quality of life.</p></li></ul><p>That&#8217;s the difference between &#8220;I know the services&#8221; and &#8220;I know how to use the services to move the needle.&#8221;</p><h2>How to prepare before your next interview</h2><p>You don&#8217;t need to memorize more services. You need to package what you already know into stories. Here&#8217;s a practical drill:</p><ol><li><p><strong>List your last 5&#8211;6 real projects.</strong> Anything you touched like a migration, a cost cut, an incident, a pipeline.</p></li><li><p><strong>For each, write three lines:</strong> the Context (the constraint), the Decision (and the road not taken), and the Impact (with a number).</p></li><li><p><strong>Attach a metric to every story.</strong> Dollars saved, latency reduced, deploy frequency increased, incidents eliminated. If you don&#8217;t know the exact number, estimate it honestly (&#8221;roughly&#8221;, &#8220;about&#8221;) as managers value the instinct to measure.</p></li><li><p><strong>Practice the trade-off out loud.</strong> For each story, be ready to answer: <em>&#8220;What else did you consider, and why didn&#8217;t you pick it?&#8221;</em> This is where senior candidates separate themselves.</p></li></ol><p>Do this for six stories and you&#8217;ll have a toolkit that covers almost any technical or behavioural question they throw at you.</p><h2>The takeaway</h2><p>Twenty hiring managers, one message: <strong>technical skill gets you into the room, but storytelling and impact get you the offer.</strong></p><p>The candidates who win aren&#8217;t the ones who know the most services. They&#8217;re the ones who can take a real problem, walk you through how they thought about it, name the trade-offs they made, and show with numbers what changed because of it.</p><p>Next time you prep, don&#8217;t ask <em>&#8220;Do I know enough AWS?&#8221;</em> Ask <em>&#8220;Can I tell the story of what I built, and prove it mattered?&#8221;</em></p><p>That&#8217;s the answer hiring managers are actually waiting for.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[Lambda Managed Instances: When Serverless Meets Steady-State Traffic]]></title><description><![CDATA[Same code, EC2 pricing, no cold starts. Here's the catch.]]></description><link>https://blog.thecloudengineers.com/p/lambda-managed-instances-when-serverless</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/lambda-managed-instances-when-serverless</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 08 Jul 2026 09:30:54 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/4051667f-d49c-4b22-b7b7-a89be4fd5c14_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>For years, there&#8217;s been one pushback against Lambda that never fully went away: <em>&#8220;It gets expensive at scale.&#8221;</em></p><p>And honestly? For steady, high-volume workloads, that criticism held up. Standard Lambda gives you <strong>one request per execution environment</strong>. So a function that spends most of its time waiting on a database or downstream API is burning paid execution time doing nothing, and at thousands of requests per second, per-invocation billing adds up fast.</p><p>That&#8217;s exactly the gap <strong>AWS Lambda Managed Instances</strong> (announced at re:Invent 2025) is built to close. Let&#8217;s break down what it actually changes, and more importantly when you should reach for it.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>What it actually is</h2><p>You keep the Lambda programming model. Same handler, same event source mappings, same IAM roles, same CloudWatch. But instead of running on Lambda&#8217;s shared fleet, your function runs on <strong>EC2 instances in your own account</strong> and AWS still manages them for you: OS patching, load balancing, auto-scaling, instance lifecycle. You never touch an ASG.</p><p>Three things change the game:</p><ol><li><p><strong>Multi-concurrency.</strong> One execution environment can now handle <em>many</em> concurrent requests instead of one. For IO-heavy workloads, AWS lets you run up to 64 concurrent requests per vCPU. That&#8217;s a completely different mental model as concurrency now means more work per environment, not just more environments.</p></li><li><p><strong>EC2 pricing.</strong> You pay standard EC2 instance charges plus a 15% management fee, <em>not</em> per-request duration. Your Compute Savings Plans and Reserved Instances apply to the EC2 portion (up to 72% off on-demand). For a steady baseline, this can be dramatically cheaper.</p></li><li><p><strong>No cold starts.</strong> Requests route to pre-provisioned environments. You also get access to specialized hardware like Graviton4 and high-bandwidth networking.</p></li></ol><h2>The catch: this is not a free upgrade</h2><p>Here&#8217;s where teams will get burned. <strong>It still says &#8220;Lambda,&#8221; but it behaves like a small service process.</strong></p><ul><li><p><strong>Thread safety is now your problem.</strong> Global state, connection pools, mutable singletons, writes to <code>/tmp</code> &#8212; anything that quietly relied on &#8220;one request at a time&#8221; needs an audit before you flip the switch. Concurrency-unsafe code doesn&#8217;t just underperform; it breaks.</p></li><li><p><strong>No scale-to-zero.</strong> Managed Instances scale to the <em>minimum</em> environments you configure, even at 3am with zero traffic. You&#8217;re deliberately paying for a capacity floor.</p></li><li><p><strong>Scaling is asynchronous.</strong> It scales on CPU and concurrency saturation, sized to absorb roughly a 50% spike before adding capacity (new instances in tens of seconds). If your traffic goes from near-zero to a massive spike in seconds, standard Lambda still has the better shape.</p></li></ul><h2>The decision framework</h2><p>Reach for <strong>Lambda Managed Instances</strong> when <em>most</em> of these are true:</p><ul><li><p>Traffic is steady or predictable as the service does real work most of the day</p></li><li><p>A minimum warm footprint is acceptable (you don&#8217;t need scale-to-zero)</p></li><li><p>Your code is thread-safe under concurrent load</p></li><li><p>The workload is IO-heavy, so multiple requests per environment boost throughput</p></li><li><p>You want EC2 purchase options or specific hardware (Graviton4, high networking)</p></li></ul><p>The textbook fit: an API that loads a model, vector index, or ruleset into memory at init, then serves lots of read-heavy requests. On standard Lambda you&#8217;d push that state to an external store and pay the latency tax on every call.</p><p>Stick with <strong>standard Lambda</strong> for bursty, spiky, event-driven functions where scale-to-zero matters.</p><p>Stick with <strong>Fargate</strong> when you need full container semantics &#8212; sidecars, background daemons, EFS mounts, long-running processes, or task-definition control.</p><h2>Getting started</h2><p>The new primitive is the <strong>capacity provider</strong> (VPC, scaling mode, instance requirements):</p><pre><code><code>aws lambda create-capacity-provider \
  --capacity-provider-name app-api-managed \
  --vpc-config SubnetIds=subnet-123,subnet-456,SecurityGroupIds=sg-789 \
  --instance-requirements Architectures=arm64 \
  --capacity-provider-scaling-config ScalingMode=Auto
</code></code></pre><p>Attach a function to it, publish an active version, and you&#8217;re serving traffic on EC2-backed capacity with the same code.</p><h2>The bottom line</h2><p>AWS didn&#8217;t make Lambda more magical here. It made it more <em>honest</em> about the workloads people were already forcing into it. Standard Lambda is still king for spiky event-driven functions. Managed Instances is the new answer for predictable, high-throughput, Lambda-shaped services, as long as your code is ready for concurrency.</p><p><em>Steady traffic? Do the math. It might be time to give your functions a permanent home.</em></p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[My Insights After 10 Years of Serverless]]></title><description><![CDATA[Common mistakes, emerging tools, and architecture patterns from a decade in the trenches]]></description><link>https://blog.thecloudengineers.com/p/my-insights-after-10-years-of-serverless</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/my-insights-after-10-years-of-serverless</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 01 Jul 2026 09:30:49 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/6fae255f-a356-4d62-bff5-b9a06f4d8309_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>Ten years ago, I discovered Serverless and AWS Lambda, and it changed the way I build software forever.</p><p>What started as curiosity quickly turned into conviction. Over the past decade, I&#8217;ve designed and shipped production systems entirely on Serverless. I even built a startup from scratch, on a fully Serverless stack and took it to production in just 10 months.</p><p>In my four years at AWS, I&#8217;ve worked alongside hundreds of customers on their Serverless journeys, from first Lambda functions to complex event-driven architectures. Along the way, I distilled everything I&#8217;ve learned into my book, <a href="https://a.co/d/0ESOp5f">Mastering Event-Driven Microservices in AWS</a>.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="https://a.co/d/0ESOp5f" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!7Fdy!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg 424w, https://substackcdn.com/image/fetch/$s_!7Fdy!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg 848w, https://substackcdn.com/image/fetch/$s_!7Fdy!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg 1272w, https://substackcdn.com/image/fetch/$s_!7Fdy!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!7Fdy!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg" width="407" height="542.573489010989" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:1941,&quot;width&quot;:1456,&quot;resizeWidth&quot;:407,&quot;bytes&quot;:1686995,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/jpeg&quot;,&quot;href&quot;:&quot;https://a.co/d/0ESOp5f&quot;,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/202706159?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!7Fdy!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg 424w, https://substackcdn.com/image/fetch/$s_!7Fdy!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg 848w, https://substackcdn.com/image/fetch/$s_!7Fdy!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg 1272w, https://substackcdn.com/image/fetch/$s_!7Fdy!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F29eab5c3-6b40-4a12-8b69-2ac15fbeb9f1_2316x3088.jpeg 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>Last month, Lee Gilmore, an AWS Hero, reached out and featured me in his Serverless Advocate newsletter, where he posed three thought-provoking questions about the state of Serverless. I&#8217;m sharing my answers here, because they touch on things I think every Serverless engineer should be thinking about.</p><h4>Q1: What is one common mistake you see teams making when building their solutions, and how can they avoid it?</h4><p>A common mistake is that companies think serverless is all about AWS Lambda, and as a result, they become overly concerned about cold starts.</p><p>In reality, serverless is much broader than Lambda. Many use cases can be solved without Lambdas at all. For example, by using direct integrations with Amazon API Gateway or orchestrating workflows with AWS Step Functions.</p><p><span>The key is to step back and evaluate whether Lambda is actually needed. If it&#8217;s only being used to move data from one service to another, it&#8217;s often unnecessary.</span></p><p><span>That said, when you do need Lambda, you should know how to optimise it properly.</span></p><p><span>Three of the most effective techniques are:</span></p><ol><li><p><span>Optimise memory: Use the </span><a href="https://github.com/alexcasalboni/aws-lambda-power-tuning"><span>AWS Lambda Power Tuning tool</span></a><span> to find the optimal memory configuration. Since memory allocation also scales CPU, the right balance can significantly reduce both execution time and cost.</span></p></li><li><p><span>Minimise deployment size: Smaller packages lead to faster cold starts, so remove unused dependencies and keep artefacts lean.</span></p></li><li><p><span>Use SnapStart: Especially for Java workloads, SnapStart can dramatically reduce cold start latency by initialising functions ahead of time.</span></p></li></ol><p><span>By using Lambda intentionally and optimising it when needed, you can avoid unnecessary complexity and get the best out of serverless.</span></p><h4>Q2: Which tool, package, or AWS service are you most excited about right now, and why?</h4><p><span>Right now, I&#8217;m most excited about </span><a href="https://docs.aws.amazon.com/lambda/latest/dg/durable-functions.html"><span>AWS Lambda durable functions</span></a><span>. This is something the ecosystem has needed for a long time, bringing orchestration closer to the application layer. Previously, you could achieve similar outcomes with AWS Step Functions, but local development, testing, and debugging were often cumbersome.</span></p><p><span>Although this may seem similar to Step Functions, the trade-offs are important:</span></p><p><strong>Use Lambda durable functions when:</strong></p><ul><li><p><span>Your team prefers standard programming languages and familiar development tools</span></p></li><li><p><span>Your application logic primarily lives inside Lambda functions</span></p></li><li><p><span>You&#8217;re building Lambda-centric systems with tight coupling between workflow and business logic</span></p></li></ul><p><strong>Use Step Functions when:</strong></p><ul><li><p><span>You need a visual workflow representation for cross-team visibility</span></p></li><li><p><span>You&#8217;re orchestrating multiple AWS services and want native integrations without writing custom SDK code</span></p></li><li><p><span>You want zero-maintenance infrastructure (no patching or runtime concerns)</span></p></li></ul><p><span>Durable functions make it much easier to build complex, long-running workflows directly in code, opening the door to more advanced use cases like multi-step processes and agent-style orchestration, without sacrificing developer experience.</span></p><h4>Q3: What is your favourite trick or tip that the readers may find interesting?</h4><p><span>A common anti-pattern I see is treating AWS Lambda as &#8220;one service = one function.&#8221; This often leads to architectures with hundreds of tiny Lambda functions, which quickly become difficult to manage, deploy, and reason about.</span></p><p><span>Instead, treat your Lambdas as microservices within a bounded context. It&#8217;s perfectly fine, and often preferable, to group related functionality together. For example, within a &#8220;users&#8221; domain, you can have both &#8216;createUser&#8217; and &#8216;deleteUser&#8217; handled by the same Lambda.</span></p><p><span>When deciding how to group your functions, consider these factors:</span></p><ul><li><p>Bounded contexts</p></li><li><p><span>Team organisation</span></p></li><li><p><span>Scoped IAM permissions</span></p></li><li><p><span>Common code dependencies</span></p></li><li><p><span>Common downstream dependencies</span></p></li><li><p><span>Initialisation time (cold start impact)</span></p></li><li><p><span>Memory configuration</span></p></li></ul><p><span>A powerful way to implement this approach is the Lambda Web Adapter pattern. Instead of creating one Lambda per HTTP endpoint, you run a traditional web framework inside a single Lambda and handle routing internally. This allows you to use familiar frameworks like Express.js, Flask, Django, Spring Boot, or ASP.NET.</span></p><p><span>The result is a more maintainable system that aligns with real domain boundaries, without losing the benefits of serverless.</span></p><h2><span>Conclusion</span></h2><p>Serverless has matured enormously over the past decade, but the fundamentals remain the same: build only what matters, let the cloud handle the rest, and always optimize for simplicity. Whether it&#8217;s choosing the right tool for the job, embracing new capabilities like Lambda durable functions, or structuring your Lambdas around real domain boundaries, the goal is to ship faster with less operational burden. If you want to go deeper on event-driven architectures, my book <a href="https://a.co/d/0ESOp5f">Mastering Event-Driven Microservices in AWS</a> covers these patterns and many more in detail.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="https://a.co/d/0ESOp5f" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!HitB!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg 424w, https://substackcdn.com/image/fetch/$s_!HitB!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg 848w, https://substackcdn.com/image/fetch/$s_!HitB!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg 1272w, https://substackcdn.com/image/fetch/$s_!HitB!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!HitB!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg" width="493" height="608.1727062451812" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:1600,&quot;width&quot;:1297,&quot;resizeWidth&quot;:493,&quot;bytes&quot;:317327,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/jpeg&quot;,&quot;href&quot;:&quot;https://a.co/d/0ESOp5f&quot;,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/202706159?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!HitB!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg 424w, https://substackcdn.com/image/fetch/$s_!HitB!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg 848w, https://substackcdn.com/image/fetch/$s_!HitB!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg 1272w, https://substackcdn.com/image/fetch/$s_!HitB!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F0b768e3e-1450-40c8-8c51-28a87302aa46_1297x1600.jpeg 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div>]]></content:encoded></item><item><title><![CDATA[API Gateway: Why Your Serverless API Costs More Than an ALB at Scale]]></title><description><![CDATA[REST vs. HTTP APIs vs. ALB. A real-world cost breakdown.]]></description><link>https://blog.thecloudengineers.com/p/api-gateway-why-your-serverless-api</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/api-gateway-why-your-serverless-api</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 24 Jun 2026 09:30:40 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/128821fe-a34d-4db0-8fc3-64040e5f059b_1200x632.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>You went serverless. API Gateway in front of Lambda, clean architecture, no servers to manage. It felt great at 10,000 requests a day. Then your product grew, and now you&#8217;re staring at a $2,000/month API Gateway bill wondering what happened.</p><p>Here&#8217;s the uncomfortable truth: API Gateway&#8217;s pricing model has a scaling cliff that nobody talks about during the honeymoon phase.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>The Math That Changes Everything</h2><p>API Gateway REST APIs charge $3.50 per million requests (after the first 333 million/month, it drops slightly). Sounds cheap in isolation. Let&#8217;s do the math for a moderately successful API:</p><ul><li><p>50 million requests/month</p></li><li><p>API Gateway cost: ~$175/month</p></li></ul><p>Now the same traffic through an Application Load Balancer:</p><ul><li><p>ALB fixed cost: ~$22/month (base + LCUs)</p></li><li><p>Per-request component: negligible at this scale</p></li></ul><p>That&#8217;s already an 8x difference, and it only gets worse as you scale. At 500 million requests/month, you&#8217;re looking at $1,750 for API Gateway vs. roughly $50&#8211;80 for an ALB. The gap becomes a canyon.</p><h2>&#8220;But API Gateway Gives Me More Features&#8221;</h2><p>This is the argument that keeps teams locked in. And it&#8217;s partially true. REST APIs give you usage plans, API keys, request validation, and caching built in.</p><p>But ask yourself honestly: how many of those features are you actually using?</p><p>Most production APIs I&#8217;ve seen use API Gateway as a glorified proxy. The Lambda function does all the validation, auth happens in a middleware layer or authorizer, and nobody configured the built-in caching. If that sounds like your setup, you&#8217;re paying a premium for a feature set you&#8217;re not consuming.</p><h2>HTTP APIs: The Middle Ground Nobody Considers</h2><p>In 2019, AWS launched HTTP APIs, a stripped-down API Gateway variant at $1.00 per million requests. That&#8217;s a 70% discount over REST APIs for the same basic function: route a request to Lambda.</p><p>HTTP APIs support JWT authorizers, CORS configuration, path parameters, and Lambda proxy integration. For most CRUD APIs, that&#8217;s the complete feature set you need.</p><p>If you&#8217;re running REST APIs today and not using usage plans, API key management, or request/response transformation at the gateway level, you&#8217;re overpaying by 3.5x for no reason.</p><h2>When ALB + Lambda Actually Wins</h2><p>ALB can invoke Lambda directly. No API Gateway in the path at all. You lose the API management features entirely, but you gain:</p><ul><li><p><strong>Predictable pricing</strong> that barely moves with traffic volume</p></li><li><p><strong>Health checks and target group routing</strong> baked in</p></li><li><p><strong>gRPC support</strong> if you need it</p></li><li><p><strong>No 29-second timeout</strong> ceiling</p></li></ul><p>The trade-off: you manage SSL certificates, you don&#8217;t get built-in throttling, and monitoring requires more CloudWatch configuration. But for high-throughput internal APIs or backend-to-backend communication, ALB is dramatically cheaper.</p><h2>The Decision Framework</h2><p>Here&#8217;s how I think about it:</p><p><strong>Stay on API Gateway REST APIs</strong> if you genuinely use usage plans, per-client throttling, API key quotas, or request transformation templates. These are legitimate features with no ALB equivalent.</p><p><strong>Switch to HTTP APIs</strong> if your Gateway is a passthrough proxy with JWT or Lambda authorizer. Same developer experience, 70% cost reduction.</p><p><strong>Switch to ALB</strong> if you&#8217;re processing more than 100M requests/month, your APIs are internal or don&#8217;t need API management features, or you&#8217;re hitting the 29-second timeout limit.</p><h2>The Takeaway</h2><p>API Gateway is not expensive. API Gateway <em>at scale</em> without using its premium features is expensive. The mistake isn&#8217;t choosing API Gateway on day one &#8212; it&#8217;s never re-evaluating as your traffic grows.</p><p>Check your current monthly request count. Run the math against HTTP APIs and ALB. The five minutes of arithmetic might save you more than your last week of performance optimization work.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[Serverless with Claude Code: Build POCs Fast Without Losing Control]]></title><description><![CDATA[What I learned about keeping AI coding agents on track during customer engagements.]]></description><link>https://blog.thecloudengineers.com/p/serverless-with-claude-code-build</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/serverless-with-claude-code-build</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 17 Jun 2026 09:31:09 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/46b97401-89f0-40f4-a61a-fbe56cc1543b_1200x630.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>Proof of concepts shouldn&#8217;t take weeks. At AWS, we build many POCs for customers. Quick, focused prototypes that validate an idea, demonstrate feasibility to stakeholders, and inform the path forward. Whether it&#8217;s a new integration pattern, an AI-powered workflow, or a migration proof point, the goal is always the same: show, don&#8217;t tell.</p><p>Claude Code has become a genuine accelerator for this kind of work. Paired with AWS serverless services &#8212; Lambda, API Gateway, DynamoDB, Step Functions &#8212; it helps me go from idea to working prototype in hours rather than days. The boilerplate disappears. The IAM headaches shrink. The iteration cycles get tighter.</p><p>But here&#8217;s what I&#8217;ve learned the hard way: <strong>speed without structure creates risk.</strong></p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>The Problem with Moving Too Fast</h2><p>I&#8217;ve seen it in my own POCs and in customer engagements. Claude Code scaffolds an entire API in minutes, but then you realise the permissions are too broad, the error handling is inconsistent, or the generated code drifts from your intended architecture. For a throwaway prototype, maybe that&#8217;s fine. But the moment a POC starts to look promising &#8212; the moment a stakeholder says &#8220;let&#8217;s run with this&#8221; &#8212; those shortcuts become technical debt.</p><p>The issue isn&#8217;t Claude Code itself. It&#8217;s that most of us treat it as a raw accelerator without building the <strong>harness</strong> around it: the specs, constraints, tests, and guardrails that keep agent behaviour reliable and predictable.</p><h2>Harness Engineering: The Missing Piece</h2><p>This is exactly why I&#8217;m excited about an upcoming workshop that tackles this head-on: <strong><a href="https://www.eventbrite.co.uk/e/hands-on-harness-engineering-with-claude-tickets-1990304341864?aff=left&amp;discount=left40">Hands-On: Harness Engineering with Claude</a></strong>, hosted by Packt Publishing on <strong>Thursday, August 6, 2025 (9:00&#8211;11:30 AM EDT)</strong>.</p><p>The workshop teaches <em>harness engineering</em> &#8212; the practical discipline of building the surrounding system that makes Claude Code&#8217;s behaviour more reliable, testable, constrained, and trustworthy. Instead of relying on prompting alone, you learn how to combine:</p><ul><li><p><strong>Specs and instructions</strong> &#8212; turning requirements into executable guidance that steers Claude Code&#8217;s output</p></li><li><p><strong>Permissions and hooks</strong> &#8212; constraining what the agent can and cannot do</p></li><li><p><strong>Tests and verification</strong> &#8212; validating outputs against acceptance criteria automatically</p></li><li><p><strong>Logging and observability</strong> &#8212; understanding what the agent actually did and why</p></li></ul><p>This is the difference between &#8220;Claude Code wrote something that looks right&#8221; and &#8220;Claude Code produced a verified, reviewable output within defined boundaries.&#8221;</p><h2>Why This Matters for Serverless POCs</h2><p>When I build serverless POCs with Claude Code, the harness is what lets me move fast <em>and</em> stay confident. A well-written spec means the generated Lambda functions match the architecture I intended. Permission hooks prevent the agent from creating overly permissive IAM policies. Tests validate that the API actually handles edge cases before I demo it to a customer.</p><p>The result: I keep the speed advantage &#8212; POCs in hours, costs in pennies &#8212; without the anxiety of shipping something I haven&#8217;t properly reviewed.</p><h2>Who Should Attend</h2><p>If you&#8217;re using Claude Code (or any AI coding agent) for real work &#8212; whether that&#8217;s serverless POCs, infrastructure automation, or application development &#8212; this workshop fills a critical gap. It&#8217;s not about prompting tricks. It&#8217;s about building an engineering framework that optimises for trust, predictability, and production readiness.</p><p><strong>Event details:</strong></p><ul><li><p>&#128197; <strong>Thursday, August 6</strong> | 9:00&#8211;11:30 AM EDT</p></li><li><p>&#128187; <strong>Online</strong> &#8212; join from anywhere</p></li><li><p>&#127903;&#65039; <strong><a href="https://www.eventbrite.co.uk/e/hands-on-harness-engineering-with-claude-tickets-1990304341864?aff=left&amp;discount=left40">Register on Eventbrite</a></strong></p></li></ul><p>Speed is table stakes now. Reliability is the differentiator. Learn how to build both into your Claude Code workflows.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[The 4-Step Roadmap to Break Into Cloud (That Actually Works)]]></title><description><![CDATA[Stop Collecting Certifications. Start Building a Career.]]></description><link>https://blog.thecloudengineers.com/p/the-4-step-roadmap-to-break-into</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/the-4-step-roadmap-to-break-into</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 10 Jun 2026 09:31:18 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/2d7b3d9b-f00d-42bc-993d-4b49f6186c82_1200x630.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>Most people trying to break into cloud are stuck in an endless loop.</p><p>They watch tutorials. They collect certifications. They spin up a Lambda function, follow along with a YouTube video, tear it down, and call it &#8220;experience.&#8221;</p><p>Then they apply to 50, 100, maybe 200 jobs, and hear nothing back.</p><p>Here&#8217;s the uncomfortable truth: <strong>the market doesn&#8217;t reward what you know. It rewards what you can prove.</strong></p><p>Right now, thousands of professionals who want to switch to cloud careers are competing for the same roles with the same certifications, the same generic resumes, and zero evidence that they can build anything real.</p><p>The ones who break through do something different. They follow a system.</p><p>In this article, we&#8217;ll dive into that system, which consists of four steps.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="https://substackcdn.com/image/fetch/$s_!01wT!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!01wT!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png 424w, https://substackcdn.com/image/fetch/$s_!01wT!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png 848w, https://substackcdn.com/image/fetch/$s_!01wT!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png 1272w, https://substackcdn.com/image/fetch/$s_!01wT!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!01wT!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png" width="592" height="231.75824175824175" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:570,&quot;width&quot;:1456,&quot;resizeWidth&quot;:592,&quot;bytes&quot;:1712928,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/200731176?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!01wT!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png 424w, https://substackcdn.com/image/fetch/$s_!01wT!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png 848w, https://substackcdn.com/image/fetch/$s_!01wT!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png 1272w, https://substackcdn.com/image/fetch/$s_!01wT!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1f3d5eb3-e864-4615-a17d-5709403bdbc0_1932x756.png 1456w" sizes="100vw" fetchpriority="high"></picture><div></div></div></a></figure></div><h2>Step 1: Build Real-World Cloud Projects</h2><p>Not toy examples. Not tutorial clones.</p><p>Build production-style projects using industry best practices, the kind you can confidently walk through in an interview without breaking eye contact.</p><p><strong>That means proper architecture. Infrastructure as Code. CI/CD pipelines. Monitoring. Cost awareness. Security considerations. The full picture.</strong></p><p>When an interviewer asks, &#8220;Tell me about something you&#8217;ve built,&#8221; you should have a project so solid that your biggest challenge is deciding which part to talk about first.</p><h2>Step 2: Turn Those Projects Into a Recruiter-Ready Portfolio</h2><p>Building is only half the battle. If nobody can find your work, it doesn&#8217;t exist.</p><p>Instead, showcase your projects properly. Upload clean, well-documented code to GitHub with strong READMEs. Write blog posts explaining your architecture decisions and trade-offs.</p><p><strong>I&#8217;ve seen candidates with mediocre projects outperform stronger builders simply because their work was visible and well presented.</strong></p><p>Also, optimize your LinkedIn profile. Treat it like a landing page, not a digital CV. Use a clear headline that states what you do and who you help. Post consistently about what you&#8217;re building and learning. Recruiters search LinkedIn daily, so make sure they find you.</p><h2>Step 3: Get Visible and Secure Interviews</h2><p>You can&#8217;t get hired from the shadows. Network with intent.</p><p>Engage on LinkedIn, join cloud communities, and attend local meetups.</p><p>But don&#8217;t just lurk. Comment on posts with genuine insights, share your learnings publicly, and connect with people doing the work you want to do.</p><p>I&#8217;ve seen more opportunities come from a single thoughtful comment than from hundreds of cold applications.</p><p>Showcase your projects publicly. Talk about what you&#8217;re building, what broke, and what you learned.</p><p><strong>This isn&#8217;t bragging, it&#8217;s signaling.</strong></p><p>You&#8217;re telling the market: &#8220;I&#8217;m here, I&#8217;m building, and I&#8217;m serious.&#8221;</p><p>The interviews will come. Not from luck, but from visibility.</p><h2>Step 4: Prepare for and Master Interviews</h2><p>Getting the interview isn&#8217;t the finish line. It&#8217;s the starting line.</p><p>Practice explaining your architecture decisions, trade-offs, and problem-solving approach until it becomes second nature.</p><p>Know why you chose DynamoDB over RDS. Know what you&#8217;d change if requirements shifted. Know how you&#8217;d scale under pressure.</p><p><strong>Walk in confident, not guessing.</strong></p><p>The candidates who land offers aren&#8217;t always the most technically brilliant. They&#8217;re the ones who communicate clearly, own their decisions, and show they think like engineers who ship to production.</p><h2>The Problem With Doing This Alone</h2><p>You already know what you need to do. The steps above aren&#8217;t a secret.</p><p><strong>But knowing and executing are two different things.</strong></p><p>Most people get stuck between Step 1 and Step 2 &#8212; building projects that aren&#8217;t strong enough or never making them visible.</p><p>Others network randomly, apply generically, and wonder why nothing lands.</p><p>What separates people who break in from people who stay stuck isn&#8217;t talent.</p><p><strong>It&#8217;s having a structured path, accountability, and someone who&#8217;s done it before showing you exactly where to focus.</strong></p><h2>That&#8217;s Why I Built the Cloud Career Bootcamp</h2><p>Over the past six years, I&#8217;ve personally guided more than 200 professionals through their transition into cloud careers using this system.</p><p>The results have been consistently strong.</p><p>People who felt their backgrounds were holding them back successfully landed cloud roles at companies like AWS, J.P. Morgan, Airbnb, Uber, Pfizer, and more.</p><p>Career changers who thought it was too late to pivot moved into cloud positions.</p><p>Instead of facing constant rejection, they started receiving multiple offers from companies eager to hire them.</p><p>Now, I&#8217;m putting together a program that walks you through this entire roadmap, step by step, with hands-on guidance, real feedback, and a community of people on the same path.</p><p>If you&#8217;re serious about breaking into cloud and you&#8217;re done spinning your wheels, join the waitlist:</p><p>&#128073; <strong><a href="https://learn.thecloudengineers.com/cloud-career-bootcamp-waitlist">Cloud Career Bootcamp &#8212; Join the Free Waitlist Now</a></strong></p><p>Spots will be limited.</p><p>Get on the list so you&#8217;ll be the first to know when doors open.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div>]]></content:encoded></item><item><title><![CDATA[S3 Cost Traps: What Nobody Tells You About Lifecycle Policies]]></title><description><![CDATA[You&#8217;re running a production workload on AWS. You set up S3, maybe enabled versioning because &#8220;best practice,&#8221; and moved on. Six months later, your S3 bill is three times what you expected, and you have no idea why.]]></description><link>https://blog.thecloudengineers.com/p/s3-cost-traps-what-nobody-tells-you</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/s3-cost-traps-what-nobody-tells-you</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 03 Jun 2026 09:31:37 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/fb484cb2-0341-4b8d-a368-c96f6effd1a7_1200x630.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>You&#8217;re running a production workload on AWS. You set up S3, maybe enabled versioning because &#8220;best practice,&#8221; and moved on. Six months later, your S3 bill is three times what you expected, and you have no idea why.</p><p>You&#8217;re not alone. S3 pricing is deceptively simple on the surface, but underneath it hides several cost traps that lifecycle policies are supposed to solve. The problem? Most teams either skip lifecycle rules entirely or configure them in ways that barely help.</p><p>Let&#8217;s talk about what&#8217;s silently eating your budget.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>The Versioning Tax</h2><p>Versioning is great for data protection. Every overwrite or delete keeps the old object around, which means you can recover from accidental changes. What nobody emphasizes: <strong>every old version is a billable object</strong>.</p><p>If you&#8217;re writing logs, reports, or processed data that gets overwritten frequently, you could be storing 10x or 50x the &#8220;visible&#8221; data. The S3 console shows you the current objects. The old versions hide underneath, quietly accumulating storage charges.</p><p><strong>The fix:</strong> Always pair versioning with a lifecycle rule that expires non-current versions. Ask yourself: &#8220;Do I really need 90 days of old versions, or would 7 days cover any realistic recovery scenario?&#8221;</p><h2>The Multipart Upload Graveyard</h2><p>When a large upload fails halfway, the uploaded parts don&#8217;t disappear. They sit in your bucket as incomplete multipart uploads, invisible in the console&#8217;s normal view, but fully billable.</p><p>If you&#8217;re running data pipelines, ETL jobs, or any process that writes large objects and occasionally fails, these orphaned parts add up. Some teams discover gigabytes of phantom storage they never knew existed.</p><p><strong>The fix:</strong> Add a lifecycle rule to abort incomplete multipart uploads after a short window, 7 days is generous for most workloads. Some teams set it to 1 day.</p><h2>The &#8220;I&#8217;ll Transition Everything to Glacier&#8221; Mistake</h2><p>A common first move: create a lifecycle rule that transitions all objects to S3 Glacier after 30 days. Sounds sensible, cold storage is cheap.</p><p>Here&#8217;s what catches people:</p><ul><li><p><strong>Minimum storage duration charges.</strong> Glacier has a 90-day minimum. Delete an object on day 45? You still pay for 90 days.</p></li><li><p><strong>Retrieval costs.</strong> If your application or downstream process ever needs those objects back, retrieval fees and restore times can surprise you.</p></li><li><p><strong>Small object overhead.</strong> Glacier adds 32KB of metadata per object. If you&#8217;re storing millions of tiny files, the overhead alone can exceed what you&#8217;d pay in Standard.</p></li></ul><p><strong>The right question:</strong> Before transitioning, map your actual access patterns. If objects are never accessed after 30 days, Glacier Deep Archive might make sense. If they&#8217;re occasionally accessed, Infrequent Access (IA) with its simpler retrieval model is a safer bet.</p><h2>Lifecycle Rules That Don&#8217;t Actually Apply</h2><p>This one is subtle. You create a lifecycle rule, confirm it&#8217;s active, and assume it&#8217;s working. But lifecycle rules scope by <strong>prefix</strong> and <strong>tags</strong>. If your bucket structure changed after you wrote the rule &#8212; new prefixes, different naming conventions &#8212; your rule might be covering 10% of the bucket while the rest grows unchecked.</p><p><strong>The fix:</strong> Audit lifecycle rules quarterly. Use S3 Storage Lens to see the actual breakdown of storage classes, current vs. non-current versions, and incomplete multipart uploads across your buckets. If the numbers don&#8217;t match your expectations, your rules have gaps.</p><h2>A Mental Model for Getting This Right</h2><p>Think of lifecycle policies as a three-layer system:</p><ol><li><p><strong>Expiration layer</strong>: What can be deleted, and when? Non-current versions, expired delete markers, incomplete uploads.</p></li><li><p><strong>Transition layer</strong>: What should move to cheaper storage, and based on what access pattern evidence?</p></li><li><p><strong>Audit layer</strong>: How do you verify the rules are actually working as intended?</p></li></ol><p>Most teams only think about layer two and skip layers one and three entirely. That&#8217;s where the silent costs hide.</p><h2>The Takeaway</h2><p>S3 is not &#8220;set and forget.&#8221; The defaults are designed for durability, not cost efficiency. If you&#8217;re not actively managing object versions, failed uploads, and storage class transitions with lifecycle rules, and validating those rules still match reality, you&#8217;re overpaying.</p><p>Start with a single bucket. Check its Storage Lens dashboard. You&#8217;ll probably find at least one surprise waiting for you.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[5 Fundamental Architectures You Should Know for Cloud Interviews]]></title><description><![CDATA[If you want to break into a cloud role (Cloud Engineer, Cloud Developer, Software Engineer, DevOps, SRE, Solutions Architect, etc.) and you have an interview coming up, understanding cloud architecture is non-negotiable if you want to stand out in interviews.]]></description><link>https://blog.thecloudengineers.com/p/5-fundamental-architectures-you-should</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/5-fundamental-architectures-you-should</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 27 May 2026 09:31:12 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/2e8b6a0e-d410-4228-a371-7c7b8813f618_1200x630.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>If you want to break into a cloud role (Cloud Engineer, Cloud Developer, Software Engineer, DevOps, SRE, Solutions Architect, etc.) and you have an interview coming up, understanding cloud architecture is non-negotiable if you want to stand out in interviews.</p><p>Most candidates focus on certifications or memorising AWS services, but interviews are designed to test something deeper: how you think about building scalable, reliable, and resilient systems.</p><p>In this article, we&#8217;ll look at 5 fundamental architectures you should know. Master them, understand the trade-offs behind them, and you&#8217;ll stand out for the right reasons.</p><p>If you want hands-on practice with these 5 architectures, grab my free PDF, <a href="https://learn.thecloudengineers.com/5-aws-projects-to-get-you-hired">5 AWS Projects To Get You Hired</a>., featuring 5 real-world AWS projects with architecture diagrams and step-by-step implementation guides.</p><p class="button-wrapper" data-attrs="{&quot;url&quot;:&quot;https://learn.thecloudengineers.com/5-aws-projects-to-get-you-hired&quot;,&quot;text&quot;:&quot;Download the FREE PDF&quot;,&quot;action&quot;:null,&quot;class&quot;:null}" data-component-name="ButtonCreateButton"><a class="button primary" href="https://learn.thecloudengineers.com/5-aws-projects-to-get-you-hired"><span>Download the FREE PDF</span></a></p><h2>1. 3-Tier Architecture</h2><p>This is the foundation. Frontend, backend, database: three distinct layers, each with a clear responsibility. Simple in concept, but interviewers expect you to go far beyond drawing three boxes on a whiteboard.</p><p><strong>Key AWS Services:</strong> CloudFront + S3 (frontend), ALB + EC2/ECS with Auto Scaling (backend), RDS Multi-AZ or Aurora (database).</p><p><strong>What interviewers expect you to know:</strong></p><ul><li><p>How to scale each tier independently: stateless backends behind a load balancer, read replicas for database read-heavy workloads.</p></li><li><p>Failure scenarios: what happens when an AZ goes down? How does Multi-AZ RDS failover work?</p></li><li><p>Caching strategies: ElastiCache between backend and database to reduce latency and DB load.</p></li><li><p>The difference between horizontal and vertical scaling, and why horizontal wins at scale.</p></li></ul><p>When discussing this architecture, show that you understand the <em>why</em> behind each layer&#8217;s separation, not just the <em>what</em>.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="https://substackcdn.com/image/fetch/$s_!BV_L!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!BV_L!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png 424w, https://substackcdn.com/image/fetch/$s_!BV_L!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png 848w, https://substackcdn.com/image/fetch/$s_!BV_L!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png 1272w, https://substackcdn.com/image/fetch/$s_!BV_L!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!BV_L!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png" width="330" height="192.95681063122925" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/ceef382e-4853-4b95-ad3e-be06778106a3_602x352.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:352,&quot;width&quot;:602,&quot;resizeWidth&quot;:330,&quot;bytes&quot;:223087,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/198673803?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!BV_L!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png 424w, https://substackcdn.com/image/fetch/$s_!BV_L!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png 848w, https://substackcdn.com/image/fetch/$s_!BV_L!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png 1272w, https://substackcdn.com/image/fetch/$s_!BV_L!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fceef382e-4853-4b95-ad3e-be06778106a3_602x352.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><h2>2. Microservices</h2><p>Breaking a monolith into smaller, independent services sounds clean on paper. In practice, it introduces a whole new category of challenges.</p><p><strong>Key AWS Services:</strong> ECS or EKS, Lambda.</p><p><strong>What interviewers expect you to know:</strong></p><ul><li><p>Trade-offs vs. monoliths: when the operational overhead isn&#8217;t worth it (small teams, early-stage products).</p></li><li><p>Data ownership: each service owns its data store. No shared databases.</p></li><li><p>How you handle failures across service boundaries: circuit breakers, retries with exponential backoff, timeouts.</p></li><li><p>Observability: how do you trace a request that flows through 5 services?</p></li></ul><p>The key insight interviewers look for: you chose microservices because the problem demanded it, not because it was trendy.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="https://substackcdn.com/image/fetch/$s_!FQNE!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!FQNE!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png 424w, https://substackcdn.com/image/fetch/$s_!FQNE!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png 848w, https://substackcdn.com/image/fetch/$s_!FQNE!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png 1272w, https://substackcdn.com/image/fetch/$s_!FQNE!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!FQNE!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png" width="350" height="228.5031847133758" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:410,&quot;width&quot;:628,&quot;resizeWidth&quot;:350,&quot;bytes&quot;:247069,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/198673803?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!FQNE!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png 424w, https://substackcdn.com/image/fetch/$s_!FQNE!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png 848w, https://substackcdn.com/image/fetch/$s_!FQNE!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png 1272w, https://substackcdn.com/image/fetch/$s_!FQNE!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F2ff71116-5051-4e3d-86cb-89a25a512268_628x410.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><h2>3. Serverless</h2><p>No servers to patch, no infrastructure to manage. You can build entire applications without provisioning a single instance.</p><p><strong>Key AWS Services:</strong> Lambda, API Gateway.</p><p><strong>What interviewers expect you to know:</strong></p><ul><li><p>Cold starts: what causes them, how to mitigate</p></li><li><p>Cost model: pay-per-invocation is cheap at low scale but can surprise you with high-throughput workloads. Know the break-even point vs. containers.</p></li><li><p>When NOT to use serverless: long-running processes, workloads needing persistent connections, or latency-critical paths where cold starts are unacceptable.</p></li></ul><p>The interview-winning move is demonstrating that you can evaluate when serverless is the right tool and when it introduces more problems than it solves.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="https://substackcdn.com/image/fetch/$s_!-4AC!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!-4AC!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png 424w, https://substackcdn.com/image/fetch/$s_!-4AC!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png 848w, https://substackcdn.com/image/fetch/$s_!-4AC!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png 1272w, https://substackcdn.com/image/fetch/$s_!-4AC!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!-4AC!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png" width="350" height="125.95541401273886" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:226,&quot;width&quot;:628,&quot;resizeWidth&quot;:350,&quot;bytes&quot;:134361,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/198673803?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!-4AC!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png 424w, https://substackcdn.com/image/fetch/$s_!-4AC!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png 848w, https://substackcdn.com/image/fetch/$s_!-4AC!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png 1272w, https://substackcdn.com/image/fetch/$s_!-4AC!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F186b18d9-c743-40ac-b975-5e5ca054a59c_628x226.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><h2>4. Event-Driven Architecture</h2><p>This is where modern cloud design becomes powerful. Instead of services calling each other directly, they produce and consume events asynchronously. The result: loose coupling, high scalability, and systems that are naturally resilient to spikes in traffic.</p><p><strong>Key AWS Services:</strong> EventBridge, SNS, SQS.</p><p><strong>What interviewers expect you to know:</strong></p><ul><li><p>The difference between queuing (SQS one consumer) and pub/sub (SNS fan-out to many consumers).</p></li><li><p>Eventual consistency: data won&#8217;t be immediately up to date across services. You need to explain how your system handles this.</p></li><li><p>Idempotency: events can be delivered more than once. Your consumers must handle duplicates gracefully.</p></li><li><p>Dead-letter queues: what happens when an event fails processing repeatedly? How do you monitor and replay?</p></li><li><p>A real scenario: an order is placed &#8594; event fires &#8594; inventory, notifications, and analytics services react independently without knowing about each other.</p></li></ul><p>The challenge is showing you can design systems where components don&#8217;t need to know about each other but still behave correctly as a whole.</p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="https://substackcdn.com/image/fetch/$s_!nD2p!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!nD2p!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png 424w, https://substackcdn.com/image/fetch/$s_!nD2p!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png 848w, https://substackcdn.com/image/fetch/$s_!nD2p!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png 1272w, https://substackcdn.com/image/fetch/$s_!nD2p!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!nD2p!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png" width="350" height="163.33333333333334" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:336,&quot;width&quot;:720,&quot;resizeWidth&quot;:350,&quot;bytes&quot;:214449,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/198673803?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!nD2p!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png 424w, https://substackcdn.com/image/fetch/$s_!nD2p!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png 848w, https://substackcdn.com/image/fetch/$s_!nD2p!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png 1272w, https://substackcdn.com/image/fetch/$s_!nD2p!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F69b3eba8-4ac4-47ac-81dd-91ecd984a14a_720x336.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><h2>5. Containers</h2><p>Containers give you consistency across environments and fine-grained control over your runtime. They sit between the full control of EC2 and the abstraction of serverless.</p><p><strong>Key AWS Services:</strong> ECS, EKS, ECR.</p><p><strong>What interviewers expect you to know:</strong></p><ul><li><p>When containers beat serverless: long-running processes, specific runtime needs, workloads needing persistent connections, or apps being migrated from on-premises.</p></li><li><p>When serverless beats containers: short-lived, event-triggered functions with variable traffic.</p></li><li><p>Health checks, rolling deployments, and blue/green strategies for zero-downtime updates.</p></li><li><p>You don&#8217;t need to be a Kubernetes expert. But you should understand pods, services, and why teams choose (or avoid) K8s.</p></li></ul><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="https://substackcdn.com/image/fetch/$s_!aAsV!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!aAsV!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png 424w, https://substackcdn.com/image/fetch/$s_!aAsV!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png 848w, https://substackcdn.com/image/fetch/$s_!aAsV!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png 1272w, https://substackcdn.com/image/fetch/$s_!aAsV!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!aAsV!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png" width="350" height="129.34782608695653" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:272,&quot;width&quot;:736,&quot;resizeWidth&quot;:350,&quot;bytes&quot;:197437,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/198673803?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!aAsV!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png 424w, https://substackcdn.com/image/fetch/$s_!aAsV!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png 848w, https://substackcdn.com/image/fetch/$s_!aAsV!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png 1272w, https://substackcdn.com/image/fetch/$s_!aAsV!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F1d1f25da-905b-45e9-8b73-13ce5fd50988_736x272.png 1456w" sizes="100vw" loading="lazy"></picture><div></div></div></a></figure></div><h2>Conclusion</h2><p>These five architectures cover the vast majority of what you&#8217;ll face in cloud interviews. You don&#8217;t need to memorise every AWS service. You need to understand patterns, trade-offs, and when to apply each one.</p><p>The candidates who stand out are the ones who can explain <em>why</em> they chose an architecture, not just draw it on a board. Show your reasoning. Discuss trade-offs. Acknowledge limitations.</p><p>Cloud interviews are rarely about knowing the &#8220;correct&#8221; AWS service. They&#8217;re about proving you can make good engineering decisions under constraints.</p><p>If you want hands-on practice with these 5 architectures, grab my free PDF, <a href="https://learn.thecloudengineers.com/5-aws-projects-to-get-you-hired">5 AWS Projects To Get You Hired</a>., featuring 5 real-world AWS projects with architecture diagrams and step-by-step implementation guides.</p><p class="button-wrapper" data-attrs="{&quot;url&quot;:&quot;https://learn.thecloudengineers.com/5-aws-projects-to-get-you-hired&quot;,&quot;text&quot;:&quot;Download the FREE PDF&quot;,&quot;action&quot;:null,&quot;class&quot;:&quot;button-wrapper&quot;}" data-component-name="ButtonCreateButton"><a class="button primary button-wrapper" href="https://learn.thecloudengineers.com/5-aws-projects-to-get-you-hired"><span>Download the FREE PDF</span></a></p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[Building Multi-Agent Workflows on Lambda Durable Functions]]></title><description><![CDATA[Multi-agent systems are everywhere now. Every team wants autonomous agents collaborating on complex tasks, research, planning, execution, validation.]]></description><link>https://blog.thecloudengineers.com/p/building-multi-agent-workflows-on</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/building-multi-agent-workflows-on</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 20 May 2026 09:30:48 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/cd5cd993-54d8-4858-ba63-b7c6f0c324d6_1200x630.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>Multi-agent systems are everywhere now. Every team wants autonomous agents collaborating on complex tasks, research, planning, execution, validation. The problem? Orchestrating multiple agents that need to wait on each other, handle failures gracefully, and maintain state across long-running conversations is painful. We&#8217;ve been duct-taping this together with Step Functions, SQS queues, and DynamoDB state tables for too long.</p><p>Lambda Durable Functions change the game here. In this article we will walk through why durable functions are a natural fit for multi-agent orchestration, design a document processing pipeline with four agents, and show how the architecture holds together without a single line of state management code.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><h2>Why Durable Functions for Multi-Agent</h2><p>Standard Lambda functions run start-to-finish in a single invocation. If something fails midway, you retry everything. For a multi-agent workflow where Agent A researches, Agent B plans, Agent C executes, and Agent D validates. That&#8217;s unacceptable. You can&#8217;t re-run a 4-minute research phase because the validation agent hit a transient error.</p><p>Durable functions automatically checkpoint progress, suspend execution for up to one year during long-running tasks, and recover from failures. No custom state management. No DynamoDB tables tracking &#8220;which step are we on.&#8221; The runtime handles it.</p><p>This is exactly what multi-agent orchestration needs: reliable progress tracking across agents that may take seconds or minutes to respond, with automatic recovery when things go wrong.</p><h2>The Example: Document Processing Pipeline</h2><p>Let&#8217;s see an example of a document processing pipeline and how we can build it with Lambda durable functions. We have four agents and one durable function orchestrating them. The agents are:</p><ul><li><p><strong>Classifier Agent</strong> &#8212; Reads an incoming document, determines its type (invoice, contract, support ticket), and extracts metadata.</p></li><li><p><strong>Enrichment Agent</strong> &#8212; Takes the classification, pulls additional context from internal systems, and augments the document with business context.</p></li><li><p><strong>Decision Agent</strong> &#8212; Evaluates the enriched document against business rules and decides the routing: auto-approve, escalate, or reject.</p></li><li><p><strong>Action Agent</strong> &#8212; Executes the decision: files the document, notifies stakeholders, or triggers downstream workflows.</p></li></ul><h2>Architecture</h2><pre><code><code>&#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;
&#9474;                     Lambda Durable Function (Orchestrator)                  &#9474;
&#9474;                                                                             &#9474;
&#9474;  &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;    &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;    &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;    &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;   &#9474;
&#9474;  &#9474; Checkpoint 1 &#9474;    &#9474; Checkpoint 2 &#9474;    &#9474; Checkpoint 3 &#9474;    &#9474; Checkpoint 4 &#9474;  
&#9474;  &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;    &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;    &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;    &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;   &#9474;
&#9474;         &#9474;                  &#9474;                  &#9474;                  &#9474;          &#9474;
&#9474;         &#9660;                  &#9660;                  &#9660;                  &#9660;          &#9474;
&#9474;  &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;    &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;    &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;    &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;   &#9474;
&#9474;  &#9474;  Step 1:    &#9474;    &#9474;  Step 2:    &#9474;    &#9474;  Step 3:    &#9474;    &#9474;  Step 4:    &#9474;   &#9474;
&#9474;  &#9474;  Classify   &#9474;&#9472;&#9472;&#9472;&#9654;&#9474;  Enrich     &#9474;&#9472;&#9472;&#9472;&#9654;&#9474;  Decide     &#9474;&#9472;&#9472;&#9472;&#9654;&#9474;  Act        &#9474;   &#9474;
&#9474;  &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;    &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;    &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;    &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;   &#9474;
&#9474;         &#9474;                  &#9474;                  &#9474;                  &#9474;          &#9474;
&#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9532;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9532;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9532;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9532;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;
          &#9474;                  &#9474;                  &#9474;                  &#9474;
          &#9660;                  &#9660;                  &#9660;                  &#9660;
&#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;  &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;  &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;  &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;
&#9474;  Classifier     &#9474;  &#9474;  Enrichment     &#9474;  &#9474;  Decision       &#9474;  &#9474;  Action         &#9474;
&#9474;  Agent          &#9474;  &#9474;  Agent          &#9474;  &#9474;  Agent          &#9474;  &#9474;  Agent          &#9474;
&#9474;  (Lambda)       &#9474;  &#9474;  (Lambda)       &#9474;  &#9474;  (Lambda)       &#9474;  &#9474;  (Lambda)       &#9474;
&#9474;                 &#9474;  &#9474;                 &#9474;  &#9474;                 &#9474;  &#9474;                 &#9474;
&#9474;  - Reads doc    &#9474;  &#9474;  - Pulls context&#9474;  &#9474;  - Evaluates    &#9474;  &#9474;  - Files doc    &#9474;
&#9474;  - Classifies   &#9474;  &#9474;  - Calls APIs   &#9474;  &#9474;    rules        &#9474;  &#9474;  - Notifies     &#9474;
&#9474;  - Extracts     &#9474;  &#9474;  - Augments     &#9474;  &#9474;  - Routes       &#9474;  &#9474;  - Triggers     &#9474;
&#9474;    metadata     &#9474;  &#9474;    metadata     &#9474;  &#9474;                 &#9474;  &#9474;    downstream   &#9474;
&#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;  &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;  &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;  &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9516;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;
         &#9474;                    &#9474;                    &#9474;                     &#9474;
         &#9660;                    &#9660;                    &#9660;                     &#9660;
&#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;  &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;  &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;  &#9484;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9488;
&#9474;  Amazon Bedrock &#9474;  &#9474;  Internal APIs  &#9474;  &#9474;  Human Review   &#9474;  &#9474;  S3 / SNS /     &#9474;
&#9474;  (LLM)          &#9474;  &#9474;  (DynamoDB,     &#9474;  &#9474;  (Callback -    &#9474;  &#9474;  EventBridge    &#9474;
&#9474;                 &#9474;  &#9474;   other svcs)   &#9474;  &#9474;   Wait/Resume)  &#9474;  &#9474;                 &#9474;
&#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;  &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;  &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;  &#9492;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9472;&#9496;
</code></code></pre><h2>The Flow</h2><p>The durable function receives a document event. It invokes the Classifier Agent as a durable step and progress is checkpointed. If Lambda recycles the execution environment after classification completes, the function resumes from that checkpoint, not from scratch.</p><p>The Classifier&#8217;s output feeds into the Enrichment Agent. Another durable step, another checkpoint. The Enrichment Agent might call external APIs that take 30 seconds. The durable function suspends, pays nothing while waiting, and resumes when enrichment completes.</p><p>Here&#8217;s where it gets interesting. The Decision Agent might determine that a human needs to review this document. The durable function uses a wait where it suspends execution entirely, for hours or days if needed, until a callback arrives with the human&#8217;s decision. No polling. No idle compute. The function simply resumes where it left off.</p><p>Finally, the Action Agent executes. If it fails, maybe a downstream system is temporarily unavailable, the durable function retries that specific step without re-running classification, enrichment, or decision. Four agents, one orchestration function, zero state management infrastructure.</p><h2>Why This Beats the Alternative</h2><p>Before durable functions, this same workflow required: a Step Functions state machine, DynamoDB for intermediate state, SQS queues between agents, dead-letter queues for failures, and CloudWatch alarms for stuck executions. That&#8217;s five services to manage for what is conceptually a single workflow.</p><p>With durable functions, it&#8217;s one Lambda function. Same programming model you already know. Same event handler. Same integrations. The durability is built into the execution model itself.</p><h2>The Trade-Off</h2><p>Durable functions use a checkpoint-replay model. Every time execution resumes, it replays from the last checkpoint. This means your orchestration logic must be deterministic, so no random values, no reading the current time for branching decisions outside of durable steps. This is a constraint worth understanding upfront.</p><p>For multi-agent workflows specifically, this is rarely a problem. Your orchestration logic is typically: call agent, get result, pass to next agent. That&#8217;s inherently deterministic.</p><h2>When to Reach for This</h2><p>Multi-agent workflows that involve waiting on humans, on slow external systems, on other agents, are the sweet spot. If your agents all respond in under a second and never fail, you probably don&#8217;t need durability. But that&#8217;s not the real world.</p><p>In the real world, agents call LLMs that timeout, external APIs that rate-limit, and humans that go to lunch. Durable functions handle all of that without you writing a single line of state management logic.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[How to Get the Most Out of Tech Events]]></title><description><![CDATA[I&#8217;ve attended a couple of tech events over the past two weeks, and they reminded me just how much value is sitting right there, if you know how to look for it. Most people show up, sit through sessions, and leave. But the real ROI of a tech event goes well beyond the agenda.]]></description><link>https://blog.thecloudengineers.com/p/how-to-get-the-most-out-of-tech-events</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/how-to-get-the-most-out-of-tech-events</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 13 May 2026 09:31:02 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/ffed0439-563d-4f70-8bcc-dc7b617a49b5_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>I&#8217;ve attended a couple of tech events over the past two weeks, and they reminded me just how much value is sitting right there, if you know how to look for it. Most people show up, sit through sessions, and leave. But the real ROI of a tech event goes well beyond the agenda.</p><p>Here&#8217;s what I&#8217;ve learned about making the most of them.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="https://substackcdn.com/image/fetch/$s_!_hO2!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!_hO2!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png 424w, https://substackcdn.com/image/fetch/$s_!_hO2!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png 848w, https://substackcdn.com/image/fetch/$s_!_hO2!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png 1272w, https://substackcdn.com/image/fetch/$s_!_hO2!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!_hO2!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png" width="1456" height="1095" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/c482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:1095,&quot;width&quot;:1456,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:4094003,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/195838348?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!_hO2!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png 424w, https://substackcdn.com/image/fetch/$s_!_hO2!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png 848w, https://substackcdn.com/image/fetch/$s_!_hO2!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png 1272w, https://substackcdn.com/image/fetch/$s_!_hO2!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fc482e42c-d6c6-438b-b624-7130606d3ffa_1952x1468.png 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><h2>1. Do Your Research Beforehand</h2><p>Walking into an event blind is a missed opportunity. Before you even step through the door, check the agenda. Which sessions are actually worth your time? Which workshops align with what you&#8217;re working on right now? Who&#8217;s speaking, and more importantly, who&#8217;s attending?</p><p>Identify two or three people you&#8217;d genuinely like to connect with. Not just big names, but people whose work you follow, whose problems overlap with yours, or whose perspective you&#8217;d find valuable. Having that list in your head changes how you move through the event. You stop wandering and start being intentional.</p><h2>2. Don&#8217;t Just Attend &#8212; Connect</h2><p>This is where most people leave value on the table. They attend the sessions, they clap at the end, and they head to the next room. But the conversations that happen in the hallways, at the coffee station, or right after a talk? Those are often worth more than the talk itself.</p><p>Talk to speakers. Ask them a follow-up question. Share your perspective on something they said. Disagree, even &#8212; respectfully. The best conversations I&#8217;ve had at events started with &#8220;I see it slightly differently, here&#8217;s why.&#8221;</p><p>Networking isn&#8217;t about collecting business cards or LinkedIn connections. It&#8217;s about meaningful exchange. One real conversation with the right person can open a door that no session ever could.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="https://substackcdn.com/image/fetch/$s_!aAeh!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!aAeh!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png 424w, https://substackcdn.com/image/fetch/$s_!aAeh!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png 848w, https://substackcdn.com/image/fetch/$s_!aAeh!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png 1272w, https://substackcdn.com/image/fetch/$s_!aAeh!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!aAeh!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png" width="1456" height="1095" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/ea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:1095,&quot;width&quot;:1456,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:4505185,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/195838348?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!aAeh!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png 424w, https://substackcdn.com/image/fetch/$s_!aAeh!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png 848w, https://substackcdn.com/image/fetch/$s_!aAeh!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png 1272w, https://substackcdn.com/image/fetch/$s_!aAeh!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fea475762-9b7f-47a4-8f8f-bbb294cb6c5b_1952x1468.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><h2>3. Participate Actively</h2><p>Side events, workshops, roundtables, and hackathons are where the real engagement happens. The more you put in, the more you get out. It sounds obvious, but most people default to passive attendance.</p><p>When you participate actively, you become memorable. People remember the person who asked the sharp question, who contributed to the workshop discussion, who showed up to the evening side event when everyone else went back to the hotel. That presence compounds over time.</p><h2>4. Capture and Apply Insights</h2><p>Take notes. Not on everything, but on what genuinely stands out. A new mental model. A tool you hadn&#8217;t heard of. A framing of a problem that clicked. A name someone mentioned three times.</p><p>The real value isn&#8217;t in the notes themselves. It&#8217;s in what you do with them afterward. Block time in the week after the event to review what you captured and identify one or two things you can actually apply. That&#8217;s the difference between an event that felt good and one that moved the needle.</p><h2>The Right Measure of Success</h2><p>Here&#8217;s a reframe that changed how I approach events: you don&#8217;t need to walk away with ten new contacts, a notebook full of insights, and a job offer to call it a success.</p><p><strong>If you leave with one valuable new connection, one useful takeaway, or simply a great experience that reminded you why you&#8217;re in this field &#8212; that&#8217;s a win</strong>. Set that bar, and you&#8217;ll almost always clear it.</p><p>The mistake is treating events as passive consumption. The sessions are the structure, but the value is in how you engage with everything around them. Come prepared, stay curious, and be willing to start a conversation.</p><p>That&#8217;s where the real return is.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item><item><title><![CDATA[Spec-Driven Development on AWS]]></title><description><![CDATA[We&#8217;ve all been there. A service gets deployed, an API route goes live, and three weeks later someone asks, &#8220;Wait, what does this endpoint actually do?&#8221;]]></description><link>https://blog.thecloudengineers.com/p/spec-driven-development-on-aws</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/spec-driven-development-on-aws</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 06 May 2026 09:31:15 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/212c770b-a9f5-4658-a2ad-b9f28602fd65_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p><em>Hey, it&#8217;s Lefteris &#128075; I&#8217;m the voice behind the weekly newsletter &#8220;The Cloud Engineers.&#8221;</em></p><p>We&#8217;ve all been there. A service gets deployed, an API route goes live, and three weeks later someone asks, <em>&#8220;Wait, what does this endpoint actually do?&#8221;</em> The answer lives in someone&#8217;s head, a Slack thread, or a Confluence page nobody has updated since the initial design meeting. That&#8217;s the problem <strong>Spec-Driven Development (SDD)</strong> solves, and on AWS, it changes how you build, test, and evolve systems regardless of whether you&#8217;re running Lambda, ECS, EKS, or EC2.</p><p>This hands-on <strong><a href="https://www.eventbrite.co.uk/e/hands-on-spec-driven-development-workshop-cohort-2-tickets-1985498625838?aff=lefteris">Spec-Driven Development workshop</a></strong> is built for that exact problem. Instead of watching demos, you&#8217;ll build a real application while learning how to define clear specs and guide AI to produce reliable, production-ready outputs.</p><p>After a sold-out first cohort, Cohort 2 is now open.</p><p><strong>&#128073; Register here:</strong> <a href="https://www.eventbrite.co.uk/e/hands-on-spec-driven-development-workshop-cohort-2-tickets-1985498625838?aff=lefteris">https://www.eventbrite.co.uk/e/hands-on-spec-driven-development-workshop-cohort-2-tickets-1985498625838?aff=lefteris</a></p><p>Use code <strong>SD40</strong> for 40% off</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="https://substackcdn.com/image/fetch/$s_!WjTi!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!WjTi!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png 424w, https://substackcdn.com/image/fetch/$s_!WjTi!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png 848w, https://substackcdn.com/image/fetch/$s_!WjTi!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png 1272w, https://substackcdn.com/image/fetch/$s_!WjTi!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!WjTi!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png" width="1280" height="640" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/a81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:640,&quot;width&quot;:1280,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:320866,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:null,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/195966748?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!WjTi!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png 424w, https://substackcdn.com/image/fetch/$s_!WjTi!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png 848w, https://substackcdn.com/image/fetch/$s_!WjTi!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png 1272w, https://substackcdn.com/image/fetch/$s_!WjTi!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Fa81f9755-3206-49cb-b25a-090fa001ea0c_1280x640.png 1456w" sizes="100vw" fetchpriority="high"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p class="button-wrapper" data-attrs="{&quot;url&quot;:&quot;https://www.eventbrite.co.uk/e/hands-on-spec-driven-development-workshop-cohort-2-tickets-1985498625838?aff=lefteris&quot;,&quot;text&quot;:&quot;Spec-Driven Workshop at 40% off&quot;,&quot;action&quot;:null,&quot;class&quot;:null}" data-component-name="ButtonCreateButton"><a class="button primary" href="https://www.eventbrite.co.uk/e/hands-on-spec-driven-development-workshop-cohort-2-tickets-1985498625838?aff=lefteris"><span>Spec-Driven Workshop at 40% off</span></a></p><h2>What Is Spec-Driven Development?</h2><p>Spec-Driven Development is a practice where the contract, also know as specification, is written before any implementation begins. The spec becomes the single source of truth. Everything else, the application logic, the infrastructure configuration, the event schemas, derives from it.</p><p>This isn&#8217;t documentation-first development in the old sense. It&#8217;s not about writing a Word document before you code. It&#8217;s about defining the shape of your system - inputs, outputs, events, errors - in a machine-readable format that your tooling, your tests, and your team can all reason about simultaneously.</p><h2>Why It Matters Across AWS Architectures</h2><p>The need for specs is a distributed systems problem, and AWS workloads are distributed by nature, whether you&#8217;re running microservices on ECS Fargate, a data pipeline on EMR, a real-time processing layer on Kinesis, or a containerized platform on EKS.</p><p>Every boundary between components is a contract. A service on ECS calling another service over HTTP, a Kafka consumer reading from MSK, an EKS pod publishing to an SQS queue, each of these is an implicit agreement about shape, behavior, and failure modes. Without a spec, that agreement is undocumented and fragile.</p><p>We&#8217;ve seen this break in predictable ways. A team running microservices on ECS changes the response schema of an internal API. The downstream service starts returning 500s. No contract test caught it. No spec was ever written. The failure surfaces in production, during peak traffic, after a deployment that passed all unit tests. A spec would have made that breaking change visible before it shipped.</p><p>The same pattern plays out in data engineering. A Glue job changes the shape of a Parquet file it writes to S3. The Athena queries downstream start failing. The schema was never formally defined, it was inferred from the data. An explicit schema contract, enforced at write time, would have caught the drift immediately.</p><h2>Where Kiro Changes the Game</h2><p>This is where AWS&#8217;s agentic IDE, <a href="https://kiro.dev/">Kiro</a>, becomes directly relevant to how we practice SDD.</p><p>Kiro inverts the model most AI coding tools use. Kiro starts with the spec. When you describe a feature or a system in natural language, Kiro doesn&#8217;t generate code. It generates a structured specification first. That spec lives in three artifacts: <code>requirements.md</code>, <code>design.md</code>, and <code>tasks.md</code>.</p><div class="captioned-image-container"><figure><a class="image-link image2 is-viewable-img" target="_blank" href="https://substackcdn.com/image/fetch/$s_!gfi2!,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!gfi2!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png 424w, https://substackcdn.com/image/fetch/$s_!gfi2!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png 848w, https://substackcdn.com/image/fetch/$s_!gfi2!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png 1272w, https://substackcdn.com/image/fetch/$s_!gfi2!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!gfi2!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png" width="1456" height="972" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:972,&quot;width&quot;:1456,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:null,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:null,&quot;href&quot;:null,&quot;belowTheFold&quot;:true,&quot;topImage&quot;:false,&quot;internalRedirect&quot;:null,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!gfi2!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png 424w, https://substackcdn.com/image/fetch/$s_!gfi2!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png 848w, https://substackcdn.com/image/fetch/$s_!gfi2!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png 1272w, https://substackcdn.com/image/fetch/$s_!gfi2!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2F53172af3-9f76-4998-a810-c59b721dc379_1738x1160.png 1456w" sizes="100vw" loading="lazy"></picture><div class="image-link-expand"><div class="pencraft pc-display-flex pc-gap-8 pc-reset"><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container restack-image"><svg aria-hidden="true" width="20" height="20" viewBox="0 0 20 20" fill="none" stroke-width="1.5" stroke="var(--color-fg-primary)" stroke-linecap="round" stroke-linejoin="round" xmlns="http://www.w3.org/2000/svg"><g><path d="M2.53001 7.81595C3.49179 4.73911 6.43281 2.5 9.91173 2.5C13.1684 2.5 15.9537 4.46214 17.0852 7.23684L17.6179 8.67647M17.6179 8.67647L18.5002 4.26471M17.6179 8.67647L13.6473 6.91176M17.4995 12.1841C16.5378 15.2609 13.5967 17.5 10.1178 17.5C6.86118 17.5 4.07589 15.5379 2.94432 12.7632L2.41165 11.3235M2.41165 11.3235L1.5293 15.7353M2.41165 11.3235L6.38224 13.0882"></path></g></svg></button><button tabindex="0" type="button" class="pencraft pc-reset pencraft icon-container view-image"><svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-maximize2 lucide-maximize-2"><polyline points="15 3 21 3 21 9"></polyline><polyline points="9 21 3 21 3 15"></polyline><line x1="21" x2="14" y1="3" y2="10"></line><line x1="3" x2="10" y1="21" y2="14"></line></svg></button></div></div></div></a></figure></div><p>The <strong>requirements file</strong> expands your prompt into user stories with acceptance criteria written in EARS notation, a structured format that captures preconditions, triggers, and expected system responses, including edge cases that would otherwise surface during implementation. The <strong>design file</strong> produces a technical design document covering architecture decisions and sequence diagrams. The <strong>tasks file</strong> breaks the design into discrete, sequenced implementation steps with dependency tracking. Only after you review and approve those artifacts does Kiro begin writing code.</p><p>This is spec-driven development operationalized inside your IDE. The spec isn&#8217;t a side artifact you produce reluctantly. It&#8217;s the primary artifact the entire workflow is built around. Code becomes the build output of the spec, not the other way around.</p><p>For teams building on AWS, this matters because it forces the contract conversation to happen before a single line of application or infrastructure code is written. Whether you&#8217;re defining an API contract between two ECS services, an event schema for an EventBridge rule, or the interface between a CDK construct and the team consuming it, all of it gets defined and reviewed at the spec level, not discovered during a production incident.</p><h2>The Spec as the Center of Gravity</h2><p>The shift SDD requires is treating the spec as the artifact that drives everything else, not as something you generate after the fact.</p><p>When we start a new API, the OpenAPI spec is written first. The service is built to satisfy it. The tests validate against it. When a consumer team needs to integrate, we hand them the spec, not a Slack message. The same principle applies to infrastructure. Before a new CDK construct is published for internal use, its interface contract is defined and reviewed. Breaking changes are explicit. They show up in the diff before they show up in a broken pipeline.</p><p>This approach forces clarity early. You can&#8217;t write a spec for something you haven&#8217;t thought through. The act of speccing a service or an event forces you to answer questions you&#8217;d otherwise defer: What are the required fields? What are the error states? What does a partial failure look like? What&#8217;s the versioning strategy?</p><h2>The Discipline It Demands</h2><p>Adopting SDD, with or without Kiro, requires a workflow shift.</p><ul><li><p><strong>Design reviews happen at the spec level.</strong> Before any service is built, the team reviews the OpenAPI, AsyncAPI, or infrastructure spec. This is where architectural decisions get made, not in code review.</p></li><li><p><strong>Mocking becomes trivial.</strong> A spec-first API can be mocked immediately. Consumer teams don&#8217;t wait for implementation. Parallel development becomes the default.</p></li><li><p><strong>Breaking changes become visible.</strong> When the spec is versioned and diffed, breaking changes are explicit. A field removal or type change shows up in the diff before it shows up in a production incident.</p></li><li><p><strong>Onboarding accelerates.</strong> A new engineer joining the team can understand the system&#8217;s boundaries by reading the specs. The spec is the architecture, expressed precisely.</p></li></ul><p>The temptation is always to skip the spec and start building, especially under deadline pressure. But the cost of that shortcut compounds. Every undocumented contract is technical debt that accrues interest in the form of production incidents, integration failures, and onboarding friction. Kiro makes that discipline easier to maintain by making the spec the default starting point, not an afterthought.</p><p>Write the spec first. Build to it. Everything else follows.</p><div><hr></div><p>AI can get you to the first feature fast, but most developers struggle when the system starts to grow.</p><p>This hands-on <strong>Spec-Driven Development workshop</strong> is built for that exact problem. Instead of watching demos, you&#8217;ll build a real application while learning how to define clear specs and guide AI to produce reliable, production-ready outputs.</p><p>After a sold-out first cohort, Cohort 2 is now open.</p><p>Register here: <a href="https://www.eventbrite.co.uk/e/hands-on-spec-driven-development-workshop-cohort-2-tickets-1985498625838?aff=lefteris">https://www.eventbrite.co.uk/e/hands-on-spec-driven-development-workshop-cohort-2-tickets-1985498625838?aff=lefteris</a></p><p>Use code <strong>SDD40</strong> for 40% off</p><p class="button-wrapper" data-attrs="{&quot;url&quot;:&quot;https://www.eventbrite.co.uk/e/hands-on-spec-driven-development-workshop-cohort-2-tickets-1985498625838?aff=lefteris&quot;,&quot;text&quot;:&quot;Spec-Driven Workshop at 40% off&quot;,&quot;action&quot;:null,&quot;class&quot;:&quot;button-wrapper&quot;}" data-component-name="ButtonCreateButton"><a class="button primary button-wrapper" href="https://www.eventbrite.co.uk/e/hands-on-spec-driven-development-workshop-cohort-2-tickets-1985498625838?aff=lefteris"><span>Spec-Driven Workshop at 40% off</span></a></p><div><hr></div><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div>]]></content:encoded></item><item><title><![CDATA[5 Hands-On AWS Projects That Will Prepare You for the SAA-C03]]></title><description><![CDATA[Most people study for the AWS Solutions Architect Associate by watching 40 hours of video and memorizing answers.]]></description><link>https://blog.thecloudengineers.com/p/5-hands-on-aws-projects-that-will</link><guid isPermaLink="false">https://blog.thecloudengineers.com/p/5-hands-on-aws-projects-that-will</guid><dc:creator><![CDATA[Lefteris Karageorgiou]]></dc:creator><pubDate>Wed, 29 Apr 2026 09:30:41 GMT</pubDate><enclosure url="https://substack-post-media.s3.amazonaws.com/public/images/4172ed57-b685-4720-b287-bc0ef32c47f9_1731x909.png" length="0" type="image/jpeg"/><content:encoded><![CDATA[<p>Most people study for the AWS Solutions Architect Associate by watching 40 hours of video and memorizing answers. Then they get to a real job and freeze.</p><p>I took a different approach. I built projects that forced me to understand the services deeply, not just what they do, but <em>why</em> you&#8217;d choose them, what breaks under load, and how the pieces connect. I passed the SAA-C03 and could talk confidently in interviews about real implementations. Here are the 5 projects I recommend.</p><div><hr></div><h1>Sponsored by Salesforce</h1><h3>Cross-Platform Consistency with Agentforce AXL</h3><p>If you&#8217;ve ever tried to maintain brand and logic parity for an AI agent across Slack, web, and mobile, you know the pain. Enter the Agentforce Experience Layer (AXL). This new abstraction layer allows you to define agent logic and UI components once and have them render natively across any surface&#8212;including third-party platforms like Microsoft Teams.<br><br><a href="https://www.salesforce.com/plus/experience/tdx_2026?d=701ed00000iqbXAAAY&amp;nc=7013y0000022u2tAAA&amp;utm_source=loomify&amp;utm_medium=tp_email&amp;utm_campaign=emea_is_cross-cloud_cross-industry&amp;utm_content=all-segments_pg-mtp_701ed00000iqbXAAAY_english_tdx-2026">Stream the AXL Orchestration Session</a></p><div class="captioned-image-container"><figure><a class="image-link image2" target="_blank" href="https://www.salesforce.com/plus/experience/tdx_2026?d=701ed00000iqbXAAAY&amp;nc=7013y0000022u2tAAA&amp;utm_source=loomify&amp;utm_medium=tp_email&amp;utm_campaign=emea_is_cross-cloud_cross-industry&amp;utm_content=all-segments_pg-mtp_701ed00000iqbXAAAY_english_tdx-2026" data-component-name="Image2ToDOM"><div class="image2-inset"><picture><source type="image/webp" srcset="https://substackcdn.com/image/fetch/$s_!ViTl!,w_424,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png 424w, https://substackcdn.com/image/fetch/$s_!ViTl!,w_848,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png 848w, https://substackcdn.com/image/fetch/$s_!ViTl!,w_1272,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png 1272w, https://substackcdn.com/image/fetch/$s_!ViTl!,w_1456,c_limit,f_webp,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png 1456w" sizes="100vw"><img src="https://substackcdn.com/image/fetch/$s_!ViTl!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png" width="1456" height="364" data-attrs="{&quot;src&quot;:&quot;https://substack-post-media.s3.amazonaws.com/public/images/fd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png&quot;,&quot;srcNoWatermark&quot;:null,&quot;fullscreen&quot;:null,&quot;imageSize&quot;:null,&quot;height&quot;:364,&quot;width&quot;:1456,&quot;resizeWidth&quot;:null,&quot;bytes&quot;:984968,&quot;alt&quot;:null,&quot;title&quot;:null,&quot;type&quot;:&quot;image/png&quot;,&quot;href&quot;:&quot;https://www.salesforce.com/plus/experience/tdx_2026?d=701ed00000iqbXAAAY&amp;nc=7013y0000022u2tAAA&amp;utm_source=loomify&amp;utm_medium=tp_email&amp;utm_campaign=emea_is_cross-cloud_cross-industry&amp;utm_content=all-segments_pg-mtp_701ed00000iqbXAAAY_english_tdx-2026&quot;,&quot;belowTheFold&quot;:false,&quot;topImage&quot;:true,&quot;internalRedirect&quot;:&quot;https://blog.thecloudengineers.com/i/194500231?img=https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png&quot;,&quot;isProcessing&quot;:false,&quot;align&quot;:null,&quot;offset&quot;:false}" class="sizing-normal" alt="" srcset="https://substackcdn.com/image/fetch/$s_!ViTl!,w_424,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png 424w, https://substackcdn.com/image/fetch/$s_!ViTl!,w_848,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png 848w, https://substackcdn.com/image/fetch/$s_!ViTl!,w_1272,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png 1272w, https://substackcdn.com/image/fetch/$s_!ViTl!,w_1456,c_limit,f_auto,q_auto:good,fl_progressive:steep/https%3A%2F%2Fsubstack-post-media.s3.amazonaws.com%2Fpublic%2Fimages%2Ffd8bfbce-a145-4fb9-9cc9-252cd095bda9_2048x512.png 1456w" sizes="100vw" fetchpriority="high"></picture><div></div></div></a></figure></div><h3><a href="https://www.salesforce.com/plus/experience/tdx_2026?d=701ed00000iqbXAAAY&amp;nc=7013y0000022u2tAAA&amp;utm_source=loomify&amp;utm_medium=tp_email&amp;utm_campaign=emea_is_cross-cloud_cross-industry&amp;utm_content=all-segments_pg-mtp_701ed00000iqbXAAAY_english_tdx-2026">Watch the developer conference of the year. On demand on Salesforce+</a></h3><p>Agentic AI is changing the game and Agentforce is leading the way. Watch TDX on demand to explore dozens of sessions covering the latest innovations across Agentforce, Data 360, the core platform, vibe coding, Slack, and more. All free on Salesforce+.</p><p><strong>Watch TDX on Salesforce+ to:</strong></p><ul><li><p>Get roadmap insights from the leaders shaping what&#8217;s next</p></li><li><p>Access broadcast-only moments and exclusive interviews</p></li></ul><p>It all starts with the main keynote, where you&#8217;ll experience the future of software and learn how to build it. Watch it now and catch every moment at your own pace.</p><h3><strong>&#128073; <a href="https://www.salesforce.com/plus/experience/tdx_2026?d=701ed00000iqbXAAAY&amp;nc=7013y0000022u2tAAA&amp;utm_source=loomify&amp;utm_medium=tp_email&amp;utm_campaign=emea_is_cross-cloud_cross-industry&amp;utm_content=all-segments_pg-mtp_701ed00000iqbXAAAY_english_tdx-2026">Watch Now</a></strong></h3><div><hr></div><p>Let&#8217;s now go back to our article and see the 5 projects.</p><h2>Project 1: Three-Tier Web Application</h2><p><strong>What you build:</strong> A custom VPC with public and private subnets, an Application Load Balancer, an Auto Scaling Group, and an RDS database.</p><p><strong>Why it matters:</strong> This is the foundational architecture pattern behind almost every production web workload on AWS. The exam tests it constantly, and so does every technical interview.</p><p>The critical insight here is <em>traffic flow</em>. Your ALB lives in the public subnet and accepts inbound traffic on port 443. Your EC2 instances sit in private subnets and only accept traffic from the ALB&#8217;s security group, not from the internet. Your RDS instance sits in a separate private subnet and only accepts traffic from the EC2 security group. Nothing in the data tier is ever directly reachable.</p><p>When you build this yourself, you stop memorizing &#8220;databases should be private&#8221; and start understanding <em>why</em>: defense in depth, blast radius reduction, and compliance requirements that mandate network isolation. You also learn where Auto Scaling actually helps, horizontal scaling behind the ALB, and where it doesn&#8217;t, like a single-AZ RDS instance that becomes your bottleneck at 500 concurrent connections.</p><p><strong>What the exam will ask:</strong> Multi-AZ RDS failover behavior, ALB vs. NLB selection criteria, and how security group rules differ from NACLs. Build this project and those questions answer themselves.</p><h2>Project 2: Serverless Image Processing Pipeline</h2><p><strong>What you build:</strong> An S3 upload triggers Lambda, which resizes the image, stores metadata in DynamoDB, and sends an SNS notification.</p><p><strong>Why it matters:</strong> Event-driven architecture is the dominant pattern in modern cloud systems. This project teaches you how AWS services communicate asynchronously, and what happens when they don&#8217;t.</p><p>The flow looks simple: S3 event &#8594; Lambda &#8594; DynamoDB write + SNS publish. But building it forces you to confront real decisions. What&#8217;s your Lambda timeout? If image processing takes 8 seconds and you set 5, you&#8217;ll see silent failures. What&#8217;s your DynamoDB write capacity? If you&#8217;re processing 200 images per minute and your table is provisioned for 50 WCU, you&#8217;ll hit throttling. What happens to the SNS notification if the DynamoDB write fails? You&#8217;ll need to think about idempotency and partial failure handling.</p><p><strong>What the exam will ask:</strong> S3 event notification targets, Lambda concurrency limits, DynamoDB capacity modes, and SNS delivery guarantees. This project covers all of them.</p><h2>Project 3: Disaster Recovery Solution</h2><p><strong>What you build:</strong> Cross-region S3 replication, automated RDS backups, and Route 53 failover routing.</p><p><strong>Why it matters:</strong> DR is one of the most heavily tested domains on the SAA-C03, and it&#8217;s also one of the most misunderstood in practice. Most candidates can recite the four DR strategies. Few can explain the trade-offs that determine which one you&#8217;d actually choose.</p><p>Building this project forces you to internalize the RTO/RPO trade-off with real numbers. Cross-region S3 replication gives you near-zero RPO for object storage, replication typically completes in under 15 minutes for objects under 5GB. But your RDS automated backup has an RPO of up to 24 hours unless you&#8217;re using read replicas or Aurora Global Database. Route 53 health checks with failover routing can redirect traffic in under 60 seconds, but only if your secondary environment is already running (warm standby) or fully active (multi-site active-active).</p><p>The exam distinguishes between backup/restore (hours of RTO, lowest cost), pilot light (minutes of RTO, minimal running infrastructure), warm standby (seconds to minutes, scaled-down but live), and multi-site active-active (near-zero RTO, highest cost). Build this project and you&#8217;ll understand why a financial services company chooses multi-site active-active at $40,000/month while a content platform chooses backup/restore at $200/month.</p><p><strong>What the exam will ask:</strong> S3 replication configuration, RDS backup retention, Route 53 routing policies, and how to calculate RTO/RPO for each DR tier.</p><h2>Project 4: Hybrid Storage Solution</h2><p><strong>What you build:</strong> AWS Storage Gateway connected to on-premises systems, S3 lifecycle policies moving data through storage tiers, and IAM policies controlling access.</p><p><strong>Why it matters:</strong> Most cloud engineers underestimate how much enterprise workload still runs on-premises. Storage Gateway is the bridge, and understanding it makes you sound experienced in interviews because it signals you&#8217;ve thought about migration, not just greenfield architecture.</p><p>Storage Gateway has three modes: File Gateway (NFS/SMB access to S3), Volume Gateway (iSCSI block storage backed by S3), and Tape Gateway (virtual tape library for backup software). The exam tests which mode fits which scenario. Build a File Gateway and you&#8217;ll understand why a media company with 200TB of on-premises video assets uses it to extend their NAS to S3 without rewriting their editing workflows.</p><p>S3 lifecycle policies complete the picture. Moving objects from S3 Standard to S3 Standard-IA after 30 days saves roughly 46% on storage costs. Moving to S3 Glacier Instant Retrieval after 90 days saves another 68%. For a workload storing 10TB of infrequently accessed data, that&#8217;s the difference between $230/month and $40/month. The exam will ask you to design the right lifecycle policy for a given access pattern, build this project and you&#8217;ll answer from experience, not memorization.</p><p><strong>What the exam will ask:</strong> Storage Gateway modes, S3 storage class trade-offs, lifecycle policy configuration, and IAM policy structure for cross-account S3 access.</p><h2>Project 5: Containerized Microservices Application</h2><p><strong>What you build:</strong> Two services deployed on ECS with Fargate, task definitions with resource limits, ALB path-based routing to each service, and CloudWatch Container Insights for logging and metrics.</p><p><strong>Why it matters:</strong> Containers are now a core SAA-C03 domain, and ECS with Fargate is the AWS-native answer to &#8220;I want containers without managing servers.&#8221; Building this project teaches you the ECS mental model, clusters, services, task definitions, and tasks, and how they map to the infrastructure underneath.</p><p>The ALB routing piece is where most candidates get confused. Path-based routing lets you send <code>/api/orders/*</code> to your orders service and <code>/api/inventory/*</code> to your inventory service, both running as separate ECS services behind a single ALB. Each service has its own target group, its own task definition with CPU and memory limits, and its own auto-scaling policy based on CPU utilization or request count. When you build this, you understand why a task definition with 256 CPU units and 512MB memory will throttle under load before it scales, and how to set the right CloudWatch alarm threshold to trigger scaling before users notice.</p><p>CloudWatch Container Insights gives you container-level CPU, memory, network, and disk metrics without any instrumentation. You&#8217;ll see exactly which task is consuming resources and correlate it with application logs in the same console. That operational visibility is what separates a working prototype from a production-ready deployment.</p><p><strong>What the exam will ask:</strong> ECS vs. EKS selection criteria, Fargate vs. EC2 launch type trade-offs, ALB target group configuration, and CloudWatch metrics for container workloads.</p><h2>Conclusion</h2><p>Watching videos teaches you what AWS services do. Building projects teaches you what they cost, where they fail, and why you&#8217;d choose one over another. Every question on the SAA-C03 is ultimately asking: <em>given these constraints, what&#8217;s the right architecture decision?</em></p><p>These five projects give you the intuition to answer that question, not just on the exam, but in the room when a customer asks why their database is the bottleneck, why their DR plan won&#8217;t meet their RTO, or why their serverless pipeline is costing more than expected.</p><p>Build the projects. Pass the exam. Show up to the interview ready to talk about real systems.</p><div class="subscription-widget-wrap-editor" data-attrs="{&quot;url&quot;:&quot;https://blog.thecloudengineers.com/subscribe?&quot;,&quot;text&quot;:&quot;Subscribe&quot;,&quot;language&quot;:&quot;en&quot;}" data-component-name="SubscribeWidgetToDOM"><div class="subscription-widget show-subscribe"><div class="preamble"><p class="cta-caption">Thanks for reading The Cloud Engineers! Subscribe for free to receive new posts and support my work.</p></div><form class="subscription-widget-subscribe"><input type="email" class="email-input" name="email" placeholder="Type your email&#8230;" tabindex="-1"><input type="submit" class="button primary" value="Subscribe"><div class="fake-input-wrapper"><div class="fake-input"></div><div class="fake-button"></div></div></form></div></div><p></p>]]></content:encoded></item></channel></rss>