Akri’s New Extensibility Model: the Why and How
How device discovery with Akri became more extensible, lightweight, secure, and language agnostic
Akri is an open source project that discovers IoT devices and exposes them to Kubernetes clusters as resources. Akri discovers devices via its Discovery Handlers, which are oftentimes protocol implementations, such as ONVIF and OPC UA. For Akri to discover more devices, it must support more Discovery Handlers. Previously, Discovery Handler development was a tedious task. However, in v0.6.5, Akri released a new Discovery Handler model that makes Akri more extensible, lightweight, secure, and language agnostic. This blog discusses the motivation behind re-architecting Akri and how the new model works.
The Motivation
In Akri’s original design, all Discovery Handlers were embedded in the Akri Agent, which runs on every node in a cluster. This meant that if a someone wanted to add a new Discovery Handler, they would not only have to fork and modify the core Akri code base but also be restricted to implementing their Discovery Handler in Rust. The result was a long contribution process and an Agent that grew in size with each contribution. For example, when a community member created a Zeroconf Discovery Handler — which excitingly enables Akri to discover mDNS devices! — the Ahavi daemon that the protocol uses for discovery doubled the Agent size. This motivated a redesign of Akri, so Discovery Handlers can be deployed separate of the Agent. Then, in the case of Zeroconf, Akri’s footprint is only expanded for users leveraging mDNS devices.
The Solution
To decouple the Discovery Handlers from the Akri Agent, we exposed a gRPC interface for Discovery Handlers. Now Discovery Handlers can be added in any language outside of Akri’s codebase. Discovery Handlers now run in their own Pods, deployed as DaemonSets (like the Agent), instead of being bundled in with the Agent.
When installing Akri, you now can choose to install only the Discovery Handlers you need. Say you only want to discover IP cameras, you simply specify the Discovery handler you want (in this case, ONVIF, which is a common protocol for discovering and managing IP Cameras). No extra, unnecessary Discovery Handlers are deployed. The following Helm installation creates the deployment that looks like the right half of Figure 1:
helm repo add akri-helm-charts https://deislabs.github.io/akri/
helm install akri akri-helm-charts/akri \
--set onvif.discovery.enabled=true
An Agent without embedded Discovery Handlers is the default. If you prefer the previous experience of an Agent with embedded Discovery Handlers (or a “full” Agent), simply specify agent.full=true
when installing the Akri chart and an Agent image with OPC UA, udev, and ONVIF Discovery Handlers will be used, creating a deployment that looks like the left half of Figure 1.
Extending Akri
If you want to create your own Discovery Handler to support discovery of a new set of devices (say Bluetooth or your own proprietary protocol), simply create a Discovery Handler that implements our gRPC interface, defined as a proto file and shown in Figure 2. The Akri Agent implements a Registration
service. The Discovery Handler registers with the Agent, specifying the endpoint at which it is running its DiscoveryHandler
service. Then, the Agent calls out to the Discovery Handler, which updates the Agent on the stream whenever devices come or go.
If you are familiar with Kubernetes’ Device Plugin framework, you may notice similarities between Akri’s Discovery Handler interface and the Device Plugin API. The Device Plugin framework enables the creation of extended resources, so that Pods can then go request these resources just as they may request memory or CPU. Akri’s Agent creates a Device Plugin for each device a Discovery Handler discovers, thereby making it a resource that can be requested by Pods. Akri abstracts away the details discovering devices and creating device resources, which is why Akri’s name (besides meaning “edge” in Greek) is an acronym for A Kubernetes Resource Interface.
Want to get started developing an Akri Discovery Handler? If you are a friend of Rust, we’ve created a template to kickstart development.
cargo install cargo-generate
cargo generate --git https://github.com/kate-goldenring/akri-discovery-handler-template.git --name akri-discovery-handler
Simply fill in the DiscoveryHandler
service’s Discover
function, build, and add it to your Akri Helm installation. See Akri’s Discovery Handler development documentation for more details.
Summary
To summarize, Akri majorly re-architected — almost half of all of its code was touched — in order to enable:
- An easier Discovery Handler development cycle
- Non-rust developers to contribute
- Discovery Handlers to be added without increasing the Agent size or attack surface
- Deploying Akri with only the relevant Discovery Handlers
- Discovery Handlers to be created without needing to understand Akri’s code base
If you’re excited by these changes, come contribute a Discovery Handler! We are excited to see what devices you discover with Akri.