Unabhängig, aber sicher: Serverless-Security

Das Verteilen von Anwendungslogik auf zahlreiche Serverless Functions skaliert gut, bringt aber neue Herausforderungen beim Absichern der Anwendung mit sich.

In Pocket speichern vorlesen Druckansicht 8 Kommentare lesen

(Bild: NicoElNino/Shutterstock.com)

Lesezeit: 14 Min.
Von
  • Lars Röwekamp
Inhaltsverzeichnis

Serverless-Architekturen ermöglichen es, komplexe Anwendungssysteme aufzubauen, ohne sich um das Management der Infrastruktur kümmern zu müssen. Aspekte wie Verfügbarkeit, Provisionierung und Skalierung übernimmt der Cloud-Provider. Der Fokus der Anwendungsentwicklung liegt auf der Implementierung der Fachlichkeit in Form losgelöster Funktionen. Unter dem Strich ist der Ansatz zudem kosteneffizient – vorausgesetzt das Entwicklungsteam hat bei Architektur und Softwaredesign seine Hausaufgaben gemacht.

Dank Managed Runtime Model gehören Maintenance, Updates und Patches für den gesamten (virtualisierten) Hardware- und Software-Stack der Vergangenheit an. Das Team kann seinen Fokus zu 100 Prozent auf die Umsetzung der Businesslogik der Anwendung legen.

Soweit die Theorie. In der Praxis ist es am Ende nicht so trivial, wie es die Cloud-Provider gerne anpreisen. Das Aufspalten einer monolithischen Anwendung in viele kleine Funktionen, die wiederum stark verteilt, lose gekoppelt und asynchron mit anderen Funktionen oder Cloud-Komponenten interagieren, führt zu einem auf vielen Ebenen äußerst komplexen System, das nicht einfach zu beherrschen ist. Folgende Abbildung zeigt beispielhaft ein Serverless-Szenario zum Speichern eines Bildes, inklusive zugehöriger Beschreibung in einem virtuellen Reisetagebuch:

Das Speichern eines Bildes löst mehrere Serverless-Funktionen aus (Abb. 1).

In der Welt der Serverless Functions besteht eine Anwendung nicht selten aus Hunderten von Funktionen, von denen jede für sich genommen relativ trivial ist. Ihr Zusammenspiel dagegen ergibt ein hochkomplexes und – "dank" Cloud-Umgebung – fragiles Gesamtsystem.

Die Aktivierung der einzelnen Funktionen erfolgt in der Regel durch dedizierte Events, inklusive zugehöriger Payloads. Nach getaner Arbeit, beispielsweise dem Ablegen von Bildern in einem Object Store oder dem Speichern von Daten in einer NoSQL-Datenbank, triggern sie nicht selten weitere Funktionen oder Cloud-Komponenten – ebenfalls durch passende Events. Am Ende ergibt sich ein lose gekoppeltes, asynchron arbeitendes System. Eine Freude für jeden Architekten.

Um für ein solches System eine hinreichende Sicherheit zu garantieren, ist ein Umdenken gefragt. Die Angriffsfläche ist deutlich breiter als bei einer monolithischen Anwendung, die einzelnen Angriffspunkte verteilen sich auf eine Vielzahl unterschiedlicher Komponenten.

Trotz der vielen kleinen, oft trivialen Funktionen spielt insbesondere die Gesamtsicht auf das System bei der Betrachtung sicherheitsrelevanter Aspekte eine entscheidende Rolle. Welche Angriffspunkte bieten die einzelnen Komponenten des Systems und welche zusätzlichen Angriffspunkte ergeben sich durch deren Zusammenspiel? Welche Daten verarbeitet das System? Wie sensibel sind die Daten und welchen Wert haben sie? Wie hoch wäre der Schaden, wenn sie bei einem Verstoß gegen die Security Policy (aka Breach) an die Öffentlichkeit gerieten? Die Antworten auf all diese Fragen, zeigen potenzielle Punkte auf, an denen es anzusetzen gilt, um die gewünschte Sicherheit für das Gesamtsystem zu gewährleisten.

Das wirft wiederum die Frage auf, für welche Punkte die Entwickler der Anwendung und für welche der Cloud-Provider verantwortlich ist. Folgendes Diagramm zeigt anhand des "Shared Responsibility Model for AWS Lambda" die getrennten Zuständigkeiten auf.

Das Shared Responsibility Model zeigt, wer für welchen Bereich verantwortlich ist (Abb. 2).

Für andere Cloud-Provider ergibt sich ein nahezu identisches Bild.

Die folgenden Best Practices für Serverless-Security geben die wichtigsten Ansatzpunkte zur Realisierung einer Security-Policy wieder. Folgende Abbildung zeigt, an welchen Stellen die Best Practices innerhalb einer Serverless-Architektur zum Tragen kommen:

Übersicht über die Best Practices (Abb. 3).

Ein Gesamtbild des Zusammenspiels der in einen Use Case involvierten Komponenten ist essenziell. Intensives Monitoring und Auditing auf Ebene der Serverless Functions hilft, dieses Bild zu erstellen und im Falle von Anomalien zielgerichtet und automatisiert zu reagieren. Anomalien können beispielsweise Aufrufpfade sein, die in der Form nicht vorgesehen sind oder aber unvollständige, unerwartete oder korrumpierte Daten in eingehenden Events.

Sonderheft zu sicherer Softwareentwicklung

Dieser Artikel stammt aus dem iX-Developer-Sonderheft "Sichere Software entwickeln". Es behandelt auf 156 Seiten unter anderem die Themen Web-Application-Security, Codeanalyseverfahren und Cloud-Security. Der Schwerpunkt zu DevSecOps zeigt Methoden, Werkzeuge und Reifegradmodelle auf.

Für spezifische Programmiersprachen soll ein Artikel helfen, Speicherfehler in C++ aufzuspüren und zu vermeiden, und ein weiterer zeigt die Sicherheitskonzepte von Rust auf. Wer mit Java entwickelt, findet eine Übersicht der Änderungen an der Security von Java 11 bis Java 17.

Der Themenbereich Kryptografie geht von den Grundlagen über die Fallstricke beim Einbinden kryptografischer Verfahren in eigene Anwendungen bis zum Ausblick auf die Post-Quanten-Kryptografie.

Das Heft ist im heise Shop als PDF für 12,99 Euro verfügbar. Die gedruckte Ausgabe lässt sich für 14,90 Euro vorbestellen. Ein Bundle aus gedruckter Ausgabe plus PDF ist ebenfalls verfügbar.

Als Best Practice sollten Teams ein intensives und sicheres Logging auf Ebene der Serverless Functions einführen. Log-Informationen sollten dabei aus Gründen der Performance asynchron geschrieben und in einem zentralen Log zur übergreifenden Auswertung gesammelt werden. Zusätzliche Kontextinformationen wie Correlation IDs und Tags helfen beim zielgerichteten Monitoring und erleichtern das Auffinden von Problemen und deren Ursachen. Tools können sowohl die Metriken und Log-Information einzelner Serverless Functions visualisieren als auch deren Zusammenspiel. Über Thresholds lassen sich Alarme auslösen, Benachrichtigungen versenden und automatisiert Gegenmaßnahmen anstoßen.

Ebenso wie in der nicht Serverless-basierten Entwicklung gilt es, die Abhängigkeiten der einzelnen Funktionen der Libraries von Drittanbietern regelmäßig auf Schwachstellen zu prüfen. Die besondere Herausforderung ergibt sich im Umfeld der Serverless-Anwendungen durch die Vielzahl der Funktionen sowie deren Änderungsfrequenz. Die berühmte Dependency Hell erlangt in der Serverless-Welt eine neue Komplexitätsstufe.

Als Best Practice hat es sich etabliert, die benötigten Checks voll automatisiert und als Teil des Continuous-Integration und -Deployment-Lifecycles durchzuführen. Tools zur Sicherstellung der Continuous Code Quality und Code Security wie Snyk, Codacy oder sonarcloud lassen sich nahtlos in die CI/CD-Pipeline integrieren und ermöglichen automatische Security Scans auf unterschiedlichsten Ebenen.

Alternativ bietet das quelloffene Framework Serverless passende Plug-ins.