Bitte beachten Sie den Code unten; Es wird geprüft, ob eine Person mit einem weiblichen Geschlecht zum Angebot berechtigt ist1:
[Fact]
public void ReturnsFalseWhenGivenAPersonWithAGenderOfFemale()
{
var personId = Guid.NewGuid();
var gender = "F";
var person = new Person(personId, gender);
var id = Guid.NewGuid();
var offer1 = new Offer1(id,"Offer1");
Assert.False(offer1.IsEligible(person));
}
Dieser Komponententest ist erfolgreich. Es wird jedoch scheitern, wenn 'Offer1' künftig Frauen angeboten wird.
Ist es akzeptabel zu sagen - wenn sich die Geschäftslogik um Angebot 1 ändert, muss sich der Komponententest ändern. Bitte beachten Sie, dass in einigen Fällen (für einige Angebote) die Geschäftslogik in der Datenbank wie folgt geändert wird:
update Offers set Gender='M' where offer=1;
und in einigen Fällen im Domain-Modell wie folgt:
if (Gender=Gender.Male)
{
//do something
}
Bitte beachten Sie auch, dass sich in einigen Fällen die dahinter stehende Domain-Logik regelmäßig ändert und in einigen Fällen nicht.
c#
unit-testing
domain-driven-design
xunit
w0051977
quelle
quelle
Antworten:
Dies ist im üblichen Sinne nicht spröde. Ein Komponententest wird als spröde angesehen, wenn er aufgrund von Implementierungsänderungen abbricht, die das zu testende Verhalten nicht beeinflussen. Aber wenn die Business - Logik selbst ändert, dann wird ein Test dieser Logik ist angeblich zu brechen.
Wenn sich die Geschäftslogik jedoch häufig ändert, ist es möglicherweise nicht angebracht, die Erwartungen in die Komponententests einzubeziehen. Stattdessen können Sie testen, ob sich die Konfigurationen in der Datenbank erwartungsgemäß auf die Angebote auswirken.
Der Name des Tests
Returns False When Given A Person With A Gender Of Female
beschreibt keine Geschäftsregel. Eine Geschäftsregel wäre so etwas wieOffers Applicable to M should not be applied to persons of gender F
.So können Sie einen Test, bestätigt schreiben könnten , dass , wenn ein Angebot als nur anwendbar definiert ist M Personen zu geben, dann wird eine Art F Person nicht als für sie angezeigt werden. Dieser Test stellt sicher, dass die Logik auch dann funktioniert, wenn sich die Konfiguration der spezifischen Angebote ändert.
quelle
Wenn die Eigenschaft in der Produktionsdatenbank (oder einem Klon zum Testen) definiert ist, handelt es sich nicht um einen Komponententest . Ein Komponententest überprüft eine Arbeitseinheit und erfordert keinen bestimmten externen Zustand, um zu arbeiten. Dies setzt voraus, dass
Offer1
in der Datenbank ein Angebot nur für Männer definiert ist. Das ist ein äußerer Zustand. Dies ist also eher ein Integrationstest , insbesondere ein System- oder Abnahmetest . Beachten Sie, dass Akzeptanztests häufig nicht per Skript ausgeführt werden (nicht in einem Testframework ausgeführt, sondern manuell von Menschen durchgeführt).Wenn die Eigenschaft im Domänenmodell mit einer
if
Anweisung definiert ist, ist derselbe Test ein Komponententest. Und es kann spröde sein. Das eigentliche Problem ist jedoch, dass der Code spröde ist. In der Regel ist Ihr Code widerstandsfähiger, wenn das Geschäftsverhalten konfigurierbar und nicht fest codiert ist. Weil eine schnelle Bereitstellung zur Behebung eines kleinen Codierungsfehlers selten sein sollte. Eine Geschäftsanforderung, die sich ohne Vorankündigung ändert, ist jedoch nur ein Dienstag (was wöchentlich geschieht).Möglicherweise verwenden Sie ein Unit-Test-Framework, um den Test auszuführen. Unit-Test-Frameworks sind jedoch nicht auf die Ausführung von Unit-Tests beschränkt. Sie können und können auch Integrationstests durchführen.
Wenn Sie einen Komponententest schreiben würden, würde erstellen Sie beide
person
undoffer1
von Grund auf ohne Vertrauen auf Datenbankstatus. So etwas wieBeachten Sie, dass sich dies basierend auf der Geschäftslogik nicht ändert. Es ist keine Behauptung,
offer1
die Frauen ablehnt. Es istoffer1
die Art von Angebot, das Frauen ablehnt.Sie können die Datenbank als Teil des Tests erstellen und konfigurieren. In C # mit NUnit oder in Java JUnit würden Sie die Datenbank in einer
Setup
Methode einrichten . Vermutlich hat Ihr Test-Framework eine ähnliche Vorstellung. Bei dieser Methode können Sie Datensätze mit SQL in die Datenbank einfügen.Wenn Sie Schwierigkeiten haben, Code zu schreiben, der die Produktionsdatenbank durch eine Testdatenbank ersetzt, klingt dies nach einer Testschwäche in Ihrer Anwendung. Zum Testen ist es besser, so etwas wie eine Abhängigkeitsinjektion zu verwenden, die eine Substitution ermöglicht. Dann könnten Sie Tests schreiben, die unabhängig von den aktuellen Geschäftsregeln sind.
Ein Nebeneffekt davon ist, dass es für den Geschäftsinhaber häufig einfacher ist (nicht unbedingt für den Unternehmensinhaber, sondern eher für die Person, die in der Unternehmenshierarchie für dieses Produkt verantwortlich ist), die Geschäftsregeln direkt zu konfigurieren. Wenn Sie über ein solches technisches Framework verfügen, ist es einfach, dem Geschäftsinhaber die Verwendung einer Benutzeroberfläche (UI) zur Konfiguration des Angebots zu ermöglichen. Der Geschäftsinhaber würde die Einschränkung in der Benutzeroberfläche auswählen und den
markLimitedToGender("M")
Aufruf ausgeben . Wenn das Angebot dann in der Datenbank gespeichert wird, wird dies gespeichert. Sie müssten das Angebot jedoch nicht speichern, um es zu verwenden. Ihre Tests könnten also ein Angebot erstellen und konfigurieren, das nicht in der Datenbank vorhanden ist.In Ihrem System müsste der Geschäftsinhaber, wie beschrieben, eine Anforderung an die technische Gruppe senden, die die entsprechende SQL-Anweisung ausgibt und die Tests aktualisiert. Oder die technische Gruppe muss Ihren Code und Ihre Tests bearbeiten (oder testet dann den Code). Das scheint ein ziemlich schwerer Ansatz zu sein. Du kannst es schaffen. Aber Ihre Software (nicht nur Ihre Tests) wäre weniger spröde, wenn Sie dies nicht tun müssten.
TL; DR : Sie können Tests wie diese schreiben, aber Sie sind möglicherweise besser dran, Ihre Software zu schreiben, damit Sie dies nicht tun müssen.
quelle