Swift-Sicherheit: SQL-Injection und XSS – wie man Code schützt

Online Python-Trainer für Anfänger

Lernen Sie Python einfach ohne theoretische Überlastung. Lösen Sie praktische Aufgaben mit automatischer Überprüfung und schreiben Sie Code direkt im Browser.

Kurs starten

Swift an vorderster Front: Warum Sicherheit keine Option, sondern eine Notwendigkeit ist

\n

Sie programmieren in Swift, sind stolz auf Leistung und schönen Code. Aber haben Sie schon einmal darüber nachgedacht, wie anfällig Ihre App für Angriffe ist? SQL-Injection und XSS (Cross-Site-Scripting) sind nicht nur Gruselgeschichten aus Lehrbüchern. Es sind reale Bedrohungen, die Sie Ihre Benutzerdaten, Ihren Ruf und Ihr Geld kosten können.

\n

In diesem Artikel analysieren wir, wie Sie Ihre Swift-App (sei es ein iOS-Client oder ein Server-Backend mit Vapor) vor den beiden gefährlichsten Angriffsarten schützen. Kein überflüssiges Wissen – nur praktische Beispiele, fertige Lösungen und lebendiger Code. Los geht's!

\n\n

SQL-Injection in Swift: Wie Hacker die Datenbank „austricksen“

\n

Stellen Sie sich vor: Ein Benutzer gibt in ein Textfeld '; DROP TABLE Users; -- ein. Wenn Sie diese Zeichenfolge direkt in eine SQL-Abfrage einfügen, führt die Datenbank den Löschbefehl aus. Ein Klassiker.

\n

In Swift tritt diese Schwachstelle am häufigsten in Server-Frameworks (Vapor, Kitura) oder bei der Arbeit mit Core Data und SQLite über unsichere Wrapper auf.

\n\n

Gefährliches Beispiel: Wie man es NICHT machen sollte

\n
import SQLite\n\nlet username = userInput.text // "admin' OR '1'='1"\nlet query = "SELECT * FROM users WHERE name = '\\(username)'"\ntry db.execute(query) // BEDROHUNG! Kompromittierte Abfrage\n
\n

Dieser Code ist ein rotes Tuch. Ein Angreifer kann auf beliebige Daten zugreifen oder die Tabelle zerstören.

\n\n

Der richtige Ansatz: Parametrisierte Abfragen

\n

Goldene Regel: Fügen Sie Benutzereingaben niemals direkt in eine Abfragezeichenfolge ein. Verwenden Sie Parametrisierung.

\n
import SQLite\n\nlet db = try Connection("path/to/db.sqlite3")\nlet users = Table("users")\nlet name = Expression<String>("name")\n\nlet username = userInput.text // "admin' OR '1'='1"\nlet query = users.filter(name == username) // SICHER\nlet result = try db.prepare(query)\n
\n

Die Bibliothek SQLite.swift maskiert Sonderzeichen automatisch. Für Vapor mit Fluent verwenden Sie Modelle und Filter:

\n
import Fluent\nimport Vapor\n\nstruct UserController: RouteCollection {\n    func login(req: Request) async throws -> String {\n        let input = try req.content.decode(LoginRequest.self)\n        // Fluent parametrisiert die Abfrage automatisch\n        let user = try await User.query(on: req.db)\n            .filter(\\.$name == input.username)\n            .first()\n        return user?.name ?? "Not found"\n    }\n}\n
\n

Wichtig: Selbst wenn Sie in Vapor raw SQL verwenden, nutzen Sie SQLBind zur Parameterbindung.

\n\n

ORM und Core Data: Die Illusion der Sicherheit

\n

Viele Entwickler glauben, dass Core Data oder Fluent automatisch vor Injection schützen. Das stimmt – solange Sie kein NSExpression mit Zeichenfolgenformatierung oder raw SQL verwenden. Aber merken Sie sich: Jedes NSPredicate, das durch Zeichenfolgeninterpolation erstellt wird, birgt ein Risiko.

\n
// GEFÄHRLICH\nlet predicate = NSPredicate(format: "name == %@", userInput) // Sicher?\n// NEIN! Wenn userInput '%' enthält, kann eine Injection durch Substitution erfolgen.\n
\n

Verwenden Sie immer %@ mit Variablen, nicht %K mit Schlüsseln, und fügen Sie Zeichenfolgen niemals über \\() ein.

\n\n

XSS-Angriffe in Swift: Wenn ein Angreifer JavaScript einschleust

\n

XSS ist ein Angriff, bei dem ein bösartiges Skript im Browser des Benutzers ausgeführt wird. Für iOS-Apps ist XSS relevant, wenn Sie WKWebView zur Anzeige von HTML-Inhalten verwenden (z. B. in einem Nachrichtenfeed oder Chat).

\n\n

Reales Szenario: Chat mit HTML-Formatierung

\n

Ein Benutzer schreibt: Hallo! <script>alert('XSS')</script>. Wenn Sie diese Nachricht ohne Verarbeitung in einer WebView anzeigen – wird das Skript ausgeführt.

\n
// GEFÄHRLICH\nlet html = "<div>\\(message.text)</div>"\nwebView.loadHTMLString(html, baseURL: nil)\n

Blogs

Buchempfehlungen