Sicherheitstests für Go-Projekte mit DepGraphs verbessern
Antonio Gomes
26. August 2020
0 Min. LesezeitWir freuen uns, die deutlich verbesserte Performance von Sicherheitstests für Go-Projekte über die Snyk CLI bekannt zu geben. In einigen Fällen verkürzt sich die Scan-Zeit um mehr als 90 %! Diese Verbesserung, die bald auch für weitere Sprachen eingeführt wird, wurde durch Änderungen an unserer Scan-Methode ermöglicht. Dadurch kann Snyk riesige Projekte verarbeiten – sogar Projekte in der Größenordnung von Kubernetes! (Mehr dazu weiter unten.)
Abhängigkeiten, Abhängigkeiten und noch mehr Abhängigkeiten
Anwendungen und Projekte gibt es in den unterschiedlichsten Formen und Größen. Eines haben sie jedoch alle gemeinsam: Sie enthalten Open-Source-Abhängigkeiten. Als Mitglied des Snyk Language-Teams kann ich außerdem mit Überzeugung sagen, dass Projekte, die zunächst klein sind und nur wenige Abhängigkeiten umfassen, schnell wachsen und zu größeren Projekten mit Dutzenden, wenn nicht Hunderten direkter und transitiver Abhängigkeiten werden.
Die Anzahl der Abhängigkeiten in einem Projekt kann sich direkt auf die Scan-Performance auswirken. Als einige unserer Nutzer von langsamen Scans und Monitoring ihrer Go-Projekte berichteten, machten wir uns auf die Suche nach einer langfristigen Lösung, die mit unseren Nutzern und ihren Projekten mitwachsen kann. Die Lösung, für die wir uns schließlich entschieden, war die Migration der Datenstruktur unserer Anwendung von dependedencyTrees zu dependencyGraphs.
DepTrees vs. DepGraphs: Sicherheitstests verbessern
Beim Scannen der Manifestdatei eines Projekts wird ein dependencyTree erstellt, der alle darin verwendeten Open-Source-Abhängigkeiten auflistet – direkte und transitive. Für kleine Projekte eignet sich diese Methode, bei größeren erwies sie sich jedoch als problematisch. Die dependencyTrees wurden zu groß und beanspruchten unverhältnismäßig viel Arbeitsspeicher.
Zur Veranschaulichung und Einordnung sehen wir uns ein einfaches Beispiel an: die Verarbeitung eines kleinen Go-Projekts mithilfe eines dependencyTree.

Einfaches Beispiel für die Verarbeitung eines Go-Projekts mithilfe eines Dependency Trees
Die aufgelösten Abhängigkeiten dieses kleinen Go-Projekts sehen mit dependencyTree folgendermaßen aus:

Selbst bei nur drei direkten Open-Source-Abhängigkeiten führen die enthaltenen transitiven Abhängigkeiten zu einem dependencyTree mit einer Größe von 11 MB. Stellen Sie sich ein Projekt mit mehr als 100 direkten Abhängigkeiten vor. Der resultierende dependencyTree wäre riesig und würde Scans höchstwahrscheinlich verlangsamen oder sogar einen CLI-Scan mit einem OutOfMemory-Fehler zum Absturz bringen.
Das von dependencyGraph bereitgestellte Datenmodell löst dieses Problem. Mithilfe von Knoten und Kanten müssen wir dieselbe Abhängigkeit nicht mehr mehrfach aufnehmen. Dadurch wird enorm viel Arbeitsspeicher eingespart, wie die folgende Abbildung zeigt:

Für dasselbe einfache Projekt, das wir uns zuvor angesehen haben, umfasst der dependencyGraph jetzt 51 KB. Das ist eine deutliche Verringerung gegenüber 11 MB!
Mehr Performance bei … Kubernetes-Sicherheitsscans
Die Migration von dependencyTree zu dependencyGraph hatte enorme Auswirkungen und beseitigte die zuvor bei Go-Projekten aufgetretenen Performanceprobleme.
Eine besonders interessante Erfolgsgeschichte ist ein Projekt, von dem einige unserer Leser vielleicht schon gehört haben: Kubernetes.
Beim Versuch, das Kubernetes-Projekt mit Snyk auf Schwachstellen zu scannen, waren wir auf Schwierigkeiten gestoßen. Diese waren eine direkte Folge des bisherigen Datenmodells dependencyTree und der enormen Größe des Projekts.
Der neue dependencyGraph half, diese Probleme zu lösen. Tests des Kubernetes-Hauptrepositorys mit der Snyk CLI sind jetzt schnell und ergeben eine Datei mit einer Größe von 1,1 MB – für ein derart großes und vielschichtiges Projekt völlig akzeptabel.

Wie geht es weiter?
Da wir wissen, dass Performance bei großen Projekten für unsere Nutzer ein zentrales Anliegen ist, verbessern wir kontinuierlich unsere Unterstützung für Programmiersprachen und Ökosysteme. Die Migration zu dependencyGraph ist ein Beispiel dafür. Das Feedback unserer Nutzer nach dieser Änderung war äußerst positiv.
Wie bereits erwähnt, wurden diese Änderungen kürzlich für Go-Projekte in der Snyk CLI umgesetzt. Java-Nutzer wird es freuen zu hören, dass wir auch für Java-Gradle-Projekte zu dependencyGraph migriert sind. Auch hier gilt: nur in der CLI.
Noch bessere Nachrichten: Wir planen, die Migration auf die neue Datenstruktur zu beschleunigen. Zunächst für weitere Sprachen über die CLI (npm, yarn, maven, sbt), anschließend auch außerhalb der CLI für unsere Git-basierten Integrationen.
Weitere Neuigkeiten dazu gibt es bald. Bleiben Sie also dran – und noch wichtiger: Bleiben Sie sicher!
Starten Sie mit Capture-the-Flag
Erfahren Sie in unserem virtuellen On-Demand-Workshop für Einsteiger, wie Sie Capture-the-Flag-Challenges lösen.