Frage

Ich bin neu in Mock-Objekte, aber ich verstehe, dass ich meine Klassen Schnittstellen implementieren haben, um sie zu verspotten.

Das Problem, das ich habe, ist, dass in meiner Datenzugriffsschicht, ich statische Methoden haben will, aber ich kann nicht eine statische Methode in einer Schnittstelle setzen.

Was ist der beste Weg, um dies? Soll ich nur Instanzmethoden verwenden (was falsch scheint) oder gibt es eine andere Lösung?

War es hilfreich?

Lösung

Ich würde ein Verfahren Objektmuster verwenden. Haben Sie eine statische Instanz dieser, und es in der statischen Methode aufrufen. Es sollte möglich sein, für die Prüfung zu Unterklasse, abhängig von Ihrem Mockframework.

d. in der Klasse mit der statischen Methode hat:

private static final MethodObject methodObject = new MethodObject();

public static void doSomething(){
    methodObject.doSomething();
}

und Ihre Methode Objekt kann ein sehr einfach sein, leicht getestet:

public class MethodObject {
    public void doSomething() {
        // do your thang
    }
}

Andere Tipps

Ja, verwenden Sie Instanzmethoden. Statische Methoden im Grunde sagen: „Es gibt einen Weg, um diese Funktionalität zu erreichen - es ist nicht polymorph ist.“ Mocking beruht auf Polymorphismus.

Nun, wenn Ihre statische Methoden logisch nicht kümmern, was Implementierung Sie verwenden, könnten sie in der Lage sein, die Schnittstellen als Parameter zu nehmen, oder vielleicht arbeiten, ohne überhaupt mit staatlichen interagieren - aber ansonsten sollten Sie verwenden Instanzen (und wahrscheinlich Dependency Injection alles Draht zusammen).

Ich habe eine Blog via google mit einigen großen Beispielen dafür, wie dies zu tun:

  1. Umgestalten Klasse eine Instanz der Klasse und implementieren eine Schnittstelle sein.

    Sie haben bereits erklärt, dass Sie nicht wollen, dies zu tun.

  2. Verwenden Sie eine Wrapper-Instanz der Klasse mit den Delegierten für statische Klassen Mitglieder

    Dadurch Sie eine statische Schnittstelle über Teilnehmer simulieren können.

  3. eine Wrapper-Instanz der Klasse mit geschützten Elemente verwenden, die die statische Klasse aufrufen

    Dies ist wahrscheinlich die am einfachsten zu verspotten / verwalten, ohne, wie es Refactoring kann nur aus und erweitert vererbt werden.

Sie könnten versuchen, bei einem zu tiefem Ausgangspunkt zu testen. Ein Test muss nicht jede einzelne Methode zu testen individuell erstellt werden; private und statische Methoden durch Aufrufen der öffentlichen Methoden getestet werden sollten, die dann die private und statische diejenigen wiederum nennen.

kann also sagen, dass Ihr Code wie folgt lautet:

public object GetData()
{
 object obj1 = GetDataFromWherever();
 object obj2 = TransformData(obj1);
 return obj2;
} 
private static object TransformData(object obj)
{
//Do whatever
}

Sie brauchen nicht einen Test gegen die TransformData Methode zu schreiben (und Sie können nicht). Statt einen Test für die Methode GetData schreiben, die die Arbeit in TransformData Tests durchgeführt.

Instanz-Methoden verwenden, wenn möglich.

Verwenden public static Func [T, U] (statische Funktion für Referenzen, die mock-Funktionen substituiert sein kann), in dem Instanzmethoden nicht möglich sind.

Eine einfache Lösung ist die statische Klasse-Implementierung über einen Setter zu ermöglichen, zu ändern:

class ClassWithStatics {

  private IClassWithStaticsImpl implementation = new DefaultClassWithStaticsImpl();

  // Should only be invoked for testing purposes
  public static void overrideImplementation(IClassWithStaticsImpl implementation) {
     ClassWithStatics.implementation = implementation;
  }

  public static Foo someMethod() {
    return implementation.someMethod();
  }

}

So in der Einrichtung Ihrer Tests, rufen Sie overrideImplementation mit etwas verspottet Schnittstelle. Der Vorteil ist, dass Sie nicht brauchen, um Kunden Ihrer statischen Klasse zu ändern. Der Nachteil ist, dass Sie wahrscheinlich ein wenig duplizierten Code haben werden, weil Sie die Methoden der statischen Klasse wiederholen werden müssen, und es ist die Umsetzung. Aber einige Male die statischen Methoden können eine ligther Schnittstelle verwenden, die Basis funcionality liefern.

Das Problem, das Sie haben, wenn Sie 3rd-Party-Code verwenden und es ist von einem Ihrer Methoden aufgerufen. Was wir am Ende ist es zu tun in einem Objekt Einwickeln, und nannte es in mit dep inj vorbei, und dann können Sie Ihre Unit-Test-3rd-Party-statische Methode rufen Sie die Setter damit verspotten.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top