AWS Lambda Runtime API

Amazon recently introduced the Lambda Runtime API which should make it easier to use any programming languages to write Lambda functions.This could be a great way to grow Swift in some interesting server side directions. Anyone looking into this yet? If so, I'd love to join in and help.

Announcement:

Docs:

15 Likes

Yeah a broader support for serverless Swift would be amazing. I personally wait until Google would announce Swift support for Google Cloud Functions (especially for Firebase). I really hope that when stable ABI comes out that more platforms and tools will adopt Swift (one tool on my wish list is Unity3D; here Windows support would also be necessary). When the two mentioned tools would support Swift it would already feel like the world is finally conquered, at least to me.

3 Likes

I agree. As of now AWS has by far the largest market share, so a strong presence there could have a big influence on adoption of Swift outside mac/iOS. I think the sooner we get proper tooling for Swift up there, the sooner we can "conquer the world" :smile:

With this new API adoption seems a little more "native" to the platform than the previous methods others have used (have a small nodejs script execute a Swift binary and pass it the lambda arguments)

3 Likes

I just wanted to say that I agree with this point. I think the Swift project growing support for AWS Lambda would be really great for the Swift on Server ecosystem.

13 Likes

The project that I am part of - Smoke Framework (GitHub - amzn/smoke-framework: A light-weight server-side service framework written in the Swift programming language.) - will hopefully be adding an integration to make it possible to use the framework in a Lambda, both as a simple Lambda function or as a Lambda Proxy[1].

[1] Tutorial: Build a Hello World REST API with Lambda proxy integration - Amazon API Gateway

We also have some AWS service integrations - SmokeAWS (GitHub - amzn/smoke-aws: AWS services integration for the Smoke Framework), SmokeAWSCredentials (GitHub - amzn/smoke-aws-credentials: A library to obtain and assume automatically rotating AWS IAM roles written in the Swift programming language.) and SmokeDynamoDB (GitHub - amzn/smoke-dynamodb: SmokeDynamoDB is a library to make it easy to use DynamoDB from Swift-based applications, with a particular focus on usage with polymorphic database tables (tables that do not have a single schema for all rows).). These libraries should already work with the new runtime API to be able to make use of other AWS services.

There is also a question around supporting compilation for Lambda environments which run on Amazon Linux 2017.03 which we will need to look into.

11 Likes

I implemented draft version of AWSLambdaRuntime.

However It have not been run on AWS yet.
I can't make a binary without any libraries due to a swiftc's issue.
I'm working on about this issue.

4 Likes

That’s great news! What can others here do to help? @tachyonics / @giginet

I also started implementing an AWS Lambda Runtime for Swift: GitHub - tonisuter/aws-lambda-swift: A custom AWS Lambda Runtime for Swift. I got it to work on AWS and there is a tutorial in the README if you want to try it out for yourself. AWS Lambda runs on Amazon Linux which doesn't support Swift "out of the box". Because of that, I had to upload a custom AWS Lambda Layer which contains the shared libraries that a simple Swift executable links to (e.g., the Standard Library, Foundation, Glibc, Grand Central Dispatch, etc). The lambda then references the layer, so we don't need to re-upload the shared libraries every time the lambda function changes.

I'm not sure if this is a great solution but it works at least for simple things. Any feedack would be appreciated.

9 Likes

Great Work Toni. Thank you for sharing. I started my own before discovering yours :-( GitHub - sebsto/swift-custom-runtime-lambda: Provide an AWS Lambda runtime implemntation for Swift programming language

I ran into a problem when going beyond and above the "hello world" example. When trying to make an HTTPS connection from the lambda function, it fails with "error setting certificate verify locations:\n CAfile: /etc/ssl/certs/ca-certificates.crt\n CApath: /etc/ssl/certs"

This is because Swift's binaries are linked against libgnutls.so and this library is built to search root certificates at /etc/ssl/certs/ca-certificates.crt, which does not exist on Amazon Linux :-(

I have a couple of ideas to solve this (rebuilding Swift on Amazon Linux, building just lignutls.so with a different path hardcoded - this is a build time option - are two of them)

I wonder if you hit this as well and though about possible solutions. I am available to discuss options.

1 Like

Hi SĂ©bastien. Sorry for the late response. Unfortunately, I haven't had a lot of time to work on it lately, so I haven't tried that yet. I would have to setup an AWS VPC to access an external API from a lambda, right?

I’d say this is a bug to be reported to AWS- if they’re bundling libgnutls I’m sure it’s well within their control to make it work as expected

Hello Georgie. Short answer : no. Long answer : AWS Lambda is running on Amazon Linux. Apple provides the Swift runtime for Ubuntu only. So to execute a Swift binary on Amazon Linux, the trick is to import into the runtime environment all dependencies from Ubuntu, including the libgnutls library from Ubuntu. Problem is that library has some hard coded path to configuration file. I am working on a solution to recompile libgnutls on ubuntu but this time using the Amazon Linux path for configuration files. I'll keep this thread posted with my results

3 Likes

Hello Toni,

No, there is no need for VPC. Any HTTPS call from the lambda function will fail.

This looks like it’s already at least 80% there, great work!

Architecture-wise I’m wondering whether the handler can be further decoupled from the handler by linking it as a prebuilt shared library (in the base layer).

As it stands this would be compiling (and statically linking) its own handler for each packaged set. I don’t know the runtime API well enough to be sure this is avoidable but seems like it should be able to have one binary running the runtime as called initially by bootstrap and running the infinite loop. And then maybe use dlopen to open the handlers dynamically in a sort of “plugin” pattern. Or just run each handler as invocations of separately-built handler binaries. I’m not sure what the performance implications would be of running a binary vs opening a shared library- if it makes no difference just running the handlers as individual binaries would be easiest to reason about and test.

That architecture has the disadvantage of having no static safety that the handler actually exists, but this is no different to js/python etc. But it has the advantage of having faster compile times, smaller binaries, less overhead, faster starts, and also running multiple handlers on a single layer - as it stands it seems like the handleName is hardcoded on init?

The only uncertain part about this architecture is that it would still need a way of sharing datatypes for event input and output between runtime and handler, or a manual coding/decoding of the input and return types in the handler. It could also be a function imported from the runtime shared library- runLambdaFunctionHandler(_ handler: (Codable) -> Codable) which just thinly decodes stdin and encodes the handler’s return value to an IOStream (stderr?). But I’m not sure- I’m pretty new to IPC. Architecting handlers as “plugins” would make these decisions unnecessary and allow the handlers to be called directly with real error handling etc.

Sorry for the long message, I don’t expect you to actually do any of this. It’s just as much a notepad for my own ideas about it. I’m excited about the prospect of using Swift on Lambda but I don’t have a lot of time to play around with it myself at the moment so this is in case I do. But feel free of course to try any of these ideas out of you’re interested.

I see, if they’re not bundling it then no I wouldn’t expect them to fix it ;)

Smoke Framework looks really promising. Are there any example projects to help getting started?

@mrmikemon
@tachyonics

I’d like to know this too. Would really like to see some information on getting started so we can take it for a spin and help move it forward.

@mrmikemon
@GalCohen

Thanks guys, appreciate your interest!

We actually have a full example showing a service with a REST-like API with some operations using DynamoDB as a persistence layer coded up and waiting approval. I don't have a firm timeline when we will be able to release it but in the past it hasn't taken long from this point.

Thanks @tachyonics ! Looking forward to it. Has compiling for the lambda execution environment been worked out yet?

@GalCohen Not yet. My team has a build script for building the Swift Toolchain for Amazon Linux 2 (which is what we run our services on). One of the next things I have planned for us is to finish adapting the script for Amazon Linux 2017.03 which is what Lambda uses.