It’s been fun watching the recent evolution of .NET. Since .NET became an open source platform, it has finally fulfilled its cross-platform promise.
Having cross-platform capabilities means you can also run .NET on any cloud. All you need is a supported Linux virtual machine host or a Kubernetes instance that supports distributionless containers. This is enough to run .NET code on infrastructure-as-a-service platforms like AWS or managed Kubernetes like Google Kubernetes Engine (GKE). Code can migrate from platform to platform using REST APIs to access platform services. In some cases, SDKs are available from the platform provider or developed by the community.
Portability like this is a good thing: It allows you to move from cloud to cloud with minimal changes to your code (especially if you don’t use any service-specific applications). However, there are limitations as you cannot take advantage of the serverless platform features that allow you to enjoy the scalability of the cloud and the economic benefits that come with on-demand operations.
Using C# in AWS Lambda
If you’re using AWS Lambda for your serverless applications, you’ve had the option of using .NET with C# along with JavaScript, Go, Python, Java, Ruby, Rust, PowerShell, and TypeScript for some time now. Amazon support began with .NET Core and has been updated with successive versions of the platform. There is currently support for both .NET 6 and .NET 7. Since .NET 7 is only available for hosted containers, you’ll probably want to use .NET 6 for now.
Much like Azure Functions, AWS Lambda is a serverless computing platform built around event-driven operations. Lambda functions are typically triggered by events from other AWS services and can be used to support data processing, stream processing, API-driven backends for web and mobile applications, and IoT (internet of things) deployments, among many different options. .
The key feature of AWS Lambda is that, like Azure Functions, you have no control over the compute resources it uses. The service scales with demand and you pay for the resources you consume.
Creating Lambda functions in .NET
Using .NET with AWS Lambda does not require any changes to your development toolbox. You can use Visual Studio, Visual Studio Code or any third-party IDE. All you have to do is install a set of AWS templates from NuGet via the .NET CLI.
At the core of AWS’s C# functions is the Lambda function handler. This method is what the base service calls to initialize your code. This is an important component of the Lambda function and provides both an event and a context object to your code. The event object is probably the most useful because it provides information about the event, while the context object provides information about the runtime environment. The data will need to be serialized as a JSON object ready for use in your code.
Understanding the context object is important to ensure your C# code works well. The important runtime information it provides includes the remaining time before a function times out and AWS reclaims its resources. You can use this information to write appropriate error handling controls, cancel tasks, and deliver notifications if a timeout is about to be triggered.
C# code in AWS Lambda is called in one of two ways. The first option is to provide a function as a class library, configuring the service with class and assembly names and the method to be called when the function is triggered. The second option is to provide an executable assembly that will run when called.
Simplifying C# function development with Lambda Annotations
Amazon provides additional features that can simplify writing C# functions. The Lambda Annotations framework is a way to hide most of the Lambda-specific code from your business logic, use resource renderers to render it from a REST API path, and also create the appropriate Lambda handlers. You can find a template for creating an Annotations Framework project in the AWS Toolkit for Visual Studio as part of the included plans.
Because Annotations Framework can set Lambda properties programmatically, you can add timeouts and memory limits as part of the initial function definition. Once your code is ready, build it and deploy it directly to AWS from within Visual Studio.
You’re not limited to standalone C# applications. Lambda can be used to host and run ASP.NET Core web applications too, giving you an on-demand back end for sites that see relatively low usage or that need to respond to bursty demands.
Using .NET 8 in AWS Lambda
Amazon is working to deliver .NET 8 support for AWS Lambda hosts, with the final release is due soon. As the GitHub issue notes, there are a lot of moving parts that must come together to deliver a long-term stable release of a managed runtime. In addition to building a new host based on the latest releases of Amazon’s own internal Linux distribution, AWS’s .NET team is also developing and testing an updated set of .NET APIs and CLI tools to help build new Lambdas and update existing code.
That last point is important, as AWS plans to start deprecating both its .NET 6 and .NET 7 support in 2024, with a hard limit for updating .NET 6 functions in February 2025. Migrating to the long-term support release of .NET will help ensure your code remains supported—by both Microsoft and Amazon. Some tools are already available, including an update to the AWS Toolkit for Visual Studio, which lets you build custom runtime templates based on .NET 8, and support for a .NET 8 container base image.
If you plan on using this Amazon Linux 3 base image, you’ll need to clone the AWS .NET GitHub repository and build the image on your own development systems (see this blog post). This will allow you to test code before packaging and deploying it to AWS. When AWS finalizes its .NET 8 tools, this will become part of the platform, and you will be able to use it as part of your standard build process.
Support for .NET in AWS AWS Lamba makes your .NET skills portable beyond traditional application development and Azure cloud-native platforms. It’s important to note that this is not a one-off, but a long-term project that has been through multiple updates to the underlying runtime, in line with .NET’s own support life cycle. With an effective set of abstractions that make it easier to concentrate on your code, AWS is delivering an approach that should simplify porting serverless .NET code from other cloud platforms as well as from on-premises applications.