„Wenn ein Arbeiter seine Arbeit gut machen will, muss er zuerst seine Werkzeuge schärfen.“ – Konfuzius, „Die Gespräche des Konfuzius. Lu Linggong“
Titelseite > Programmierung > Konzentrieren Sie Ihre Tests auf die Domäne. Ein PHPUnit-Beispiel

Konzentrieren Sie Ihre Tests auf die Domäne. Ein PHPUnit-Beispiel

Veröffentlicht am 03.11.2024
Durchsuche:380

Einführung

Oft versuchen Entwickler, 100 % (oder fast 100 %) ihres Codes zu testen. Anscheinend ist dies das Ziel, das jedes Team für seine Projekte erreichen sollte, aber aus meiner Sicht sollte nur ein Teil des gesamten Codes vollständig getestet werden: Ihre Domain.

Die Domäne ist im Grunde der Teil Ihres Codes, der definiert, was das Projekt tatsächlich tut. Wenn Sie beispielsweise eine Entität in der Datenbank beibehalten, ist Ihre Domäne nicht für die Beibehaltung dieser Entität in der Datenbank verantwortlich, sondern dafür, sicherzustellen, dass die beibehaltenen Daten für Ihr Geschäftsmodell sinnvoll sind. Wenn Sie Ihre Daten in der Datenbank speichern, verwenden Sie möglicherweise eine externe Bibliothek wie PHP Doctrine. Diese Bibliothek ist bereits vollständig getestet, es besteht keine Notwendigkeit, ihre Funktionen zu testen. Wenn Sie die richtigen Daten an doctrine übergeben, werden diese ohne Probleme in der Datenbank gespeichert.

Das in den folgenden Abschnitten gezeigte Beispiel versucht nicht zu zeigen, wie das Domain Driven Design funktioniert, es gibt viele Artikel, die es sehr gut erklären. Ich werde versuchen zu zeigen, wie eine gut definierte und entkoppelte Domäne dazu beitragen kann, die Tests einfacher zu gestalten und sich auf die Funktionsweise Ihrer Anwendung zu konzentrieren.

Das Beispiel basiert auf einer Symfony-Umgebung und unter Verwendung der PHPUnit-Bibliothek, aber die Idee ist für jede Sprache oder jedes Framework gültig.

Der zu testende Code

Stellen wir uns vor, dass unsere Anwendung eine Verbindung zu einer externen API herstellt, die Daten über die Regenwahrscheinlichkeit für ein bestimmtes Datum zurückgibt. Die zurückgegebenen Daten sehen folgendermaßen aus:


{
   "date" : "2022-12-01",
   "rain_probability" : 0.75
}


Jetzt müssen wir diese Daten nehmen und sie gemäß dieser Zuordnung klassifizieren:

  • rain_probability LOW
  • rain_probability ≥ 0,40 && rain_probability MEDIUM
  • rain_probability ≥ 0,75: HIGH

und speichern Sie das Ergebnis in einer Datenbanktabelle, die durch die folgende Entität beschrieben wird:


#[ORM\Entity(repositoryClass: RainMeasure::class)]
class RainMeasure {

    #[ORM\Column]
    private string $date;

    #[ORM\Column]
    private float $probability;

    #[ORM\Column(length: 10)]
    private string $label;

    // Getters and setters
    // .......
}


Lassen Sie uns einen Handler erstellen, der die externen API-Daten abruft, die Beschriftung entsprechend der Regenwahrscheinlichkeit festlegt und sie in der Datenbank speichert.


class RainMeassureHandler {
    private EntityManagerInterface $em;

    public function __construct(EntityManagerInterface $em)
    {
        $this->em = $em;
    }

    public function saveMeasure(array $measureData): void
    {
        if($measureData['rain_probability'] = 0.40 && $measureData['rain_probability'] setDate($measureData['date']);
        $rainMeasure->setProbability($measureData['rain_probability']);
        $rainMeasure->setLabel($label);

        $this->em->persist($rainMeasure);
        $this->em->flush();
    }
}


Wenn wir versuchen, einen Test für den obigen Handler zu erstellen, werden wir feststellen, dass wir das EntityManagerInterface einfügen müssen, da das Verhalten, das wir testen möchten (Festlegen einer Bezeichnung entsprechend dem Wahrscheinlichkeitswert), ist im selben Handler gekoppelt, der das Ergebnis in der Datenbank speichert. Wir könnten versuchen, das EntityManagerInterface mithilfe von Mocks und Stubs zu laden, aber ist das notwendig? Offensichtlich nicht. Wie bereits erwähnt, sollten wir versuchen, uns auf das Testen des Verhaltens zu konzentrieren, das zu unserer Domäne gehört, nämlich das Erhalten der richtigen Bezeichnung entsprechend der Regenwahrscheinlichkeit.

Entkopplungsverhalten wollen wir testen

Um unseren Test zu vereinfachen, verschieben wir das Verhalten, das wir testen möchten, in eine andere Klasse:


class RainMeasureLabelHandler 
{
    public function getLabelFromProbability(float $prob): string
    {
        if($prob = 0.40 && $prob 

Und jetzt sieht unser RainMeassureHandler so aus:


class RainMeasureHandler 
{
    private EntityManagerInterface $em;

    public function __construct(EntityManagerInterface $em)
    {
        $this->em = $em;
    }

    public function saveMeasure(array $measureData): void
    {
        $rainMeasureLabelHandler = new RainMeasureLabelHandler();
        $label = $rainMeasureLabelHandler->getLabelFromProbability($measureData['rain_probability']);

        $rainMeasure = new RainMeasure();
        $rainMeasure->setDate($measureData['date']);
        $rainMeasure->setProbability($measureData['rain_probability']);
        $rainMeasure->setLabel($label);

        $this->em->persist($rainMeasure);
        $this->em->flush();
    }
}


Jetzt können wir uns darauf konzentrieren, unseren RainMeasureLabelHandler zu testen, der Teil unserer Domäne wäre und keine Abhängigkeiten zu externen Ebenen hätte. Das Testen wäre so einfach wie gezeigt:

Focusing your tests on the domain. A PHPUnit example

Abschluss

Ich möchte sagen, dass auch andere Arten von Tests nützlich wären. Vielleicht haben wir eine API und möchten Eingaben und Ausgaben mit einer Testumgebung testen, die Datenbanken und andere Ressourcen enthält, die wir möglicherweise benötigen. Denken Sie jedoch daran, Ihre Domain zu entkoppeln und vollständig zu testen.

Freigabeerklärung Dieser Artikel ist reproduziert unter: https://dev.to/icolomina/focusing-your-tests-on-domain-a-phpunit-example-c82?1 Wenn es zu Verstößen besteht, wenden Sie sich bitte an [email protected], um ihn zu löschen.
Neuestes Tutorial Mehr>

Haftungsausschluss: Alle bereitgestellten Ressourcen stammen teilweise aus dem Internet. Wenn eine Verletzung Ihres Urheberrechts oder anderer Rechte und Interessen vorliegt, erläutern Sie bitte die detaillierten Gründe und legen Sie einen Nachweis des Urheberrechts oder Ihrer Rechte und Interessen vor und senden Sie ihn dann an die E-Mail-Adresse: [email protected] Wir werden die Angelegenheit so schnell wie möglich für Sie erledigen.

Copyright© 2022 湘ICP备2022001581号-3