FlawOpen

flawopen.com/SQL-Injection in JavaScript/Knex.js

Ist Knex.js vor SQL-Injection geschützt?

Referenzleitfaden
Kurzantwort

Stell dir SQL als Formular vor: Ein Binding setzt die Eingabe in ein Wertefeld; Interpolation fügt sie in die Anweisungen ein. Knex’ Query Builder und knex.raw(sql, bindings) trennen Werte. Tabellen- und Spaltennamen sind jedoch SQL-Struktur und brauchen eine vertrauenswürdige Allowlist.

?? ist Knex’ Raw-Bezeichnerplatzhalter. Er quotet den Bezeichner, autorisiert die Auswahl aber nicht; verwende eine Allowlist.
SICHER — Bindings und Allowlist
const query = knex.raw(
  `SELECT * FROM users WHERE id = ${userId}`
);
UNSICHER — SQL aus Eingabe
// Eingabe wird an SQL angehängt.
const allowedSortColumns = new Set(["created_at", "name"]);

const rows = await knex("users")
  .where("id", userId)
  .orderBy(
    allowedSortColumns.has(requestedSort)
      ? requestedSort
      : "created_at",
    requestedDirection === "asc" ? "asc" : "desc"
  );

// Wert und SQL-Syntax getrennt halten.
knex.raw("SELECT * FROM users WHERE id = ?", [userId]);

Wie Knex-Bindings Werte schützen

Methoden wie .where(), .insert() und .select() trennen Werte vom erzeugten SQL. Übergib Raw-Werte als Bindings: knex.raw("... = ?", [value]). ? steht für Werte, ?? für Bezeichner. Interpoliere Eingaben nicht in SQL-Strings.

Dynamische Bezeichner brauchen eine Allowlist

Ein Binding autorisiert keine vom Nutzer gewählten Spalten, Tabellen, Sortierungen, Operatoren oder SQL-Fragmente. ?? quotet einen Bezeichner, entscheidet aber nicht über die Berechtigung. Ordne die Auswahl vor .orderBy() einer festen Allowlist zu; SQL-Schlüsselwörter und Operatoren bleiben im Code fest.

Raw-Abfragen überprüfen

Suche alle knex.raw()-Aufrufe und prüfe SQL-String und Bindings gemeinsam. Datenwerte müssen Bindings verwenden; dynamische Bezeichner müssen aus einer kleinen Allowlist stammen. Raw bedeutet nicht automatisch verwundbar; entscheidend sind SQL-Aufbau und Eingaben.

rg -n 'knex\.raw\(' -g '*.js' -g '*.ts' -g '*.mjs' -g '*.cjs' .

Häufige Fragen

Verhindert knex.raw() SQL-Injection von selbst?

Nein. Nutze Bindings für nicht vertrauenswürdige Werte, etwa knex.raw("... = ?", [value]). Interpolation macht den Wert zum Teil des SQL-Quelltexts. Prüfe jeden Raw-Aufruf und seine Eingaben.

Kann ich ?? nutzen und jede Nutzerspalte akzeptieren?

?? ist Knex’ Raw-Bezeichnerplatzhalter. Er quotet den Bezeichner, autorisiert die Auswahl aber nicht; verwende eine Allowlist.

Quellen

Siehe auch SQL-Injection (CWE-89): Funktionsweise und Schutz in jeder Sprache — flawopen.com MyBatis ${} vs. #{}: SQL Injection verhindern MySQLi vs. PDO: sichere Prepared Statements Schützt NHibernate vor SQL-Injection? MongoDB NoSQL Injection: sichere Abfragefilter Können auch numerische IDs SQL Injection verursachen? Was ist eine parametrisierte Abfrage?