Broken Access Control in Express-Node.js-Anwendungen verhindern
Ben Smitthimedhin
22. Mai 2024
0 Min. LesezeitDie Zugriffskontrolle in Node.js-Backend-Anwendungen ist grundlegend für Webanwendungen, die mit dem Express-Webframework erstellt wurden. Sie stellt sicher, dass Nutzer nur auf Daten und Funktionen zugreifen können, für deren Nutzung sie berechtigt sind. Wird die Zugriffskontrolle jedoch kompromittiert, können Nutzer auf Daten zugreifen, die ihnen nicht zugänglich sein sollten. Das ist besonders problematisch, wenn Angreifer versuchen, private Daten zu manipulieren oder zu stehlen.
Es ist entscheidend, dass Sie Schwachstellen in der Zugriffskontrolle verstehen und verhindern, denn der Verlust privater Daten kann für viele Unternehmen katastrophale Folgen haben. In diesem Artikel erfahren Sie mehr über Broken Access Control in Node.js-Anwendungen und Strategien, um solche Schwachstellen beim Erstellen von Webanwendungen mit dem Express-Webframework zu verhindern.
Was ist Broken Access Control?
Zugriffskontrolle bedeutet, einzuschränken, was Nutzer innerhalb einer Anwendung tun und sehen können. Eine Schwachstelle in der Zugriffskontrolle liegt vor, wenn die Implementierung der Zugriffskontrollregeln einer Anwendung Fehler aufweist und dadurch unbefugte Nutzer auf vertrauliche Informationen zugreifen oder eingeschränkte Aktionen ausführen können.
Wenn beispielsweise ein gewöhnlicher Nutzer aufgrund fehlerhafter Zugriffskontrollen die privaten Daten eines anderen Nutzers einsehen, dessen Passwort ändern oder sogar seine Berechtigungen auf Administratorebene erweitern kann, kann das katastrophale Folgen haben – von Datenlecks bis hin zu unbefugten Systemänderungen.
Im folgenden Abschnitt sehen Sie einige Codebeispiele für verschiedene Arten von Schwachstellen in der Zugriffskontrolle.
Vertikale Broken Access Control in Express-Middleware
Eine Art von Schwachstelle in der Zugriffskontrolle tritt auf, wenn die vertikale Zugriffskontrolle fehlerhaft oder unzureichend ist. Dabei erhält ein regulärer Nutzer Zugriff auf Funktionen oder andere Berechtigungen auf Administratorebene, obwohl er dazu nicht berechtigt sein sollte. Dieser Nutzer steigt somit vertikal in der Berechtigungshierarchie auf und kann Änderungen oder Löschungen vornehmen oder andere administrative Aktionen ausführen, obwohl er dazu nicht in der Lage sein sollte.
Im Folgenden finden Sie konkrete Code-Schwachstellen, die zu vertikaler Broken Access Control führen können:
Ungeschütztes Admin-Panel in Express-Routen
Ein ungeschütztes Admin-Panel liegt vor, wenn Routen zu Funktionen auf Administratorebene auf einer Webseite oder einem Server nicht durch irgendeine Art von Autorisierung geschützt sind:
In diesem Szenario erhält jeder, der eine GET-Anfrage an die Route /admin stellt, automatisch Zugriff auf die Nachricht Welcome to the Admin Panel! – unabhängig davon, ob die Person zuvor angemeldet war oder über die erforderlichen Berechtigungen verfügen sollte. Das /admin-Panel ist von der Route /login entkoppelt, obwohl das nicht der Fall sein sollte. Dies ist somit eine Form von Broken Access Control.
Express-Admin-Panel auf Basis von Abfrageparametern
Ein Admin-Panel auf Basis von URL-Parametern lässt sich einfach implementieren. Ohne irgendeine Art von Validierung kann es jedoch leicht manipuliert werden:
In diesem Beispiel erhält ein Nutzer, der direkt eine GET-Anfrage an die Route /admin stellt, die Antwort Access denied. Um diese Ablehnung zu umgehen, genügt es, ?isAdmin=true zur URL hinzuzufügen. Da diese Parameter unabhängig davon hinzugefügt werden können, wer auf das Admin-Panel zugreift, besteht dieselbe Schwachstelle wie im ersten Beispiel fort: Ein regulärer Nutzer erhält Zugriff auf Administratorrechte.
Zugriffskontrolle in Express-Routen durch Verschleierung
Theoretisch ließe sich die Route zum Admin-Panel verschleiern, indem sie schwer zu erraten ist, beispielsweise mit der folgenden Express-Routen-Middleware:
Das scheint das Admin-Panel zwar sicherer zu machen, ist jedoch eine unsichere und fehlerhafte Methode, eine Anwendung zu schützen. Angreifer können einen Weg finden, die Sitemap der Website zu hacken und so alle Endpunkte offenzulegen. Sie können auch Fuzzing-Techniken verwenden, um alle möglichen Endpunkte zu testen und zu prüfen, welche Antworten zurückgegeben werden. Oder sie versuchen, auf die Logdateien zuzugreifen, um die protokollierte URL zu finden, über die sie das Admin-Panel erreichen können. Diese Methode wirkt zwar clever, bietet aber tatsächlich keinerlei sinnvollen Schutz und führt letztlich zu einer Schwachstelle durch Broken Access Control.
Klartextprotokollierung in Express-Anwendungen
Entwickler sollten auch bei Protokollierungsmechanismen vorsichtig sein, damit vertrauliche Informationen nicht versehentlich an Anwendungsnutzer weitergegeben werden. Beispielsweise kann eine Anwendung bei einer Anmeldung einen Logeintrag mit vertraulichen Informationen erstellen, ohne das Passwort aus den Logdaten zu entfernen:
Beachten Sie die console.log-Anweisung am Ende. Wer Zugriff auf die Logdateien hat, kann auch auf Nutzerdaten zugreifen und sich damit als beliebiger Nutzer mit Administratorzugriff anmelden. Deshalb ist es wichtig, im jeweiligen Kontext nur die erforderlichen Informationen zu protokollieren. Außerdem sollten Sie grundsätzlich sicherstellen, dass niemand vertrauliche Informationen protokolliert, mit denen Hacker im Fall eines Sicherheitsvorfalls Daten ausnutzen könnten.
Horizontale Broken Access Control in Express-Middleware
Bei Problemen mit vertikaler Zugriffskontrolle können Nutzer ihre Berechtigungen erweitern. Probleme mit horizontaler Zugriffskontrolle treten hingegen auf, wenn ein Nutzer Zugriff auf Ressourcen oder Daten erhält, die anderen Nutzern derselben Berechtigungsstufe gehören.
Sehen wir uns einige konkrete Codebeispiele für Schwachstellen in der horizontalen Zugriffskontrolle mit dem Express-Webframework für Node.js an.
Nutzer-ID im Anfrageparameter einer Express-Route
Eine Anwendung, in der Nutzer ihre Nutzer-ID in einem Anfrageparameter sehen können, kann problematisch sein – insbesondere, wenn sich mit derselben Nutzer-ID in den Anfrageparametern auf die Daten eines Nutzers zugreifen lässt. Das bedeutet, dass schon die Kenntnis der IDs anderer Personen Zugriff auf deren Daten ermöglichen kann.
Wenn Ihre ID beispielsweise 123 lautet, rufen Sie die Kontoinformationen auf einer Website über folgende Adresse auf: www.[website name].com/account?userId=123:
In diesem Beispiel können Sie mit einer GET-Anfrage an /account und der Abfrage userId=1 ganz einfach das Objekt accountData von logan@test.com abrufen, obwohl Sie möglicherweise als eine andere Person angemeldet sind. Dieselbe GET-Anfrage mit der Abfrage userId=2 gewährt Ihnen Zugriff auf das Objekt accountData von megan@test.com. Wenn Sie in der Abfrage die ID eines bestimmten Nutzers verwenden, erhalten Sie das zugehörige Objekt accountData.
Diese Sicherheitslücke wird allgemein als Insecure Direct Object Reference (IDOR) bezeichnet und tritt in Java, Ruby und anderen Programmiersprachen auf.
Unvorhersehbare Nutzer-ID in einem Anfrageparameter, der an eine Express-Routen-Middleware übergeben wird
Ausgehend vom vorherigen Beispiel könnte man meinen, dass eine gut konzipierte Zugriffskontrolle einfach darin besteht, die Nutzer-ID zu verschleiern. Beispielsweise könnte eine Nutzer-ID 1 durch Änderungen wie Hashing und Kodierung in der Abfrage zu 8a76dh3t werden, sodass der Zugriff auf die Nutzerdaten anderer Personen erschwert wird:
In diesem Beispiel übernimmt die Funktion obfuscateUserId die Nutzer-ID aus der Liste vorhandener Nutzer und verschleiert sie. Um über die Route /account Kontoinformationen abzurufen, ist daher eine GET-Anfrage erforderlich, die die verschleierte ID im Anfrageparameter enthält (zum Beispiel userId=8a76dh3t).
Diese Methode stützt sich nicht auf wirksame Sicherheitskontrollen und hält das Problem der Broken Access Control lediglich aufrecht. Mit genügend Zeit und Ausdauer können Hacker weiterhin Fuzzing einsetzen und die richtige verschleierte Nutzer-ID erraten, um Zugriff zu erhalten. Damit besteht die Schwachstelle in der Zugriffskontrolle weiterhin.
Fehlender CSRF-Schutz in Express-Anwendungen als Angriffsvektor
Eine gängige Methode, mit der Angreifer die Broken Access Control in Ihrer Express-Anwendung ausnutzen können, sind Cross-Site-Request-Forgery-Angriffe (CSRF). Einfach ausgedrückt, erstellen diese Angriffe gefälschte Webseiten oder Links, die Sie dazu verleiten, Ihre Informationen zu übermitteln. Diese Informationen werden dann an eine Funktion angehängt, die eine legitime Anfrage an die tatsächliche Website sendet, auf der Ihre Daten nun zugänglich sind.
Ohne CSRF-Schutz können alle Beispielserveranwendungen, die Sie sich angesehen haben, in ein gefälschtes Formular auf einer Webseite eingebunden werden. Nutzer geben darin Daten ein und senden sie ab, sodass ein Angreifer sie ausnutzen kann.
So verhindern Sie Schwachstellen durch Broken Access Control in Node.js
Nachdem Sie Beispiele für Schwachstellen in der vertikalen und horizontalen Zugriffskontrolle gesehen haben, geht es nun um allgemeine Strategien, mit denen Sie diese verhindern können.
Verwenden Sie aktuelle Bibliotheksversionen
Eine Möglichkeit, hohe Standards für Ihre Zugriffskontrolle sicherzustellen, ist die Verwendung angesehener npm-Pakete, die gepflegt und abgesichert werden. Node.js und sein Paketökosystem erhalten jedoch regelmäßig Updates, die Sicherheitslücken beheben. Daher ist es ebenfalls unerlässlich, die Pakete aktuell zu halten.
Die Node.js-Runtime und Pakete auf dem neuesten Stand zu halten, ist entscheidend, um das Risiko bekannter Sicherheitsprobleme zu verringern. Eine Möglichkeit dazu ist, den Zustand Ihrer Datei package.json einfach mit Snyk Advisor zu prüfen. Das Tool zeigt Ihnen, welche Bibliotheken Schwachstellen aufweisen, die behoben werden müssen, und ob ein npm-Paket veraltet oder nicht mehr gepflegt ist.
Wenn Sie eine Beispieldatei package.json per Drag-and-drop in Snyk Advisor ziehen, sehen Sie, dass dieses Projekt mehrere potenziell problematische npm-Pakete enthält:

Bei genauerem Hinsehen zeigt Snyk Advisor, dass für loader seit acht Jahren keine neuen Versionen erschienen sind und das Paket bei npm-Nutzern im Vergleich zu anderen Paketen nicht sehr beliebt ist. Updates regelmäßig zu prüfen und zeitnah einzuspielen – oder veraltete Bibliotheken im Projekt sogar zu ersetzen – sind gute erste Schritte, um Ihre Zugriffskontrolle sicher zu halten.
Verlassen Sie sich nicht allein auf Verschleierung
Wie Sie an einigen der Beispielanwendungen gesehen haben, ist Security by Obscurity keine verlässliche Strategie. Wenn ein Angreifer sich durch Erraten oder Fuzzing letztlich Zugriff verschaffen kann, ist Ihre Anwendung unsicher. Sie sollten geeignete Mechanismen zur Zugriffskontrolle und Authentifizierungsprüfungen implementieren, damit nur autorisierte Nutzer auf vertrauliche Funktionen und Daten zugreifen können.
Im vorherigen Beispiel gab es eine Route mit schwer zu erratenden Zahlen als Endpunkt:
In der Praxis ist es meist sicherer, auf die bewährte Methode zu vertrauen, Daten durch geeignete Authentifizierungsverfahren zu schützen, bevor Zugriff gewährt wird. Zwar empfiehlt es sich, sicherere Anmeldebibliotheken wie Passport.js oder AWS Cognito zu verwenden, doch zu Lernzwecken sehen Sie hier einen groben Entwurf einer Anmeldeseite ohne externe Bibliotheken:
Statt die Route zum Admin-Panel zu verschleiern, können Nutzer direkt auf /login zugreifen. Sie müssen jedoch die richtige E-Mail-Adresse und das richtige Passwort im Anfrage-Body angeben, bevor sie Zugriff auf das Admin-Panel erhalten. So verlassen Sie sich nicht auf riskante Verschleierungsmethoden und können besser kontrollieren, welche Informationen und/oder Antworten die einzelnen Nutzer erhalten.
Zugriff standardmäßig verweigern und granular Berechtigungen erteilen
Wenn Sie entscheiden, welche Nutzer auf welche Datentypen in Ihrer Anwendung zugreifen dürfen, empfiehlt es sich oft, ganz von vorne zu beginnen. Wenden Sie das Prinzip der geringsten Berechtigung an: Nutzer erhalten zunächst keinen Zugriff und bekommen nur dann Zugriff auf bestimmte Ressourcen und Aktionen, wenn es erforderlich ist.
Außerdem sollten Sie eine fein abgestufte Zugriffskontrolle implementieren, die Berechtigungen schrittweise erweitert. So können Nutzer nur die Aktionen ausführen, zu denen sie ausdrücklich berechtigt sind. Im vorherigen Beispiel können zusätzliche Rollen eine noch feinere Kontrolle ermöglichen:
Die höchsten Berechtigungen sind hier dem “Level 3 panel” vorbehalten, auf das nur Nutzer mit der Rolle admin zugreifen können. Andere Nutzer mit der Rolle manager erhalten nach der Anmeldung Zugriff auf ein “Level 2 panel”, das beispielsweise Informationen zu den einzelnen Nutzern enthalten kann, aber keine Schaltfläche zum Löschen.
Wer keiner Rolle ausdrücklich zugewiesen wurde, erhält automatisch die Antwort “Unauthorized access”. Wenn Sie Nutzern detaillierte Berechtigungen erteilen und diese bei Bedarf schrittweise erweitern, vermeiden Sie, dass Nutzer zusätzliche Berechtigungen erhalten, auf die sie keinen Zugriff haben sollten.
Führen Sie gründliche Audits und Tests durch
Überprüfen Sie regelmäßig Ihre Codebasis und führen Sie Sicherheitstests durch, etwa statische Codeanalysen, Dependency-Scans und sichere Code-Reviews, um Sicherheitslücken bei der Zugriffskontrolle und andere Sicherheitsprobleme zu erkennen. Es kann hilfreich sein, diese (oder eine andere) Liste möglicher Sicherheitslücken bei der Zugriffskontrolle als Lesezeichen zu speichern und damit sicherzustellen, dass Ihre Anwendung keine davon enthält. Außerdem sind Unit-Tests in Ihrer gesamten Anwendung ein gängiges Mittel, um sicherzustellen, dass jede Codezeile wie erwartet funktioniert.
Automatisierte Scan-Tools wie Static Application Security Testing (SAST) sollten Sie stets in Betracht ziehen, um gängige Sicherheitsprobleme zu erkennen. Mit der VS-Code-Erweiterung von Snyk erhalten Sie bei jedem Speichern Ihrer JavaScript-Dateien schnell Rückmeldung durch Sicherheits-Scans – einschließlich automatisierter Empfehlungen zur Behebung.
Verwenden Sie die Snyk-IDE-Erweiterung für Visual Studio Code
Ein leistungsstarkes Tool, das besonders erwähnenswert ist, ist Snyk. Snyk bietet verschiedene Tools zum Schutz Ihrer Anwendung. Insbesondere die Visual-Studio-Code-Erweiterung (VS Code) hilft Ihnen, Sicherheitslücken durch fehlerhafte Zugriffskontrollen in Ihrem Node.js-Code bereits während des Schreibens zu erkennen und zu beheben.
So richten Sie die Snyk-Erweiterung ein und nutzen sie effektiv:
Öffnen Sie in VS Code die Registerkarte Erweiterungen und suchen Sie nach „Snyk“, um die Erweiterung Snyk Security - Code, Open Source Dependencies, IaC Configurations zu finden. Klicken Sie auf Installieren:

Nach der Installation fordert Snyk Sie auf, Ihr Konto zu authentifizieren, indem Sie es mit Ihrer IDE verbinden. Klicken Sie auf VS Code mit Snyk verbinden. Daraufhin wird eine externe Snyk-Webseite geöffnet, auf der Sie um die Erlaubnis zur Verbindung gebeten werden. Klicken Sie dort auf Authentifizieren.
Klicken Sie nach der Authentifizierung auf Scannen, um Ihren Code auf Sicherheitslücken zu prüfen. Bei Bedarf können Sie die Erweiterung auch konfigurieren.
Mit den vorherigen Beispielen der Routen /admin, /login und /account konnte Snyk zwölf Sicherheitslücken erkennen. Darüber hinaus scannt Snyk Ihren Code auf mögliche Probleme mit der Codequalität, der Konfiguration und der Open-Source-Sicherheit, die entweder in Ihrer Anwendung oder den darin verwendeten Bibliotheken auftreten:


Die Snyk-Erweiterung scannt Ihren Code auf bekannte Sicherheitslücken, darunter auch solche im Zusammenhang mit der Zugriffskontrolle. Sie gibt in Echtzeit Rückmeldung und schlägt Lösungen für die erkannten Probleme vor. Mit dieser Erweiterung können Sie Sicherheitslücken durch fehlerhafte Zugriffskontrollen erkennen und beheben, bevor sie in Ihre Produktionsumgebung gelangen.
Darüber hinaus bietet Snyk verschiedene Code-Scan-Tools, die Sie verwenden können. Ähnlich wie die VS-Code-Erweiterung helfen diese Tools dabei, Sicherheitsprobleme in Ihrem Code bereits während des Schreibens zu finden. Damit sind sie unverzichtbar, um Probleme mit der Zugriffskontrolle in Echtzeit zu erkennen und zu beheben.
Fazit
In diesem Artikel haben Sie erfahren, warum fehlerhafte Zugriffskontrollen in Node.js ein kritisches Sicherheitsproblem darstellen: Sie können in Anwendungen auf Basis des Express-Webframeworks zu unbefugtem Zugriff auf Daten und Berechtigungen führen. Die Beispiele in diesem Artikel veranschaulichen die möglichen Risiken – von ungeschützten Express-Routen für Admin-Panels bis hin zu unvorhersehbaren Nutzer-IDs in Request-Parametern.
Um Sicherheitslücken durch fehlerhafte Zugriffskontrollen in Ihren Node.js-Anwendungen zu verhindern, können Sie verschiedene wichtige Maßnahmen ergreifen: Verwenden Sie aktuelle Bibliotheksversionen, vermeiden Sie Security-through-Obscurity-Methoden, wenden Sie das Prinzip der geringsten Berechtigungen an, führen Sie gründliche Audits und Tests durch und nutzen Sie Tools wie die Snyk Visual Studio Code-Erweiterung. Zusammen können diese Maßnahmen die Sicherheit Ihrer Anwendung deutlich verbessern. Denken Sie daran: Die Entwicklung und Wartung einer sicheren Anwendung ist ein fortlaufender Prozess. Wachsamkeit ist entscheidend, um die Integrität Ihrer Anwendungen und Daten zu schützen.
Nutzen Sie Snyk und beheben Sie noch heute Ihre Sicherheitsprobleme!
