Für einfache Tests ist es durchaus akzeptabel, die Datenbankzugriffsebene zu verspotten. Sie rufen an getName()
, es ruft das verspottete DAO auf und gibt "John" für den Vornamen und "Smith" für den Nachnamen zurück, setzt sie zusammen und alles ist perfekt. Es ist nicht erforderlich, eine Datenbank dort tatsächlich als Einheit zu testen.
Die Dinge werden ein bisschen komplexer, wenn die Logik ein bisschen komplexer wird. Was wäre, wenn Sie eine Methode "createOrUpdateUser (...)" hätten? Wenn Sie die Datenbank verspottet haben, können Sie überprüfen, ob eine bestimmte Methode einmal mit einem bestimmten Parameter aufgerufen wurde, wenn die Verspottung keine Objekte zurückgibt, und eine andere Methode für die Datenbank aufgerufen wird, wenn sie ein vorhandenes Objekt zurückgibt. Dies führt zu der unscharfen Zeile, in der es möglicherweise einfacher ist (insbesondere, wenn sie bereits vorhanden ist), eine spezialisierte Speicherdatenbank hochzufahren und diesen Code mit vorkonfigurierten Daten zu testen.
In einem Code, an dem ich gearbeitet habe (Verkaufsstelle), hatten wir eine resumeSuspededTransaction(...)
Methode. Dies würde die Transaktion aus der Datenbank in ein Objekt (und seine Komponenten) ziehen und die Datenbank aktualisieren. Wir hatten es verspottet und irgendwo im Code lauerte ein Fehler mit der Serialisierung und Deserialisierung der Daten, die in die Datenbank gingen (wir haben einen Typ geändert, der in der Datenbank anders serialisiert wurde).
Der Mock hat uns den Fehler nicht gezeigt, weil er seinen fehlerfreien Pfad zurückgegeben hat - serialisieren Sie die Transaktion, speichern Sie sie im Mock, deserialisieren Sie sie vom Mock und testen Sie, ob sie gleich sind. Wenn Sie jedoch ein Objekt mit einer führenden Null in die Datenbank serialisieren, löschte es diese und kombinierte sie dann wieder zu einer Zeichenfolge ohne Nullen. Wir haben den Fehler ohne die Datenbank durch Fehlerbehebung entdeckt (es war nicht so schwer zu erkennen, sobald wir wussten, dass es da ist).
Später haben wir dort eine Datenbank abgelegt und festgestellt, dass der Fehler diesen Junit-Test nie bestanden hätte, wenn wir stattdessen eine In-Memory-Datenbank verwendet hätten.
In Speicherdatenbanken haben die Vorteile:
- Sie können schnell gestartet werden (ohne dass ein Datenbankadministrator zum Einrichten von Konten, Tabellen usw. erforderlich ist)
- Die Daten können für diesen Test vorkonfiguriert werden
- Der Test muss sich nicht darum kümmern, den Test zurückzusetzen, wenn er abgeschlossen ist
- Jeder Test verfügt über eine eigene Speicherdatenbank, sodass Sie sich keine Sorgen machen müssen, wenn zwei Tests gleichzeitig ausgeführt werden
- Sie können auf Systemen ausgeführt werden, die keine Verbindung zu den realen Datenbanken haben