Давайте выясним, ладно?!
import org.mockito.Mockito;
class Scratch {
public final static String STATIC_CONST = "static const";
private final String JUST_CONST = "private const";
protected String protectedField = "protected field";
String packageProtectedField = null;
public static void main(String[] args) {
Scratch mocked = Mockito.mock(Scratch.class);
System.out.println("static = " + mocked.STATIC_CONST);
System.out.println("const = " + mocked.JUST_CONST);
System.out.println("protected = " + mocked.protectedField);
System.out.println("package = " + mocked.packageProtectedField);
mocked.packageProtectedField = "but now";
System.out.println("updated = " + mocked.packageProtectedField);
}
}
Вышеуказанные отпечатки:
static = static const
const = private const
protected = null
package = null
updated =, но сейчас
Некоторые мысли:
Очевидно, static const
на самом деле то, что вы ожидаете (я использовал mocked.STATIC_CONST
, чтобы получить значение, но, эй, оно статическое, поэтому значение берется не из mocked
, а из определения класса Scratch в любом случае).
AНемного удивительно, по крайней мере для меня то, что назначение полей для макета объекта действительно работает.Но обратите внимание: назначения в исходном классе действительны только для этого поля final
.Другими словами: Mockito делает это правильно, но не для не финальных полей.
Еще более удивительно, что в макет можно хранить значения ...
Но, честно говоря, ничего из этого не имеет значения.Видите ли, в звуковом дизайне все ваши изменяемые поля должны быть private в самом первом месте.Это изменчивое состояние представляет собой абсолютное ядро ваших объектов. Нет внешний код должен когда-либо иметь дело с ними!Другими словами: в идеале, даже ваши тесты не заботятся о внутреннем состоянии ваших объектов (в очень редких ситуациях может иметь смысл иметь защищенный от пакетов метод getter для доступа к внутреннему состоянию для простоты проверки, но это должно бытьредкое исключение).
Кроме того: когда вы издеваетесь над объектом, вы абсолютно никоим образом не должны иметь дело с полями этой насмешки.Вы видите: все методы на этом макете ... они не имеют ничего общего с исходным исходным кодом в вашем классе.Это всего лишь пустые оболочки, которые вы можете настроить / проверить с помощью соответствующих методов Mockito.Пусть это впитывается: фактическое содержание полей в макетируемом объекте не может иметь значения: потому что методы, которые обычно имеют дело с этими полями ... "не существует"!
Итак, короткая история:как показано, макетированные объекты могут нести состояние.Но, как объяснено: вы должны полностью игнорировать этот аспект.Единственный правильный способ использовать макеты - это указывать / проверять вызовы методов для них.
Наконец: я ожидаю, что EasyMock, PowerMock (ito) ведут себя аналогичным образом.С другой стороны, я бы тоже не удивился, когда другие насмешливые фреймворки на самом деле ведут себя немного иначе.Я тестировал только с Mockito, потому что, imho, в 2018 году, Mockito - это единственная среда разработки, которую следует использовать при написании модульных тестов для JVM.