Azure-Sicherheit für cloudnative Apps
Tipp
Diese Inhalte sind ein Auszug aus dem E-Book „Architecting Cloud Native .NET Applications for Azure“, verfügbar in der .NET-Dokumentation oder als kostenlos herunterladbare PDF-Datei, die offline gelesen werden kann.
Cloudnative Anwendungen können sowohl einfacher als auch schwieriger zu schützen sein als herkömmliche Anwendungen. Auf der anderen Seite müssen Sie eine größere Anzahl kleinerer Anwendungen schützen und mehr Energie darauf verwenden, die Sicherheitsinfrastruktur zu erstellen. Die heterogene Natur der Programmiersprachen und -stile bei den meisten Dienstbereitstellungen bedeutet auch, dass Sie den Sicherheitsbulletins vieler verschiedener Anbieter mehr Aufmerksamkeit schenken müssen.
Andererseits schränken kleinere Dienste, die jeweils über einen eigenen Datenspeicher verfügen, den Umfang eines Angriffs ein. Wenn ein Angreifer ein System kompromittiert, ist es für den Angreifer wahrscheinlich schwieriger, auf ein anderes System überzuspringen als bei einer monolithischen Anwendung. Prozessgrenzen sind starke Grenzen. Wenn eine Datenbanksicherung offengelegt wird, ist der Schaden geringer, da diese Datenbank nur eine Teilmenge der Daten enthält und es unwahrscheinlich ist, dass sie personenbezogene Daten enthält.
Bedrohungsmodellierung
Unabhängig davon, ob die Vorteile der cloudnativen Anwendungen die Nachteile überwiegen, muss der gleiche ganzheitliche Sicherheitsansatz befolgt werden. Sicherheit und sicheres Denken müssen in jeden Schritt der Entwicklung und des Betriebs einfließen. Stellen Sie bei der Planung einer Anwendung Fragen wie:
- Wie würde sich der Verlust dieser Daten auswirken?
- Wie können wir den Schaden begrenzen, der durch die Einschleusung fehlerhafter Daten in diesen Dienst entsteht?
- Wer sollte Zugriff auf diese Daten haben?
- Gibt es Richtlinien für die Überwachung des Entwicklungs- und Freigabeprozesses?
All diese Fragen sind Teil eines Prozesses, der Bedrohungsmodellierung (Threat Modeling) genannt wird. Bei diesem Prozess wird versucht, die Frage zu beantworten, welche Bedrohungen für das System bestehen, wie wahrscheinlich die Bedrohungen sind und wie hoch der potenzielle Schaden ist.
Sobald die Liste der Bedrohungen eingerichtet wurde, müssen Sie entscheiden, ob sie eine Risikominderung wert sind. Manchmal ist eine Bedrohung so unwahrscheinlich und teuer zu planen, dass es sich nicht lohnt, Energie darauf zu verwenden. So könnte beispielsweise ein Akteur auf der Zustandsebene Änderungen in den Entwurf eines Prozesses einschleusen, der von Millionen von Geräten verwendet wird. Anstatt nun einen bestimmten Codeabschnitt in Ring 3 auszuführen, wird dieser Code in Ring 0 ausgeführt. Dieser Prozess ermöglicht einen Exploit, der den Hypervisor umgehen und den Angriffscode auf den Bare-Metal-Computern ausführen kann, was Angriffe auf alle virtuellen Computer ermöglicht, die auf dieser Hardware ausgeführt werden.
Die veränderten Prozessoren sind ohne ein Mikroskop und fortgeschrittene Kenntnisse des Siliziumdesigns des Prozessors nur schwer zu erkennen. Es ist unwahrscheinlich, dass dieses Szenario eintritt, und es ist teuer, es zu entschärfen. Daher würde wahrscheinlich kein Bedrohungsmodell empfehlen, einen Exploitschutz für dieses Szenario einzurichten.
Wahrscheinlichere Bedrohungen, z. B. nicht funktionierende Zugriffssteuerungen, die Angriffe auf die Inkrementierung von Id
(Id=2
durch Id=3
in der URL ersetzen) oder SQL-Einschleusung ermöglichen, sind interessanter, um entsprechende Schutzmaßnahmen zu erstellen. Die Maßnahmen zur Risikominderung für diese Bedrohungen sind recht angemessen zu erstellen und verhindern unliebsame Sicherheitslücken, die den Ruf des Unternehmens schädigen.
Prinzip der geringsten Rechte
Eine der grundlegenden Ideen in der Computersicherheit ist das Prinzip der geringsten Rechte (Principle of Least Privilege, POLP). Das ist eigentlich ein Grundgedanke bei fast jeder Form von Sicherheit, sei sie nun digital oder physisch. Kurz gesagt ist das Prinzip, dass jeder Benutzer oder Prozess die geringstmögliche Anzahl von Rechten erhalten sollte, die zum Ausführen seiner Aufgabe erforderlich ist.
Denken Sie z. B. an die Kassierer in einer Bank: Der Zugang zum Tresor ist eine ungewöhnliche Tätigkeit. Der durchschnittliche Kassierer kann den Tresor also nicht selbst öffnen. Um Zugang zu erhalten, müssen sie ihre Anforderung über einen leitenden Angestellten der Bank eskalieren, der zusätzliche Sicherheitsüberprüfungen durchführt.
Ein hervorragendes Beispiel in einem Computersystem sind die Rechte eines Benutzers, der eine Verbindung mit einer Datenbank herstellt. In vielen Fällen wird ein einzelnes Benutzerkonto verwendet, um sowohl die Datenbankstruktur zu erstellen als auch die Anwendung auszuführen. Außer in extremen Fällen benötigt das Konto, das die Anwendung ausführt, nicht die Möglichkeit, Schemainformationen zu aktualisieren. Es sollte mehrere Konten geben, die unterschiedliche Berechtigungsstufen bieten. Die Anwendung sollte nur die Berechtigungsstufe verwenden, die Lese- und Schreibzugriff auf die Daten in den Tabellen gewährt. Diese Art von Schutz würde Angriffe verhindern, die darauf abzielen, Datenbanktabellen zu löschen oder schädliche Trigger einzuführen.
Fast jeder Bereich beim Erstellen einer cloudnativen Anwendung kann davon profitieren, sich an das Prinzip der geringsten Rechte zu erinnern. Sie finden es beim Einrichten von Firewalls, Netzwerksicherheitsgruppen, Rollen und Geltungsbereichen der rollenbasierten Zugriffssteuerung (RBAC).
Penetrationstests
Da Anwendungen immer komplizierter werden, steigt die Zahl der Angriffsvektoren in alarmierendem Maße. Die Bedrohungsmodellierung ist insofern fehlerhaft, als sie in der Regel von denselben Personen durchgeführt wird, die das System erstellen. Genauso wie viele Entwickler Schwierigkeiten haben, sich die Interaktionen der Benutzer vorzustellen und dann unbrauchbare Benutzeroberflächen erstellen, haben die meisten Entwickler Schwierigkeiten, jeden Angriffsvektor zu erkennen. Es ist auch möglich, dass die Entwickler, die das System erstellen, sich nicht gut mit Angriffsmethoden auskennen und etwas Entscheidendes übersehen.
Bei Penetrationstests werden externe Akteure hinzugezogen, die versuchen, das System anzugreifen. Diese Angreifer können ein externes Beratungsunternehmen oder andere Entwickler mit guten Sicherheitskenntnissen aus einem anderen Teil des Unternehmens sein. Sie erhalten einen Freibrief für den Versuch, das System zu sabotieren. Oftmals finden sie umfangreiche Sicherheitslücken, die gepatcht werden müssen. Manchmal ist der Angriffsvektor etwas völlig Unerwartetes, wie ein Phishing-Angriff auf den Geschäftsführer.
Azure selbst ist ständig Angriffen durch ein Team von Hackern innerhalb von Microsoft ausgesetzt. Im Laufe der Jahre waren sie die ersten, die Dutzende von potenziell katastrophalen Angriffsvektoren entdeckt und geschlossen haben, bevor sie von außen ausgenutzt werden konnten. Je verlockender ein Ziel ist, desto wahrscheinlicher ist es, dass endlose Akteure versuchen werden, es auszunutzen, und es gibt nur wenige Ziele auf der Welt, die verlockender sind als Azure.
Überwachung
Sollte ein Angreifer versuchen, in eine Anwendung einzudringen, sollte es eine entsprechende Warnung geben. Häufig lassen sich Angriffe durch die Untersuchung der Protokolle von Diensten aufdecken. Angriffe hinterlassen verräterische Zeichen, die Sie erkennen können, bevor sie erfolgreich sind. Ein Angreifer, der versucht, ein Kennwort zu erraten, wird z. B. viele Anforderungen an ein Anmeldesystem stellen. Die Überwachung rund um das Anmeldesystem kann ungewöhnliche Muster erkennen, die nicht mit dem typischen Zugriffsmuster übereinstimmen. Diese Überwachung kann in eine Warnung umgewandelt werden, die wiederum eine zuständige Person alarmieren kann, um eine Art von Gegenmaßnahme zu ergreifen. Ein sehr ausgereiftes Überwachungssystem könnte sogar auf der Grundlage dieser Abweichungen proaktiv Maßnahmen ergreifen und Regeln zum Blockieren von Anforderungen oder Drosseln von Antworten hinzufügen.
Sichern des Builds
Ein Bereich, in dem die Sicherheit oft übersehen wird, ist der Buildprozess. Der Build sollte nicht nur Sicherheitsprüfungen ausführen, z. B. die Überprüfung auf unsicheren Code oder eingecheckte Anmeldeinformationen, sondern auch der Build selbst sollte sicher sein. Wenn der Buildserver kompromittiert ist, bietet er einen idealen Vektor für die Einschleusung von unerwünschtem Code in das Produkt.
Stellen Sie sich vor, dass ein Angreifer versucht, die Kennwörter von Personen zu stehlen, die sich bei einer Webanwendung anmelden. Sie könnten einen Buildschritt einführen, der den ausgecheckten Code so ändert, dass er jede Anmeldeanforderung zu einem anderen Server spiegelt. Wenn der Code das nächste Mal den Build durchläuft, wird er unbemerkt aktualisiert. Die Sicherheitsrisikoüberprüfung des Quellcodes fängt dieses Sicherheitsrisiko nicht ab, da sie vor dem Build ausgeführt wird. Auch bei einer Codeüberprüfung wird es niemandem auffallen, da die Schritte zum Erstellen des Builds auf dem Buildserver liegen. Der ausgenutzte Code gelangt in die Produktion, wo er Kennwörter auslesen kann. Wahrscheinlich gibt es kein Überwachungsprotokoll der Änderungen im Buildprozess, oder zumindest überwacht niemand die Überwachung.
Dieses Szenario ist ein perfektes Beispiel für ein scheinbar geringwertiges Ziel, das ausgenutzt werden kann, um in das System einzudringen. Sobald ein Angreifer die Systemgrenzen durchbrochen hat, kann er nach Möglichkeiten suchen, seine Berechtigungen so weit zu erhöhen, dass er überall echten Schaden anrichten kann.
Erstellen von sicherem Code
.NET Framework ist bereits ein ziemlich sicheres Framework. Es vermeidet einige der Fallstricke von nicht verwaltetem Code, z. B. das Verlassen der Enden von Arrays. Es wird aktiv daran gearbeitet, Sicherheitslücken zu schließen, sobald sie entdeckt werden. Es gibt sogar ein Bug Bounty-Programm, das Interessierte dafür bezahlt, dass sie Fehler im Framework finden und melden, anstatt sie auszunutzen.
Es gibt viele Möglichkeiten, .NET-Code sicherer zu gestalten. Das Befolgen von Richtlinien wie im Artikel Richtlinien für sichere Codierung für .NET ist ein sinnvoller Schritt, um sicherzustellen, dass der Code von Grund auf sicher ist. Die OWASP Top 10 ist ein weiterer unschätzbarer Leitfaden, um sicheren Code zu erstellen.
Der Buildprozess ist ein guter Platz, um Scantools zu platzieren, um Probleme im Quellcode zu erkennen, bevor sie in die Produktion gelangen. Fast jedes Projekt hat Abhängigkeiten von einigen anderen Paketen. Ein Tool, das auf veraltete Pakete prüft, wird Probleme bei einem nächtlichen Build erkennen. Auch beim Erstellen von Docker-Images ist es sinnvoll, zu prüfen und sicherzustellen, dass das Basisimage keine bekannten Sicherheitsrisiken aufweist. Überprüfen Sie auch, ob niemand versehentlich Anmeldeinformationen eingecheckt hat.
Integrierte Sicherheit
Azure ist so konzipiert, dass Benutzerfreundlichkeit und Sicherheit für die meisten Benutzer in Einklang gebracht werden. Verschiedene Benutzer werden unterschiedliche Sicherheitsanforderungen haben, sodass sie ihren Ansatz für die Cloudsicherheit genau abstimmen müssen. Microsoft veröffentlicht eine Vielzahl von Sicherheitsinformationen im Trust Center. Diese Ressource sollte die erste Anlaufstelle für alle Experten sein, die verstehen möchten, wie die integrierten Technologien zur Angriffsabwehr funktionieren.
Innerhalb des Azure-Portals ist Azure Advisor ein System, das eine Umgebung ständig überprüft und Empfehlungen unterbreitet. Einige dieser Empfehlungen zielen darauf ab, den Benutzern Geld zu sparen, andere wiederum sollen potenziell unsichere Konfigurationen aufzeigen, z. B. einen für die Öffentlichkeit zugänglichen Speichercontainer, der nicht durch ein virtuelles Netzwerk geschützt ist.
Azure-Netzwerkinfrastruktur
In einer lokalen Bereitstellungsumgebung wird viel Energie für das Einrichten von Netzwerken aufgewendet. Das Einrichten von Routern, Switches und dergleichen ist eine komplizierte Angelegenheit. Netzwerke gestatten es bestimmten Ressourcen, mit anderen Ressourcen zu kommunizieren, und verhindern in manchen Fällen den Zugriff darauf. Eine häufige Regel im Netzwerk besteht darin, den Zugriff auf die Produktionsumgebung von der Entwicklungsumgebung aus zu beschränken, falls ein unfertiger Code versehentlich ausgeführt wird und einen großen Teil der Daten löscht.
Die meisten PaaS-Azure-Ressourcen verfügen standardmäßig nur über die einfachsten und freizügigsten Netzwerkeinstellungen. So kann beispielsweise jeder im Internet auf einen App-Dienst zugreifen. Neue SQL Server-Instanzen werden in der Regel mit Einschränkungen bereitgestellt, sodass externe Parteien keinen Zugriff auf sie haben. Die von Azure selbst verwendeten IP-Adressbereiche sind jedoch zugelassen. Während der SQL-Server also vor externen Bedrohungen geschützt ist, muss ein Angreifer lediglich einen Azure-Bridgehead festlegen, von dem aus er Angriffe auf alle SQL-Instanzen in Azure starten kann.
Glücklicherweise lassen sich die meisten Azure-Ressourcen in ein virtuelles Azure-Netzwerk einbinden, das eine differenzierte Zugriffssteuerung ermöglicht. Ähnlich wie lokale Netzwerke private Netzwerke einrichten, die vor der Außenwelt geschützt sind, sind virtuelle Netzwerke Inselsysteme privater IP-Adressen, die sich innerhalb des Azure-Netzwerks befinden.
Abbildung 9-1. Virtuelles Netzwerk in Azure.
Genauso wie lokale Netzwerke über eine Firewall verfügen, die den Zugriff auf das Netzwerk regelt, können Sie eine ähnliche Firewall an der Grenze des virtuellen Netzwerks einrichten. Standardmäßig können alle Ressourcen in einem virtuellen Netzwerk weiterhin mit dem Internet kommunizieren. Nur bei eingehenden Verbindungen ist eine explizite Firewallausnahme erforderlich.
Wenn das Netzwerk eingerichtet ist, können Sie interne Ressourcen wie Speicherkonten so festlegen, dass nur der Zugriff von Ressourcen möglich ist, die sich ebenfalls im virtuellen Netzwerk befinden. Diese Firewall bietet eine zusätzliche Sicherheitsstufe. Sollten die Schlüssel für dieses Speicherkonto bekannt werden, können Angreifer keine Verbindung mit diesem Konto herstellen, um die bekannt gewordenen Schlüssel auszunutzen. Dieses Szenario ist ein weiteres Beispiel für das Prinzip der geringsten Rechte.
Die Knoten in einem Azure Kubernetes-Cluster können an einem virtuellen Netzwerk teilnehmen, genau wie andere Ressourcen, die eher in Azure verwurzelt sind. Diese Funktionalität wird Azure Container Networking Interface genannt. Tatsächlich wird ein Subnetz innerhalb des virtuellen Netzwerks zugewiesen, in dem virtuelle Computer und Containerimages zugeordnet werden.
Um das Prinzip der geringsten Rechte zu verdeutlichen, muss nicht jede Ressource innerhalb eines virtuellen Netzwerks mit jeder anderen Ressource kommunizieren. In einer Anwendung, die eine Web-API über ein Speicherkonto und eine SQL-Datenbank bereitstellt, ist es beispielsweise unwahrscheinlich, dass die Datenbank und das Speicherkonto miteinander kommunizieren müssen. Die Freigabe von Daten zwischen ihnen erfolgt über die Webanwendung. Daher könnte eine Netzwerksicherheitsgruppe (NSG) verwendet werden, um den Datenverkehr zwischen den beiden Diensten zu unterbinden.
Die Implementierung einer Richtlinie zur Verweigerung der Kommunikation zwischen Ressourcen kann lästig sein, insbesondere wenn Sie Azure ohne Datenverkehrsbeschränkungen verwenden. In einigen anderen Clouds ist das Konzept der Netzwerksicherheitsgruppen viel weiter verbreitet. Die Standardrichtlinie von AWS sieht zum Beispiel vor, dass Ressourcen erst dann untereinander kommunizieren können, wenn sie durch Regeln in einer NSG aktiviert wurden. Die Entwicklung ist zwar langsamer, aber eine restriktivere Umgebung bietet einen sichereren Standard. Die Verwendung geeigneter DevOps-Methoden, insbesondere die Verwendung von Azure Resource Manager oder Terraform zur Verwaltung von Berechtigungen, kann die Kontrolle der Regeln erleichtern.
Virtuelle Netzwerke können auch nützlich sein, wenn Sie die Kommunikation zwischen lokalen und Cloudressourcen festlegen. Ein virtuelles privates Netzwerk kann verwendet werden, um die beiden Netzwerke nahtlos miteinander zu verbinden. Dieser Ansatz ermöglicht es, ein virtuelles Netzwerk ohne jegliche Art von Gateway für Szenarien auszuführen, bei denen alle Benutzer vor Ort sind. Es gibt eine Reihe von Technologien, die Sie zum Einrichten dieses Netzwerks verwenden können. Am einfachsten ist es, ein Site-to-Site-VPN zu verwenden, das zwischen vielen Routern und Azure eingerichtet werden kann. Der Datenverkehr wird verschlüsselt und zu den gleichen Kosten pro Byte über das Internet getunnelt wie jeder andere Datenverkehr. Für Szenarien, in denen mehr Bandbreite oder mehr Sicherheit erforderlich ist, bietet Azure einen Dienst namens Express Route, der eine private Leitung zwischen einem lokalen Netzwerk und Azure verwendet. Die Einrichtung ist kostenintensiver und schwieriger, aber auch sicherer.
Rollenbasierte Zugriffssteuerung zur Einschränkung des Zugriffs auf Azure-Ressourcen
RBAC ist ein System, das Anwendungen, die in Azure ausgeführt werden, eine Identität verleiht. Anwendungen können auf Ressourcen zugreifen, indem sie diese Identität anstelle von Schlüsseln oder Kennwörtern oder zusätzlich zu diesen verwenden.
Sicherheitsprinzipale
Die erste Komponente in RBAC ist ein Sicherheitsprinzipal. Ein Sicherheitsprinzipal kann ein Benutzer, eine Gruppe, ein Dienstprinzipal oder eine verwaltete Identität sein.
Abbildung 9-2: Verschiedene Arten von Sicherheitsprinzipalen.
- Benutzer: Jeder Benutzer, der über ein Konto in Azure Active Directory verfügt, ist ein Benutzer.
- Gruppe: Eine Sammlung von Benutzern von Azure Active Directory. Als Mitglied einer Gruppe übernimmt ein Benutzer die Rollen dieser Gruppe zusätzlich zu seiner eigenen.
- Dienstprinzipal: Eine Sicherheitsidentität, unter der Dienste oder Anwendungen ausgeführt werden.
- Verwaltete Identität: Eine von Azure verwaltete Azure Active Directory-Identität. Verwaltete Identitäten werden in der Regel bei der Entwicklung von Cloudanwendungen verwendet, die die Anmeldeinformationen für die Authentifizierung bei Azure-Diensten verwalten.
Der Sicherheitsprinzipal kann auf fast jede Ressource angewendet werden. Dieser Aspekt bedeutet, dass es möglich ist, einem in Azure Kubernetes ausgeführten Container einen Sicherheitsprinzipal zuzuweisen, der ihm den Zugriff auf die in Key Vault gespeicherten Geheimnisse ermöglicht. Eine Azure-Funktion kann eine Berechtigung übernehmen, mit der sie mit einer Active Directory-Instanz kommunizieren kann, um einen JWT für einen aufrufenden Benutzer zu überprüfen. Sobald Dienste mit einem Dienstprinzipal aktiviert sind, können ihre Berechtigungen präzise mithilfe von Rollen und Bereichen verwaltet werden.
Rollen
Ein Sicherheitsprinzipal kann viele Rollen übernehmen. Jede Rolle definiert eine Reihe von Berechtigungen wie „Nachrichten vom Azure Service Bus-Endpunkt lesen“. Der effektive Berechtigungssatz eines Sicherheitsprinzipals ist die Kombination aller Berechtigungen, die allen Rollen zugewiesen sind, über die ein Sicherheitsprinzipal verfügt. Azure verfügt über eine große Anzahl integrierter Rollen und Benutzer können ihre eigenen Rollen definieren.
Abbildung 9-3. RBAC-Rollendefinitionen.
In Azure sind auch eine Reihe von Rollen für höhere Ebenen wie „Besitzer“, „Mitwirkender“, „Leser“ und „Benutzerkontoadministrator“ integriert. Mit der Rolle „Besitzer“ kann ein Sicherheitsprinzipal auf alle Ressourcen zugreifen und Berechtigungen an andere vergeben. Ein Mitwirkender hat den gleichen Zugriff auf alle Ressourcen, kann aber keine Berechtigungen zuweisen. Ein Leser kann nur vorhandene Azure-Ressourcen anzeigen und ein Benutzerkontoadministrator kann den Zugriff auf Azure-Ressourcen verwalten.
Präzisere integrierte Rollen wie Mitwirkender für DNS-Zone haben Rechte, die auf einen einzelnen Dienst beschränkt sind. Sicherheitsprinzipale können eine beliebige Anzahl von Rollen übernehmen.
Bereiche
Rollen können auf eine begrenzte Anzahl von Ressourcen in Azure angewendet werden. Wenn Sie z. B. den Geltungsbereich auf das vorherige Beispiel des Lesens aus einer Service Bus-Warteschlange anwenden, können Sie die Berechtigung auf eine einzelne Warteschlange beschränken: „Nachrichten vom Azure Service Bus-Endpunkt blah.servicebus.windows.net/queue1
lesen“.
Der Geltungsbereich kann sich auf eine einzelne Ressource, eine ganze Ressourcengruppe, ein Abonnement oder sogar eine Verwaltungsgruppe beschränken.
Bei der Prüfung, ob ein Sicherheitsprinzipal über eine bestimmte Berechtigung verfügt, wird die Kombination aus Rolle und Geltungsbereich berücksichtigt. Diese Kombination bietet einen leistungsfähigen Autorisierungsmechanismus.
Verweigern
Bisher waren für RBAC nur Regeln vom Typ „Zulassen“ erlaubt. Dieses Verhalten gestaltete das Erstellen einiger Geltungsbereiche kompliziert. Wenn Sie beispielsweise einem Sicherheitsprinzipal Zugriff auf alle Speicherkonten außer einem gewähren würden, müssten Sie einer potenziell endlosen Liste von Speicherkonten eine ausdrückliche Berechtigung erteilen. Jedes Mal, wenn ein neues Speicherkonto erstellt würde, müsste es zu dieser Liste von Konten hinzugefügt werden. Dies würde zu einem zusätzlichen Verwaltungsaufwand führen, der sicherlich nicht wünschenswert ist.
Den Zugriff verweigernde Regeln haben Vorrang vor Regeln, die den Zugriff erlauben. Jetzt könnte derselbe Geltungsbereich „alle außer einem zulassen“ durch die beiden Regeln „alle zulassen“ und „diesen einen bestimmten verweigern“ dargestellt werden. Den Zugriff verweigernde Regeln erleichtern nicht nur die Verwaltung, sondern sorgen auch für besonders sichere Ressourcen, da der Zugriff für alle verweigert wird.
Zugriffsprüfung
Wie Sie sich vorstellen können, kann es bei einer großen Anzahl von Rollen und Geltungsbereichen recht schwierig sein, die effektive Berechtigung eines Dienstprinzipals zu ermitteln. Wenn Sie die Regeln für die Verweigerung noch weiter ausdehnen, wird die Komplexität nur noch größer. Zum Glück gibt es einen Berechtigungsrechner, der die effektiven Berechtigungen für jeden Dienstprinzipal anzeigen kann. Er befindet sich normalerweise unter der Registerkarte „IAM“ im Portal, wie in Abbildung 9-3 gezeigt.
Abbildung 9-4. Berechtigungsrechner für einen App-Dienst.
Schützen von Geheimnissen
Kennwörter und Zertifikate sind ein häufiger Angriffsvektor für Angreifer. Hardware zum Knacken von Kennwörtern kann einen Brute-Force-Angriff durchführen und versuchen, Milliarden von Kennwörtern pro Sekunde zu erraten. Es ist daher wichtig, dass die Kennwörter, die für den Zugriff auf Ressourcen verwendet werden, ausreichend stark sind und eine große Vielfalt von Zeichen enthalten. Diese Kennwörter sind genau die Art von Kennwörtern, die sich kaum jemand merken kann. Glücklicherweise müssen die Kennwörter in Azure eigentlich keinem Menschen bekannt sein.
Viele Sicherheitsexperten empfehlen, einen Kennwort-Manager zu verwenden, um Ihre eigenen Kennwörter zu speichern. Während er Ihre Kennwörter an einem zentralen Ort verwaltet, ermöglicht er es, hochkomplexe Kennwörter zu verwenden und sicherzustellen, dass sie für jedes Konto eindeutig sind. Das gleiche System gibt es auch in Azure: einen zentralen Speicher für Geheimnisse.
Azure-Schlüsseltresor
Azure Key Vault bietet einen zentralen Ort zum Speichern von Kennwörtern für Datenbanken, API-Schlüssel und Zertifikate. Sobald ein Geheimnis in den Tresor eingegeben wurde, wird es nie wieder angezeigt und die Befehle, um es zu extrahieren und anzuzeigen, sind absichtlich kompliziert. Die Informationen im Tresor werden entweder mithilfe von Softwareverschlüsselung oder FIPS 140-2 Level 2 validierten Hardwaresicherheitsmodulen geschützt.
Der Zugriff auf den Schlüsseltresor erfolgt über RBACs, was bedeutet, dass nicht jeder Benutzer auf die Informationen im Tresor zugreifen kann. Angenommen, eine Anwendung möchte auf die in Azure Key Vault gespeicherte Verbindungszeichenfolge für die Datenbank zugreifen. Um Zugriff zu erhalten, müssen Anwendungen mithilfe eines Dienstprinzipals ausgeführt werden. In dieser angenommenen Rolle können sie die Geheimnisse aus dem Tresor lesen. Es gibt eine Reihe verschiedener Sicherheitseinstellungen, mit denen der Zugriff einer Anwendung auf den Tresor weiter eingeschränkt werden kann, sodass sie Geheimnisse nicht aktualisieren, sondern nur lesen kann.
Der Zugriff auf den Schlüsseltresor kann überwacht werden, um sicherzustellen, dass nur die erwarteten Anwendungen auf den Tresor zugreifen. Die Protokolle können wieder in Azure Monitor integriert werden, sodass Sie Warnungen festlegen können, wenn unerwartete Bedingungen eintreten.
Kubernetes
Innerhalb von Kubernetes gibt es einen ähnlichen Dienst für die Aufrechterhaltung kleinerer geheimer Informationen. Kubernetes Secrets kann über die typische ausführbare Datei kubectl
festgelegt werden.
Das Erstellen eines Geheimnisses ist so einfach wie die Suche nach der Base64-Version der zu speichernden Werte:
echo -n 'admin' | base64
YWRtaW4=
echo -n '1f2d1e2e67df' | base64
MWYyZDFlMmU2N2Rm
Dann fügen Sie es zu einer Geheimnisdatei namens secret.yml
hinzu, die z. B. so ähnlich aussieht wie das folgende Beispiel:
apiVersion: v1
kind: Secret
metadata:
name: mysecret
type: Opaque
data:
username: YWRtaW4=
password: MWYyZDFlMmU2N2Rm
Schließlich können Sie diese Datei in Kubernetes laden, indem Sie den folgenden Befehl ausführen:
kubectl apply -f ./secret.yaml
Diese Geheimnisse können dann in Volumes eingebunden oder über Umgebungsvariablen für Containerprozesse verfügbar gemacht werden. Der Ansatz der Zwölf-Faktoren-App zum Erstellen von Anwendungen empfiehlt, den kleinsten gemeinsamen Nenner zu verwenden, um Einstellungen an eine Anwendung zu übertragen. Umgebungsvariablen sind der kleinste gemeinsame Nenner, da sie unabhängig vom Betriebssystem oder der Anwendung unterstützt werden.
Eine Alternative zur Verwendung der integrierten Kubernetes-Geheimnisse ist der Zugriff auf die Geheimnisse in Azure Key Vault von Kubernetes aus. Die einfachste Möglichkeit hierfür ist das Zuweisen einer RBAC-Rolle zum Container, der Geheimnisse lädt. Die Anwendung kann dann die Azure Key Vault-APIs verwenden, um auf die Geheimnisse zuzugreifen. Dieser Ansatz erfordert jedoch Änderungen am Code und folgt nicht dem Muster der Verwendung von Umgebungsvariablen. Stattdessen ist es möglich, Werte in einen Container einzuschleusen. Dieser Ansatz ist tatsächlich sicherer als die direkte Verwendung der Kubernetes-Geheimnisse, da die Benutzer im Cluster darauf zugreifen können.
Verschlüsselung während der Übertragung und im Ruhezustand
Der Schutz von Daten ist wichtig, egal ob sie sich auf Datenträgern befinden oder zwischen verschiedenen Diensten übertragen werden. Die effektivste Methode zur Vermeidung von Datenlecks ist die Verschlüsselung in einem Format, das von anderen nicht ohne weiteres gelesen werden kann. Azure unterstützt eine Vielzahl von Verschlüsselungsoptionen.
Während der Übertragung
Es gibt mehrere Möglichkeiten zum Verschlüsseln des Datenverkehrs im Netzwerk in Azure. Der Zugriff auf Azure-Dienste erfolgt in der Regel über Verbindungen, die Transport Layer Security (TLS) verwenden. Beispielsweise erfordern alle Verbindungen mit den Azure-APIs entsprechende TLS-Verbindungen. Ebenso können Verbindungen mit Endpunkten im Azure-Speicher so eingeschränkt werden, dass sie nur über TLS-verschlüsselte Verbindungen funktionieren.
TLS ist ein kompliziertes Protokoll, aber das bloße Wissen, dass die Verbindung TLS verwendet, reicht nicht aus, um die Sicherheit zu gewährleisten. TLS 1.0 ist zum Beispiel chronisch unsicher, und TLS 1.1 ist nicht viel besser. Auch innerhalb der TLS-Versionen gibt es verschiedene Einstellungen, die die Entschlüsselung der Verbindungen erleichtern können. Am besten überprüfen Sie, ob die Serververbindung aktuelle und ordnungsgemäß konfigurierte Protokolle verwendet.
Diese Prüfung kann von einem externen Dienst wie SSL Server Test von SSL Labs durchgeführt werden. Ein Test, der mit einem typischen Azure-Dienstendpunkt, in diesem Fall einem Service Bus-Endpunkt, ausgeführt wird, ergibt ein nahezu perfektes Ergebnis.
Selbst Dienste wie Azure SQL-Datenbanken verwenden TLS-Verschlüsselung, um Daten zu verbergen. Das Interessante an der Verschlüsselung der Daten während der Übertragung mithilfe von TLS ist, dass es selbst für Microsoft nicht möglich ist, die Verbindung zwischen Computern, die TLS ausführen, abzuhören. Dies sollte Unternehmen beruhigen, die befürchten, dass ihre Daten von Microsoft selbst oder sogar von einem staatlichen Akteur mit mehr Ressourcen als dem Standardangreifer gefährdet werden könnten.
Abbildung 9-5. Bericht von SSL lab zeigt ein sehr gutes Ergebnis für einen Service Bus-Endpunkt.
Dieses Verschlüsselungsniveau wird zwar nicht für alle Zeiten ausreichen, aber es sollte das Vertrauen schaffen, dass Azure-TLS-Verbindungen recht sicher sind. Azure wird seine Sicherheitsstandards im Zuge der Verbesserung der Verschlüsselung weiterentwickeln. Es ist gut zu wissen, dass es jemanden gibt, der die Sicherheitsstandards überwacht und Azure aktualisiert, wenn sie sich verbessern.
Im Ruhezustand
In jeder Anwendung gibt es eine Reihe von Stellen, an denen Daten auf dem Datenträger ruhen. Der Anwendungscode selbst wird über einen Speichermechanismus geladen. Die meisten Anwendungen verwenden auch eine Art von Datenbank wie SQL Server, Cosmos DB oder sogar das erstaunlich preisgünstige Table Storage. Diese Datenbanken verwenden alle eine stark verschlüsselte Speicherung, um sicherzustellen, dass niemand außer den Anwendungen mit den entsprechenden Berechtigungen Ihre Daten lesen kann. Selbst die Systembetreiber können verschlüsselte Daten nicht lesen. So können die Kunden sicher sein, dass ihre geheimen Informationen geheim bleiben.
Storage
Die Grundlage für einen Großteil von Azure ist die Azure Storage-Engine. Datenträger von virtuellen Computern werden über Azure Storage eingebunden. Azure Kubernetes Service wird auf virtuellen Computern ausgeführt, die ihrerseits auf Azure Storage gehostet werden. Selbst serverlose Technologien wie Azure Functions-Apps und Azure Container Instances werden über Datenträger ausgeführt, die Teil von Azure Storage sind.
Wenn Azure Storage ausreichend verschlüsselt ist, bietet dies die Grundlage dafür, dass auch die meisten anderen Daten verschlüsselt werden können. Azure Storage wird mit FIPS 140-2-konformen 256-Bit-AESverschlüsselt. Dabei handelt es sich um eine anerkannte Verschlüsselungstechnologie, die in den letzten 20 Jahren eingehend wissenschaftlich untersucht wurde. Gegenwärtig ist kein praktischer Angriff bekannt, der es jemandem ohne Kenntnis des Schlüssels ermöglichen würde, mit AES verschlüsselte Daten zu lesen.
Standardmäßig werden die Schlüssel, die für die Verschlüsselung von Azure Storage verwendet werden, von Microsoft verwaltet. Es gibt umfangreiche Schutzmechanismen, die sicherstellen, dass ein böswilliger Zugriff auf diese Schlüssel verhindert wird. Benutzer mit besonderen Verschlüsselungsanforderungen können jedoch auch ihre eigenen Speicherschlüssel bereitstellen, die in Azure Key Vault verwaltet werden. Diese Schlüssel können jederzeit widerrufen werden, wodurch der Inhalt des Speicherkontos, das sie verwendet, unzugänglich wird.
Virtuelle Computer verwenden verschlüsselten Speicher, aber es ist möglich, eine weitere Verschlüsselungsebene zu schaffen, indem Sie Technologien wie BitLocker unter Windows oder DM-Crypt unter Linux verwenden. Diese Technologien bedeuten, dass es selbst dann, wenn das Datenträgerimage unberechtigt aus dem Speicher abgerufen würde, nahezu unmöglich wäre, es zu lesen.
Azure SQL
Datenbanken, die auf Azure SQL gehostet werden, verwenden eine Technologie namens Transparent Data Encryption (TDE), um sicherzustellen, dass die Daten verschlüsselt bleiben. Sie ist standardmäßig für alle neu erstellten SQL-Datenbanken aktiviert, muss aber für Legacydatenbanken manuell aktiviert werden. TDE verschlüsselt und entschlüsselt nicht nur die Datenbank, sondern auch die Sicherungen und Transaktionsprotokolle in Echtzeit.
Die Verschlüsselungsparameter sind in der master
-Datenbank gespeichert und werden beim Start für die weiteren Vorgänge in den Arbeitsspeicher eingelesen. Dies bedeutet, dass die master
-Datenbank unverschlüsselt bleiben muss. Der tatsächliche Schlüssel wird von Microsoft verwaltet. Benutzer mit exakten Sicherheitsanforderungen stellen jedoch möglicherweise ihren eigenen Schlüssel in Key Vault auf fast die gleiche Weise bereit wie für Azure Storage. Key Vault bietet Dienste wie Schlüsselrotation und -widerruf.
Der „transparente“ Teil von TDS kommt daher, dass keine Clientänderungen erforderlich sind, um eine verschlüsselte Datenbank zu verwenden. Dieser Ansatz bietet zwar eine angemessene Sicherheit, aber wenn das Kennwort der Datenbank aufgedeckt wird, können die Benutzer die Daten entschlüsseln. Es gibt noch einen anderen Ansatz, bei dem einzelne Spalten oder Tabellen in einer Datenbank verschlüsselt werden. Always Encrypted stellt sicher, dass die verschlüsselten Daten zu keinem Zeitpunkt als Nur-Text in der Datenbank angezeigt werden.
Das Einrichten dieser Verschlüsselungsebene erfordert das Ausführen eines Assistenten in SQL Server Management Studio, um die Art der Verschlüsselung auszuwählen und zu bestimmen, wo in Key Vault die zugehörigen Schlüssel gespeichert werden sollen.
Abbildung 9-6. Auswahl von Spalten in einer Tabelle, die mit Always Encrypted verschlüsselt werden sollen.
Clientanwendungen, die Informationen aus diesen verschlüsselten Spalten lesen, müssen besondere Vorkehrungen zum Lesen verschlüsselter Daten treffen. Die Verbindungszeichenfolgen müssen mit Column Encryption Setting=Enabled
aktualisiert werden und die Anmeldeinformationen des Clients müssen aus Key Vault abgerufen werden. Der SQL Server-Client muss dann mit den Spaltenverschlüsselungsschlüsseln vorbereitet werden. Sobald dies geschehen ist, verwenden die übrigen Aktionen die Standardschnittstellen zum SQL-Client. Das heißt, dass Tools wie Dapper und Entity Framework, die auf dem SQL-Client basieren, weiterhin ohne Änderungen funktionieren werden. Always Encrypted ist möglicherweise noch nicht für jeden SQL Server-Treiber und jede Sprache verfügbar.
Die Kombination von TDE und Always Encrypted, die beide mit clientspezifischen Schlüsseln verwendet werden können, stellt sicher, dass auch die anspruchsvollsten Verschlüsselungsanforderungen unterstützt werden.
Cosmos DB
Cosmos DB ist die neueste Datenbank, die von Microsoft in Azure bereitgestellt wird. Sie wurde von Grund auf im Hinblick auf Sicherheit und Kryptografie erstellt. Die AES-256-Bit-Verschlüsselung ist Standard für alle Cosmos DB-Datenbanken und kann nicht deaktiviert werden. In Verbindung mit der TLS 1.2-Anforderung für die Kommunikation ist die gesamte Speicherlösung verschlüsselt.
Abbildung 9-7. Der Ablauf der Datenverschlüsslung in Cosmos DB.
Cosmos DB sieht zwar keine Bereitstellung von Verschlüsselungsschlüsseln für Kunden vor, aber das Team hat viel Arbeit investiert, um sicherzustellen, dass es auch ohne dies PCI-DSS-konform bleibt. Cosmos DB unterstützt auch noch keine Verschlüsselung einzelner Spalten, wie sie Azure SQL mit Always Encrypted bietet.
Erhalten der Sicherheit
Azure verfügt über alle notwendigen Tools, um ein hochsicheres Produkt zu veröffentlichen. Eine Kette ist jedoch nur so stark wie ihr schwächstes Glied. Wenn die Anwendungen, die in Azure bereitgestellt werden, nicht mit einem angemessenen Sicherheitsansatz und geeigneten Sicherheitsüberwachungen entwickelt werden, sind sie das schwache Glied in der Kette. Es gibt viele großartige statische Analysetools, Verschlüsselungsbibliotheken und Sicherheitsmethoden, die Sie verwenden können, um sicherzustellen, dass die in Azure installierte Software ebenso sicher ist wie Azure selbst. Beispiele sind statische Analysetools, Verschlüsselungsbibliotheken und Sicherheitsmethoden.