1 /* 2 * Copyright (c) 2007 Mockito contributors 3 * This program is made available under the terms of the MIT License. 4 */ 5 package org.mockito.internal.stubbing.answers; 6 7 import java.io.Serializable; 8 import java.lang.reflect.Modifier; 9 import org.mockito.invocation.InvocationOnMock; 10 import org.mockito.stubbing.Answer; 11 import org.mockito.stubbing.ValidableAnswer; 12 13 import static org.mockito.Answers.RETURNS_DEFAULTS; 14 import static org.mockito.internal.exceptions.Reporter.cannotCallAbstractRealMethod; 15 16 /** 17 * Optional Answer that adds partial mocking support 18 * <p> 19 * {@link Answer} can be used to define the return values of unstubbed invocations. 20 * <p> 21 * This implementation can be helpful when working with legacy code. 22 * When this implementation is used, unstubbed methods will delegate to the real implementation. 23 * This is a way to create a partial mock object that calls real methods by default. 24 * <p> 25 * As usual you are going to read <b>the partial mock warning</b>: 26 * Object oriented programming is more less tackling complexity by dividing the complexity into separate, specific, SRPy objects. 27 * How does partial mock fit into this paradigm? Well, it just doesn't... 28 * Partial mock usually means that the complexity has been moved to a different method on the same object. 29 * In most cases, this is not the way you want to design your application. 30 * <p> 31 * However, there are rare cases when partial mocks come handy: 32 * dealing with code you cannot change easily (3rd party interfaces, interim refactoring of legacy code etc.) 33 * However, I wouldn't use partial mocks for new, test-driven & well-designed code. 34 * <p> 35 */ 36 public class CallsRealMethods implements Answer<Object>, ValidableAnswer, Serializable { 37 private static final long serialVersionUID = 9057165148930624087L; 38 answer(InvocationOnMock invocation)39 public Object answer(InvocationOnMock invocation) throws Throwable { 40 if (Modifier.isAbstract(invocation.getMethod().getModifiers())) { 41 return RETURNS_DEFAULTS.answer(invocation); 42 } 43 return invocation.callRealMethod(); 44 } 45 46 @Override validateFor(InvocationOnMock invocation)47 public void validateFor(InvocationOnMock invocation) { 48 if (new InvocationInfo(invocation).isAbstract()) { 49 throw cannotCallAbstractRealMethod(); 50 } 51 } 52 } 53