Ich verwende Mockitos @Mock
und @InjectMocks
Annotationen, um Abhängigkeiten in private Felder einzufügen, die mit Spring's kommentiert sind @Autowired
:
@RunWith(MockitoJUnitRunner.class)
public class DemoTest {
@Mock
private SomeService service;
@InjectMocks
private Demo demo;
/* ... */
}
und
public class Demo {
@Autowired
private SomeService service;
/* ... */
}
Jetzt möchte ich auch reale Objekte in private @Autowired
Felder einfügen (ohne Setter). Ist dies möglich oder beschränkt sich der Mechanismus nur auf das Injizieren von Mocks?
MockitoAnnotations.initMocks(this);
in der@Before
Methode. Ich weiß, dass es nicht direkt mit der ursprünglichen Frage zusammenhängt, sondern mit jemandem, der später vorbeikommt, der hinzugefügt werden müsste, um diese Frage ausführbar zu machen.@RunWith(MockitoJUnitRunner.class)
) verwenden, brauchen Sie die Linie nichtMockitoAnnotations.initMocks(this);
Antworten:
Verwenden Sie
@Spy
AnmerkungenMockito betrachtet alle Felder mit
@Mock
oder mit@Spy
Anmerkungen als potenzielle Kandidaten, die in die mit@InjectMocks
Anmerkungen versehene Instanz eingefügt werden sollen. Im obigen Fall wird die'RealServiceImpl'
Instanz in die 'Demo' eingefügt.Weitere Einzelheiten finden Sie unter
Mockito-Zuhause
@Spion
@Spotten
quelle
Mockito cannot mock/spy following: - final classes - anonymous classes - primitive types
new RealServiceImpl()
,@Spy private SomeService service;
erzeugt ein reales Objekt Standardkonstruktors verwenden , bevor sowieso auf sie Spionage.Wenn Sie zusätzlich zu der Antwort @Dev Blanked eine vorhandene Bean verwenden möchten, die von Spring erstellt wurde, kann der Code wie folgt geändert werden:
Auf diese Weise müssen Sie Ihren Code nicht ändern (einen weiteren Konstruktor hinzufügen), damit die Tests funktionieren.
quelle
Autowired
Felder aus den Abhängigkeiten korrekt erstellt wurden.Mockito ist kein DI-Framework, und selbst DI-Frameworks fördern Konstruktorinjektionen gegenüber Feldinjektionen.
Sie deklarieren also einfach einen Konstruktor, um Abhängigkeiten der zu testenden Klasse festzulegen:
Die Verwendung von Mockito
spy
für den allgemeinen Fall ist ein schrecklicher Rat. Es macht die Testklasse spröde, nicht gerade und fehleranfällig: Was wird wirklich verspottet? Was ist wirklich getestet?@InjectMocks
und@Spy
schadet auch dem Gesamtdesign, da es aufgeblähte Klassen und gemischte Verantwortlichkeiten in den Klassen fördert.Bitte lesen Sie das
spy()
Javadoc, bevor Sie es blind verwenden (die Betonung liegt nicht bei mir):quelle
Im Frühjahr gibt es ein spezielles Dienstprogramm
ReflectionTestUtils
für diesen Zweck. Nehmen Sie die spezifische Instanz und injizieren Sie sie ins Feld.quelle
Ich weiß, dass dies eine alte Frage ist, aber wir hatten das gleiche Problem, als wir versuchten, Strings zu injizieren. Deshalb haben wir eine JUnit5 / Mockito-Erweiterung erfunden, die genau das tut, was Sie wollen: https://github.com/exabrial/mockito-object-injection
BEARBEITEN:
quelle