Der Query Builder von Laravel stellt eine flüssige Schnittstelle zum Aufbauen und Ausführen von Datenbankabfragen bereit. Sie starten mit der Methode table() der Fassade DB und kombinieren die Abfrage per Method-Chaining.
use Illuminate\Support\Facades\DB;$users = DB::table('users')->get();
Intern werden PDO-Parameterbindings verwendet – SQL-Injection wird also automatisch verhindert.
Der Query Builder funktioniert auf allen von Laravel unterstützten Datenbanken (MySQL, MariaDB, PostgreSQL, SQLite, SQL Server). Der Code bleibt beim Wechsel der Datenbank unverändert.
// Ersten Datensatz holen (null, wenn nicht gefunden)$user = DB::table('users')->where('name', 'Max Mustermann')->first();// Exception werfen, wenn nicht gefunden (liefert automatisch eine 404)$user = DB::table('users')->where('name', 'Max Mustermann')->firstOrFail();// Nur den Wert einer bestimmten Spalte$email = DB::table('users')->where('name', 'Max Mustermann')->value('email');// Per ID$user = DB::table('users')->find(3);
// Collection der E-Mail-Werte$emails = DB::table('users')->pluck('email');// Assoziative Collection: Name als Schlüssel, E-Mail als Wert$emailByName = DB::table('users')->pluck('email', 'name');
use Illuminate\Support\Collection;// In Blöcken von 100 verarbeitenDB::table('users')->orderBy('id')->chunk(100, function (Collection $users) { foreach ($users as $user) { // Verarbeitung... }});// Beim Aktualisieren während des Chunking chunkById verwendenDB::table('users')->where('active', false) ->chunkById(100, function (Collection $users) { foreach ($users as $user) { DB::table('users') ->where('id', $user->id) ->update(['active' => true]); } });
Wenn Sie während des Chunking Datensätze aktualisieren oder löschen, verwenden Sie statt chunk() immer chunkById(). Mit chunk() können Datensätze verschoben werden und übersprungen werden.
use Illuminate\Database\Query\Builder;// OR-Bedingungen zusammenklammern und mit AND kombinieren$users = DB::table('users') ->where('active', true) ->where(function (Builder $query) { $query->where('role', 'admin') ->orWhere('role', 'moderator'); }) ->get();// WHERE active = 1 AND (role = 'admin' OR role = 'moderator')
whereNullSafeEquals und orWhereNullSafeEquals behandeln zwei NULL-Werte als gleich.Beim gewöhnlichen =-Operator ist NULL = NULLfalse, whereNullSafeEquals betrachtet NULL und NULL als gleich. Es entspricht dem Operator <=> in MySQL und IS NOT DISTINCT FROM in PostgreSQL.
$lastLoginIp = $request->input('last_login_ip');// Auch wenn $lastLoginIp null ist, werden Benutzer mit last_login_ip IS NULL gefunden$users = DB::table('users') ->whereNullSafeEquals('last_login_ip', $lastLoginIp) ->get();
Ein normales where('column', null) wird zu WHERE column IS NULL; whereNullSafeEquals('column', $value) verhält sich hingegen konsistent, egal ob der gebundene Wert null ist oder nicht. Besonders praktisch, wenn Nutzereingaben null sein können.
Raw-Ausdrücke werden als SQL-String direkt eingebettet. Nutzerinput hier ungeprüft weiterzugeben, birgt SQL-Injection-Risiko. Verwenden Sie unbedingt Bindings.
// DB::raw() — beliebigen SQL-Ausdruck einbetten$users = DB::table('users') ->select(DB::raw('count(*) as user_count, status')) ->groupBy('status') ->get();// selectRaw — Raw-Ausdruck in SELECT$orders = DB::table('orders') ->selectRaw('price * ? as price_with_tax', [1.10]) ->get();// whereRaw — Raw-Ausdruck in WHERE$orders = DB::table('orders') ->whereRaw('price > IF(state = "JP", ?, 100)', [500]) ->get();// havingRaw — Raw-Ausdruck in HAVING$orders = DB::table('orders') ->select('department', DB::raw('SUM(amount) as total')) ->groupBy('department') ->havingRaw('SUM(amount) > ?', [100000]) ->get();// orderByRaw — Raw-Ausdruck in ORDER BY$orders = DB::table('orders') ->orderByRaw('updated_at - created_at DESC') ->get();
// Löschen mit Bedingung$deleted = DB::table('users')->where('status', 'inactive')->delete();// Gesamte Tabelle leeren (AUTO_INCREMENT wird zurückgesetzt)DB::table('users')->truncate();
// Erzeugten SQL-String anzeigen$sql = DB::table('users')->where('active', true)->toSql();// "select * from `users` where `active` = ?"// SQL und Bindings prüfen$bindings = DB::table('users')->where('active', true)->getBindings();// Abfrage ausführen und dumpen (Ausführung fortsetzen)DB::table('users')->where('active', true)->dump();// Abfrage ausführen, dumpen und beendenDB::table('users')->where('active', true)->dd();
dd() ist zum Debuggen praktisch, sollte in Produktion aber niemals eingesetzt werden. Sicher ist der Blick auf SQL und Bindings über toSql() und getBindings().
Der Query Builder ist eine niedrigere Ebene als Eloquent und gibt statt Model-Instanzen stdClass-Objekte zurück.
Wenn Sie Beziehungen oder Modell-Events (Observer) nicht benötigen, ist der Query Builder einfacher und schneller.