How to Plug a Lambda Function into a Legacy Application Without Changing a Single Line of Code
Introduction Every development team has one, that critical application that runs the business, that nobody dares to touch, and that a brave team somewhere is slowly rewriting. In the meantime, the business doesn't stop. New requirements keep coming, and someone has to handle them. The classic dilemma : do you ask the team rewriting the application to squeeze in this new feature, slowing down…
Every development team maintains a crucial application, largely untouched as a new team gradually overhauls it. Simultaneously, the business continues unabated, generating fresh requirements that need addressing. The inherent conflict arises: should the rewriting team incorporate this new feature, potentially slowing their already complex task, or should the legacy codebase be altered personally, risking unforeseen errors?
An overlooked third approach exists, requiring minimal effort: intercept incoming requests at the load balancer stage and process them through an AWS Lambda function, all without altering the legacy application. No single line of code needs rewriting, and there's no deployment risk. This article elucidates how to leverage an Application Load Balancer (ALB) listener rule to route a particular URL path to a Lambda function, allowing all other traffic to continue to your existing EC2 application without any modifications.
Before delving into the implementation, let's briefly review the AWS components involved. The Application Load Balancer (ALB) distributes HTTP/HTTPS traffic across multiple targets, offering content-based routing by examining URL paths, hostnames, HTTP headers, or query parameters of each request. Listeners and Rules process incoming connection requests on a specific protocol and port, with each Listener having a set of Rules evaluated in priority order, with the first matching rule taking precedence.
A Default Rule handles any traffic not fitting into specific rules. Target Groups group destinations the ALB forwards traffic to, supporting two target types pertinent to this scenario: Instance (your EC2 application) and Lambda (your function), each with independent health checks, though Lambda Target Groups bypass this requirement since Lambda oversees its own availability.
AWS Lambda is a serverless compute service responding to events like HTTP requests forwarded by an ALB, charging only for actual execution time, making it a cost-effective choice for handling specific URL paths that don't frequently receive traffic.
The architecture relies on a single ALB as the entry point for all traffic, with two distinct Target Groups managing requests based on the URL path. The Instance Target Group handles general traffic, forwarding it to the legacy EC2 application. The Lambda Target Group processes only requests matching a specific URL path (e.g., /lambda) and forwards them to the new Lambda function.
The request flow is as follows: the client sends a request, the ALB receives it, evaluates the rules in priority order, then forwards it either to the Lambda Target Group, invoking the Lambda function, or the Default Rule, routing it to the Instance Target Group and subsequently to the EC2 application. The crucial point is that the ALB makes routing decisions before the request reaches any backend, ensuring neither the Lambda function nor the EC2 application are aware of each other; they only receive and return responses, with the ALB managing all traffic orchestration.
This architecture provides surgical precision, allowing for the interception of exactly one URL path and handling it differently while maintaining the application's existing behavior untouched. No legacy app redeployment, coordination with the rewriting team, or regression risks occur. The step-by-step implementation involves creating the Lambda Target Group in the EC2 console with the Target type set to Lambda function, naming it descriptively, disabling health checks since Lambda manages its own availability, and registering the Lambda function as the target.
Next, an Instance Target Group is created for the EC2 application, with the Target type set to Instances, named similarly, protocol HTTP with port 80, and a health check path set in the legacy application's health endpoint, ensuring the instance's status is Healthy before proceeding. Adding a Listener to the ALB via the EC2 console, using HTTP on port 80 with a default action to forward to the Instance Target Group, ensures all traffic initially goes to the legacy EC2 application.
Finally, adding a Routing Rule for Lambda, specifying the path as /lambda, forwarding it to the Lambda Target Group, and setting a higher priority than the Default Rule, ensures that any request to /lambda is intercepted by the ALB and forwarded to the Lambda function, leaving all other requests to flow as usual. Finally, ensuring the Lambda returns the correct response format is essential but often overlooked, completing the implementation.
Written by urgent.news from Dev.to's reporting — not their text. Machine-written — may contain errors; check the original before relying on it.