faas-containerd - serverless without Kubernetes

A little over a year ago I started an experiment to see if I could build an OpenFaaS provider for containerd that would mean a computer could run OpenFaaS functions without the need for a cluster and Kubernetes.

An update - Jan 2020

faas-containerd is now part of the faasd project, which brings the OpenFaaS experience and ecosystem to containerd.

Learn more about faasd, or continue reading for the original story.

Overview

Let's start with a quick glossary then get into the detail.

  • containerd

    If you haven't heard of containerd yet, it's a CNCF project and was spun out of the main Docker project. It runs containers, has advanced features like snapshotting and is both fast and lightweight.

  • OpenFaaS

    A simple, modular, and extensible serverless platform for containers, the primary target for production is Kubernetes. Driven three values: developers-first, operator-friendly, and community-centric.

  • Kubernetes

    A production grade container orchestrator, offered as a service by many cloud providers.

  • k3s

    A light-weight version of Kubernetes which passes conformance tests.

  • faas-containerd

    My newest OpenFaaS provider which runs functions in containerd instead of with Kubernetes.

Since my initial attempt went on hold, k3s arrived and has dramatically reduced the memory footprint of Kubernetes and even enabled the single-node use-case even further. k3s does so many smart things like replacing etcd with sqlite and packaging all the code needed into a single binary, including a network driver.

k3s is positioned for the edge, but it does need 500MB of RAM to even run hello-world, that feels like way too much, that's where faas-containerd comes in.

OpenFaaS was originally built only for Docker Swarm and was tightly coupled to its API, so when requirements changed I extracted an interface called "faas-provider", which is now a Golang SDK and has been used by dozens of developers to build different providers for functions. Read more about The Power of Interfaces in OpenFaaS.

Provider Model

A provider implmements: CRUD on functions, secrets and logs. Functions are simply containers that serve traffic on port 8080. For bash, CLIs and other binaries, our "watchdog" can be used as a shim.

In this post I'll introduce you to faas-containerd, what it does, and how you can get involved. First of all, a bit more context.

List of OpenFaaS providers

Here's a summary from the OpenFaaS community.md file. Not all providers are "equal" in terms of features, and support so we've included some notes and grouping.

Official providers developed and supported by the OpenFaaS project

Project name and description Author Site Status
faas-netes- Kubernetes provider OpenFaaS github.com Supported
faas-swarm - Docker Swarm provider OpenFaaS github.com Supported
openfaas-operator - Kubernetes Operator provider OpenFaaS github.com Incubation

Community providers actively being developed and/or supported by a third-party

Project name and description Author Site Status
faas-nomad - Nomad provider Andrew Cornies & Nic Jackson (Hashicorp) github.com Incubation
faas-memory - In-memory provider Ed Wilde / Alex Ellis github.com Inception
faas-federation - federation provider to route between one or more providers Ed Wilde / Alex Ellis github.com Inception
faas-fargate - AWS Fargate provider Edward Wilde github.com Incubation
faas-lambda - AWS Lambda provider Ed Wilde / Alex Ellis sales@openfaas.com Incubation
faas-containerd - containerd provider for single node / edge Alex Ellis github.com Inception

Community providers no-longer being maintained

Project name and description Author Site Status
faas-rancher - Rancher/Cattle provider Ken Fukuyama github.com Inception
faas-dcos - DCOS provider Alberto Quario github.com Inception
faas-hyper - Hyper.sh provider Hyper github.com Inception
faas-guardian - Guardian provider Nigel Wright github.com Inception
faas-ecs Xicheng Chang (Huawei) github.com Inception
faas-opendns OpenDNS / Cisco / EC2 medium.com Inception

What's the role of a provider?

The OpenFaaS gateway hosts a UI and adds some important middleware like metrics, scale from zero, and authz. The provider deals with function CRUD, logs, and secret management.

faas-provider

From the faas-provider sample:

	timeout := 8 * time.Second
	bootstrapHandlers := bootTypes.FaaSHandlers{
		FunctionProxy:  handlers.MakeProxy(),
		DeleteHandler:  handlers.MakeDeleteHandler(clientset),
		DeployHandler:  handlers.MakeDeployHandler(clientset),
		FunctionReader: handlers.MakeFunctionReader(clientset),
		ReplicaReader:  handlers.MakeReplicaReader(clientset),
		ReplicaUpdater: handlers.MakeReplicaUpdater(clientset),
		InfoHandler:    handlers.MakeInfoHandler(),
		LogHandler: logs.NewLogHandlerFunc(requestor,timeout),
	}

	var port int
	port = 8080
	bootstrapConfig := bootTypes.FaaSConfig{
		ReadTimeout:  timeout,
		WriteTimeout: timeout,
		TCPPort:      &port,
	}

	bootstrap.Serve(&bootstrapHandlers, &bootstrapConfig)

To create your own provider, just head over to faas-provider, vendor the project and create your own HTTP handlers.

The simplest example is the faas-memory provider that I worked on with Ed Wilde. It's useful for testing.

Introducing faas-containerd

The idea with faas-containerd is to create a provider that can run any OpenFaaS function or service using containerd, but faster and using less resources than Kubernetes or k3s.

From the repo:

Some users could benefit from a lightweight, single-node execution environment. Using containerd and bypassing Kubernetes or Docker should reduce the start-time for functions and allow for running in resource-constrained environments.

Pros:

  • Fast cold-start
  • containerd features available such as pause/snapshot
  • Super lightweight

Cons:

  • No clustering (yet)
  • No inter-service communication (yet)
  • Very experimental

I was excited to share a Tweet showing the provider working with faas-cli and unmodified functions directly from the Function Store, a good test I think.

Working demo

What are people saying?

There's already been some initial interest from my network.

Here's our first tester, tweeting a picture of his deployment of my ping function:

Other folks in the ecosystem are also interested by the possiblities this might bring:

Darren Shepherd, the creator of k3s also had some ideas about the project

Darren's done great work with k3s, and I'm sure there's a lot that can be learned from his approach.

Going further

faas-containerd has generated some initial interest and the proof of concept is working, so you can take it for a spin yourself on a Linux computer, or even a Raspberry Pi.

If you like this idea, or think it's cool, Star / Fork the project for later:

Here's a diagram of what things might look like, if a "faasd" process was used to package and deploy everything needed:

8XeY6Pug.jpg-large

My wishlist now is to:

  • Add "faasd" a controller which starts faas-containerd, the OpenFaaS gateway, and Prometheus to give a fully-functional OpenFaaS setup
  • Move from netns to using CNI, perhaps with containerd/go-cni
  • Find a way to make the functions run as daemons, or long-running
  • Benchmark scenarios like cold-start and raw performance vs a single-node k3s cluster
  • Benchmark total memory usage vs single-node k3s
  • Ship official builds on GitHub releases and Docker Hub

Stretch goals are:

  • To explore inter-service communication - i.e. so that Prometheus can scrape the OpenFaaS gateway
  • Service discovery/look-up by name from container to container

Contribute

I'm looking for contributors who can help me with code contributions. It turns out that low-level systems programming with containers is not well documented, but it can be learned through experimentation, which is what I've done here.

If you can help with features, improvements or testing, then please join OpenFaaS Slack.

Similar projects

I wanted to highlight a few similar projects for lightweight multi-node clustering. These are alternatives to Kubernetes, but you may not want to move prod there any time soon.

Both projects have some simularities and Michael/Evan are contributing to each other's projects. Guys, if you're listening, thank you for containerd :-)

Tiny provider for a tiny devicxe

It even works on Raspberry Pi / armhf / ARM64 thanks to Golang's cross-compilation ability and the current state of dependent projects like OpenFaaS, Prometheus, NATS, and containerd itself. Given how light-weight this is, it may even open up the possibility of using the dozen of Raspberry Pi Zeros I have in my spare parts box.

You may also like

Alex Ellis

Read more posts by this author.

Subscribe to Alex Ellis' Blog

Subscribe to keep in touch. By providing your email, you agree to receive marketing emails from OpenFaaS Ltd

or subscribe via RSS with your favourite RSS reader

Learn Go with my new eBook

eBook cover

"Everyday Go" is the fast way to learn tools, techniques and patterns from real tools used in production based upon my experience of building and running OpenFaaS at scale.

Buy a copy on Gumroad