Tutorial | Source | Issues | Release notes |
---|
@Mock
method which matches all methods of
the same name in the faked class, regardless of their parameters. This "match-by-name-only" fake method must have only an
Invocation
parameter.
Deencapsulation
class (which now only contains getField
methods).
@Mocked
, @Capturing
, and
@Injectable
) can no longer be used on Java SE collection and map interfaces, for two reasons:
1) on Java 8+, such interfaces include default methods, which do get mocked, easily causing unexpected results in tests;
2) mocking of said interfaces (and more generally, of all value-oriented types which basically encapsulate state without complex
behavior in methods) is a well known bad practice.@Injectable
collection/map field which is meant to be injected
into a @Tested
object, the test should be changed to use @Tested
as
well on the collection/map field, with its declaration positioned before the target @Tested
field.
Deencapsulation.setField
methods, which were deprecated in version 1.44.@Mock
methods that target a private
method or constructor.
The intent is to disallow such mock methods in a future version.
withArgThat(Matcher)
method, which was deprecated in version 1.43.Deencapsulation.setField
methods, in favor of @Tested
and
@Injectable
.
withArgThat(Matcher)
method (available in the Expectations
and
Verifications
classes), in favor of argument capturing (the withCapture(...)
methods) and the
with(Delegate)
method.
-javaagent
" JVM initialization parameter.
See Running tests with JMockit.
@Tested
as a meta-annotation in JUnit 4/5 test method parameters.
maxInstances
attribute of the @Capturing
annotation, which was deprecated in version 1.39.
FullVerificationsInOrder
class, which was deprecated in version 1.39.
maxInstances
attribute of the
@Capturing
annotation.
This attribute provides a feature which is probably never used, and if used makes for difficult to understand
tests; existing tests using it (if any) should either be removed or rewritten.
FullVerificationsInOrder
class.
Existing tests using it, if any, can replace the one expectation block with two, a
VerificationsInOrder
block containing the verified expectations, followed by an empty
FullVerifications
block.
MockUp#getMockInstance()
method, which was deprecated in version 1.37.
unverifiedInvocations()
and verifiedInvocations(...)
methods, which were deprecated in version 1.38.
Expectations
and Verifications
, for simplicity and improved
performance.
unverifiedInvocations()
and verifiedInvocations(...)
methods from the VerificationsInOrder
and FullVerifications
classes.
These methods support "partially ordered verification", a feature which is probably never used, and if used make
for difficult to understand tests; existing tests using them (if any) should either be removed or rewritten.
getMockInstance()
method from the MockUp
class.
Normally, this method is only used to obtain an instance of a faked interface.
For faked classes, it has no practical use.
Instead of using a mock-up for an interface type, it's recommended to create a minimal implementation class, or
to use an existing implementation.
See deprecation comments in the API documentation.
StrictExpectations
class, deprecated in version 1.35.
invoke
" and "newInstance
" methods from the
Deencapsulation
class, deprecated in version 1.35.
MockUp(T)
" constructor from the MockUp
class,
deprecated in version 1.35.
StrictExpectations
class.
Existing tests should instead use Expectations
, possibly adding a
"new FullVerifications() {}
" block at the end, if detecting unrecorded invocations is still desired.
invoke
" and "newInstance
" methods from the
Deencapsulation
class.
These are simple Reflection-backed convenience methods, which are no longer useful in the overall context of
JMockit APIs.
MockUp(T)
constructor.
(Use of this constructor causes the given instance of type T
to be the only one affected by the
fake implementations.)
This feature was never intended for the faking API in the first place, it's been rarely used, and has no
demonstrable use cases; existing tests that happen to use it should instead use real (non-faked) instances.
mockups
" system property to "fakes
".
@Capturing
performance.@Tested
:
a) all available @Injectable
's having subtypes of target fields and/or
constructor parameters are now considered for injection;
b) previous @Tested
values from annotated fields or parameters are now eligible
for injection into @Tested
objects, even without
fullyInitialized = true
.
@Tested
:
a) field extraction from a tested object into other @Tested
fields
declared after it now works for any field in the source object (including primitive types, arrays, and
collections), not only for injected dependencies;
b) the annotation can now be used on test method parameters;
c) new value
attribute.
Expectations(Integer, Object...)
,
StrictExpectations(Integer, Object...)
, Verifications(int)
,
FullVerifications(int)
, FullVerifications(Integer, Object...)
,
VerificationsInOrder(int)
, FullVerificationsInOrder(int)
, and
FullVerificationsInOrder(Integer, Object...)
constructors which take a
"numberOfIterations
" parameter, which were deprecated in version 1.30.
onInstance(mock)
method (deprecated in version 1.29 - see below) from
the Expectations
and Verifications
classes.
returns(Object)
method (deprecated in version 1.29 - see below) from
the Expectations
class.
Expectations(Integer, Object...)
,
StrictExpectations(Integer, Object...)
, Verifications(int)
,
FullVerifications(int)
, FullVerifications(Integer, Object...)
,
VerificationsInOrder(int)
, FullVerificationsInOrder(int)
, and
FullVerificationsInOrder(Integer, Object...)
constructors which take a
"numberOfIterations
" parameter.
Iterated recording of expectations is a rarely used feature, and indicative of poor testing practices (when used).
Existing tests which happen to use it should be reviewed or eliminated.
invocations
", "minInvocations
", and
"maxInvocations
" attributes from the @Mock
annotation, which were
deprecated in version 1.26.
onInstance(mock)
method from classes
Expectations
and Verifications
.
Existing calls should be removed (leaving just "mock
").
Tests that need to match invocations to specific mocked instances should instead make use of
@Injectable
or of multiple @Mocked
fields/parameters of the same type.
Expectations#returns(Object, Object...)
" method to
just "returns(Object)
", and deprecated it in favor of using the "result
" field
(for a single return value) or the newly added method "returns(Object, Object, Object...)
" (for a
sequence of multiple return values).
tearDown()
" method (deprecated in version 1.26) from the
MockUp
class.
$
" field (deprecated in version 1.26) from
Expectations
and Verifications
.
MockUp#tearDown()
method.
Mock-up tear down is automatic, so explicit calls to this method are either made by mistake, or by misuse in
tests that should be broken down into two or more test methods.
@Mock
annotation
(invocations
, minInvocations
, and maxInvocations
).
Use of said attributes is indicative of a behavior-oriented test that would be better written with the
Expectations API.
$
" special field that can be used when recording or verifying
expectations to provide a custom error message.
This feature is of dubious value and probably never used.
jmockit.properties
configuration file.
5.0.0-M1
release of July 7).
Differently from JUnit 4 support (and like TestNG support), the relative order in the classpath between JMockit
and JUnit 5 dependencies is irrelevant - also, no configuration code needs to be added to a JUnit 5 test class
in order to use the JMockit API, it just works.
NonStrictExpectations
class, which was deprecated in
version 1.23.
getMinInvocations()
and getMaxInvocations()
of
the Invocation
class, which were deprecated in version 1.24.
jmockit-coverage.jar
or the equivalent Maven artifact).
It is now embedded in jmockit-1.x.jar
, but only gets activated in a test run when at least one of the
following system properties is set: coverage-output
, coverage-metrics
, or
coverage-classes
.
getMinInvocations()
and getMaxInvocations()
of
class mockit.Invocation
.
private
methods/constructors when using the
Expectations API, to prevent misuse.
If still needed, they can be mocked or stubbed out with the application of a
MockUp<T>
.
NonStrictExpectations
class.
Existing tests should use Expectations
instead.
@Tested(fullyInitialized = true)
.
See issue #224.
@Tested(fullyInitialized = true)
.
value
" attribute of
@Mocked
, which was deprecated in release 1.17.
Existing tests using "@Mocked({"someMethod", "anotherMethod", ...})
" should simply omit the
attribute, or use partial mocking as applied with new Expectations(objToPartiallyMock) { ... }
, or
apply a MockUp<T>
class.
cascading
" attribute of
@Mocked
, which had been previously deprecated.
Existing tests using "@Mocked(cascading = false)
" should simply omit the attribute, or record an
expectation with "result = null"
for the cascaded method in question.
value
" attribute of
@Mocked
, which is used for "static" partial mocking.
Existing uses should be replaced with "dynamic" partial mocking, by passing the instance or class to partially
mock in a call to the Expectations(Object...)
constructor, or by applying a
MockUp<T>
class.
cascading
" attribute of
@Mocked
.
Existing tests using "@Mocked(cascading = false)
" should simply omit the attribute, or record an
expectation with "result = null"
for the cascaded method in question.
@Cascading
annotation, which was deprecated in
version 1.12.
Since that version, cascading is active by default on all mocked types, although it can be disabled by specifying
@Mocked
(cascading = false)
.
@Autowired
and
@Value
annotations of the Spring DI framework.
In addition, all annotated dependencies (using @Inject
,
@Resource
, or @Autowired
) in a
@Tested
object will now require a corresponding
@Injectable
; this is done for the following reasons: a) consistency with DI
frameworks; b) preventing NullPointerExceptions
's from uninitialized dependencies;
c) encouraging cohesive classes with few dependencies; and d) encouraging the creation of at least one test for
each injected dependency.
See issue #103.
StrictExpectations
as a sibling to
NonStrictExpectations
.
The shared base class, Expectations
, no longer records strict expectations when
used on its own; instead, its expectations are just like the ones from
NonStrictExpectations
, but with a default minimum invocation count of 1
(one), as if recorded with a "minTimes = 1
" constraint.
This change in API semantics is meant to bring the following benefits:
Expectations
class.
New users usually don't expect "new Expectations() {{ ... }}
" blocks to be strict, but they
tend to expect such recorded expectations to require at least one matching invocation from the code
under test.
StrictExpectations
subclass.
NonStrictExpectations
subclass will become much less
common.
Essentially, this subclass is now mostly useful in test setup methods only
(@Before
, @BeforeMethod
), since such
shared expectations will often not be used by all tests in the test class (hence they should be
"minTimes = 0
" by default).
NonStrictExpectations
as before, but it's recommended
to replace such uses with Expectations
, when they occur in test methods; when they
occur in test setup methods, however, use of the non-strict subclass should be kept, unless one prefers
to add an explicit "minTimes = 0
" constraint to each recorded expectation.
Tests that do want to record strict expectations, however, should change "new Expectations...
" blocks
to the equivalent "new StrictExpectations...
" form.
@Cascading
annotation.
Mocking now cascades by default on any mocked type, unless specified otherwise through the new
boolean
cascading
attribute of @Mocked
(which is true
by default).null
to be returned, or if the return type of
some method must not be mocked; in such cases, the test will have to be changed to either record a
explicit null
return, or to deactivate cascading.
@Tested
and @Mocked
can now be
applied together to the same field.
This causes the tested object to become partially mocked, as if it had been passed in a call to the
NonStrictExpectations(Object...)
constructor.
@Tested
and @Injectable
can also
be applied together to the same field.
Besides causing the tested object to be partially mocked, it can also get injected into another
@Tested
field, if one exists having a suitable dependency.
This ability can be used in integration tests where a top-level tested object has one or more second-level
tested objects as dependencies.
@Tested(fullyInitialized = true)
fields, by properly handling injected fields of
type javax.inject.Provider<T>
, and servlet classes (which extend
javax.servlet.GenericServlet
, whose init()
and destroy()
methods get automatically called).
coverage-maxCallPoints
", to allow overriding the default value
(10 call points per covered line of source code, in the HTML report).
with(Object)
and with(T, Object)
from base class
mockit.Invocations
(shared by Expectations
and
Verifications
), which were deprecated in release 1.9.with(Delegate)
or withArgThat(org.hamcrest.Matcher)
.
native
methods cannot be redefined and therefore are never mocked;
2) JMockit initialization without the use of "-javaagent" only works if running in debug mode;
3) the java.lang.System
class cannot be reliably mocked.
Invocation#setMinInvocations(int)
and
Invocation#setMaxInvocations(int)
, which were deprecated in release 1.9.
MockUp(Object)
constructor and improved
MockUp#getMockInstance()
method to support mock-up behavior for exclusive instances of mocked
classes.
See API documentation for details.
fullyInitialized
" attribute to the
@Tested
annotation, to recursively instantiate and inject all fields from the
root tested object down to its deepest dependencies.
Types with no @Injectable
instances declared in the test class are resolved to
their real, unmocked, implementations.
This new ability is intended for integration tests, rather than unit tests.
TestCase
class.
Existing tests using the JUnit 3.8 API should be converted to the JUnit 4 API, if they happen to use JMockit.
withArgThat(org.hamcrest.Matcher)
to the Invocations
base class, while
deprecating with(Object)
and with(T, Object)
(which already support Hamcrest by
accepting Matcher
objects).
Invocations#with(Object)
and
Invocations#with(T, Object)
.
Existing calls to these methods should be replaced with calls to either with(Delegate)
or
withArgThat(Matcher)
.
setMinInvocations(int)
and setMaxInvocations(int)
methods of class Invocation
.
Such methods are unlikely to be useful in real tests, and will be removed from the API in the next release,
without any direct replacement.
merge
" is now called "serial-append
", for
clarity.
coverage-classes
and coverage-metrics
now also accept the value "none
" (which previously was only
accepted by the coverage-output
property).
Object $advice(Invocation)
" mock method.
groupId
" for Maven artifacts has changed from "com.googlecode.jmockit
" to
"org.jmockit
".
Therefore, existing pom.xml
files containing JMockit dependencies should be changed accordingly, for
JMockit 1.8+ and JMockit Coverage 0.999.27+.
@UsingMocksAndStubs
annotation,
which was deprecated in release 1.7.
mockit.integration.logging
and its classes.
They were deprecated in release 1.7.
MockUp<T>
class now has the ability to extend
mocking to the classes implementing a specified interface, or to the subclasses of a specified base class.
This is similar to what @Capturing
provides in the Expectations API.
List<T> withCapture(T)
method was added to the
Verifications
class.
When called with a constructor invocation, it allows new instances of a mocked class that were created by code
under test with a matching constructor call to be captured to a list for verification.
@Mocked
, @Injectable
,
@Cascading
, and/or @Capturing
.
(Recent releases were already writing a warning to console output when a non-annotated mock field or mock
parameter was found.)
forEachInvocation
field, which was deprecated in
release 1.6.
Existing tests using it should instead take advantage of the withCapture()
and
withCapture(List)
methods, or convert the handler object to a Delegate
object assigned to the result
field (in the case of a recorded expectation).
@UsingMocksAndStubs
annotation.
Programmatic application of mock-ups at the test class or test suite levels should be done in
@BeforeClass
methods instead (JUnit or TestNG).
mockit.integration.logging
package
(Log4jMocks
and others).
If they happen to be used in existing test classes, consider copying them into the client project or into an
standalone jar file; future versions of JMockit will no longer include them.
jmockit-stubs
system property.
coverage-classes
" system property is set to
"loaded
".
This is useful when running a set of tests targeting only a small part of the codebase, so that the generated
HTML report only includes the classes of interest.
@NonStrict
annotation, which was deprecated in
release 1.5.
Tests still using it should instead use NonStrictExpectations
blocks.
methods
" and "inverse
" attributes of the
@Mocked
annotation, which were deprecated in release 1.5.
Tests still using "@Mocked(methods = {...})
should instead use the default "value
"
attribute.
Expectations#returns(Object)
method, in favor of using the
result
field instead.
The Expectations
class still contains the returns(Object, Object...)
method, however.
Therefore, existing "returns(<a value>);
" calls will automatically become calls to the "varargs"
method, provided test classes are recompiled; if they are not, a NoSuchMethodError
will
occur whenever the removed returns(Object)
method is called.
Invocations
class
(the base for Expectations
and Verifications
), in favor of
using the static
methods of identical signatures in the Deencapsulation
class.
This change in the API will not require any changes to test code, except that test classes using these methods
should now include the following "static import":
import static mockit.Deencapsulation.*;
Expectations
and Verifications
blocks (anyInt
, result
, etc.) have been changed from static
to
instance fields.
This change should require nothing more than a recompilation of existing test classes.
forEachInvocation
field.
Existing tests using it should instead take advantage of the new withCapture()
and
withCapture(List)
argument-capturing methods, which provide better syntax.
reentrant
attribute of the @Mock
annotation, which was deprecated in release 1.1.
Existing mock methods marked as reentrant should instead have an Invocation
parameter.
it
" field.
Mock classes which have an it
field should instead use the
Invocation#getInvokedInstance()
method in order to obtain the invoked instance of the mocked class.
Mockit.setUpMocks(Object...)
and
Mockit.setUpMock(Object)
methods, which were deprecated in release 1.1.
These were the last methods in the Mockit
class, so it was removed as well.
Existing tests still using any of these methods should replace them as described in the corresponding API
deprecation comments.
@MockClass
annotation, which was deprecated in
release 1.1.
Existing mock classes should instead extend the MockUp<T>
base class.
@NonStrict
annotation.
Existing tests using it should instead use @Mocked
, while converting
"new Expectations() { ... }
" blocks to
"new NonStrictExpectations() { ... }
" blocks.
Alternatively, if strict recording is desired for some other mocked type, the expectations recorded on the
@NonStrict
mocked type can be moved to a separate non-strict expectations block.
methods
" and "inverse
" attributes of
@Mocked
.
Existing uses like @Mocked
(methods = {"method1", "method2"})
should
simply be rewritten as @Mocked
({"method1", "method2"})
(using the
default value
attribute).
As for the inverse
attribute, specify what is to be mocked instead.
jmockit-coverage-metrics=line"
can now be written without the
"jmockit-"
prefix as well.
Mockit.stubOut(...)
and Mockit.stubOutClass(...)
methods,
which were deprecated in release 1.1.
To replace existing calls, use the MockUp
class.
classNames
and inverse
attributes of the
@Capturing
annotation, which were deprecated in release 1.3.
realClassName
attribute of the @Mocked
annotation, which was deprecated in release 1.3.
Mockit.setUpMock(Class realClass, Object mock)
and
Mockit.setUpMock(Class realClass, Class mockClass)
, which were deprecated in release 1.1.
The MockUp
class should be used to replace existing calls to these methods.
@Input
annotation, which had been deprecated in
release 1.2.
Existing tests with @Input
fields will have to record equivalent expectations
instead.
Expectations#notStrict()
method, which had been deprecated in release
1.2.
Existing tests that call this method will have to use @NonStrict
or
NonStrictExpectations
instead, with the associated verification block.
Mockit.setUpMock(String realClassName, Object mock)
and
Mockit.setUpMock(String realClassName, Class> mockClass)
methods, which were deprecated in release
1.1.
To replace existing calls, use Reflection to load the non-accessible real class, then pass it in a call to
MockUp(Class)
.
Mockit.stubOutClass(String realClassName, String... filters)
and
Mockit.stubOutClass(String realClassName, boolean inverse, String... filters)
methods, which were
deprecated in release 1.1.
To replace existing calls, use Reflection to load the non-accessible real class, then pass it in a call to
MockUp(Class)
; methods to be stubbed out should have empty @Mock
methods in the mock-up class.
Mockit.setUpMocksAndStubs(Class... mockAndRealClasses)
method, which
was deprecated in release 1.1.
Use @UsingMocksAndStubs
on the test class instead.
Mockit.setUpStartupMocks(Object... mockClassesOrInstances)
method, which
was deprecated in release 1.1.
Set the jmockit-mocks
system property instead.
classNames
and inverse
attributes of the @Capturing
annotation, and the
realClassName
attribute of the @Mocked
annotation.
These annotation attributes are rarely useful and not refactoring-friendly; they are scheduled to be removed in a
future release.
jmockit-coverage-maxConditions
system property, to limit the maximum
complexity of methods for the path coverage metric.
The default value for this property is 10 (ten).
See issue 300.
Instantiation
enum, which had been deprecated in release
1.1.MockClass#instantiation
annotation attribute will
need to be converted to MockUp<T>
subclasses.
In the case of "instantiation = PerMockSetup
", simply convert the mock class to a
mock-up class, which always uses a single instance per setup.
The "instantiation = PerMockedInstance
" functionality is no longer available, since
it was rarely used and can be emulated with a Map
in a single mock-up class instance, for any state
associated to individual mocked instances.
Mockit.tearDownMocks()
and
Mockit.tearDownMocks(Class>...)
methods, which were deprecated in release 1.1.
MockUp#tearDown()
.
The first choice (simply removing existing calls) should be applicable in most or all cases, since JMockit
automatically tears down all mock classes applied on a given context, when said context (the test method/class/
suite or a test preceded by a "before" method) is exited.
If explicit tear down really is needed, then the MockUp
class and its
tearDown()
method will have to be used instead.
Mockit.newEmptyProxy(...)
methods, deprecated in
release 1.1.
Use "new MockUp<E>(){}.getMockInstance()
" instead.
@Input
annotation.
Few, if any, users seem to have ever used this small part of the mocking API.
Its use was entirely optional, since what it does can always be achieved with the
result
field; it was merely meant as a more succinct alternative in simple scenarios, where a given
mocked type would have a single mocked method which needed to return a value of a certain type, or throw a
certain checked exception.
Expectations#notStrict()
method.
This is a rarely used method, which can always be replaced by recording non-strict expectations and adding
verification blocks.
result
" field now can perform additional type conversions,
including primitive widening conversions such as from char
to int
.
Also supported are primitive narrowing conversions, for example from int
to
byte
.
See issue 285.
jmockit.jar
or jmockit-coverage.jar
in
the classpath.
Instead, the JVM should be launched with the "-javaagent:<proper path>jmockit-coverage.jar
"
initialization parameter.
@MockClass
annotation, the Instantiation
enum, the
reentrant
attribute in the @Mock
annotation, and all methods in the
Mockit
class.
See the corresponding deprecation comments in API documentation for ways to replace existing uses of these API
elements.Mockit.tearDownMocks(...)
" methods, the tearDown()
method was
added to the MockUp
class.
IsolatedClassLoader
(which gets used when certain Surefire configuration
parameters such as "<useSystemClassLoader>false</useSystemClassLoader>
" are specified).
Fixes issue 247.
result
field, but the return type of the recorded method is an array, collection, or iterator.
In these cases, a suitable container object is created with that single value.
aLocalVar = withCapture()
" expressions
will now consider the type of the local variable into which the argument is captured when looking for matching
invocations. This is useful for parameters of reference types, when the actual arguments received during replay
are of a subtype; such arguments can be captured by using a capturing variable of that subtype.
unverifiedInvocations()
method to
FullVerifications
, to allow a test to discard unverified invocations occurring in an
early preparation phase, while allowing later invocations to be verified as needed.
This is similar to "reset(mock)
" methods provided in other mocking APIs.
Fixes issue 257.
result
field. When recording a constructor expectation, simply assign an instance of the mocked class to have
it "take the place" of any new instances that get later created with a matching constructor invocation.
The replacement instance can be obtained from a mock field/parameter, or be a real instance when applying
dynamic mocking through a "new Expectations(AClassToBeMocked.class)
" or
"new NonStrictExpectations(AClassToBeMocked.class)
" call.
This solves issue 210.
@Tested
can now be applied to abstract
classes. A subclass is created with all abstract methods automatically mocked, so that expectations can be
recorded and verified on them.
result
field,
when recording return values for a method whose return type is a collection, iterator, or map.
This provides a convenient way to specify static values for such methods, since it's easier to fill out an array
than a List
or Map
.
Additionally, automatic conversions from strings to StringBuilder
,
InputStream
, ByteArrayInputStream
,
Reader
, StringReader
, and
java.nio.CharBuffer
are now also supported.
@Tested
and
@Injectable
, use of the
standard Java API for dependency
injection (JSR-330) in the tested class is now explicitly supported.
Any fields and/or constructors annotated with javax.inject.Inject
will be the only ones
considered when performing injection of @Injectable
s into the
@Tested
object.
Also, the javax.inject.Provider<T>
interface is properly supported for
@Injectable
s of type "T
".
withCapture()
and
withCapture(List)
methods
to the Verifications
base class (the second one also available in
Expectations
blocks).
These two new methods allow for the easy and succinct capture of invocation arguments for recorded/verified
expectations.
For details and an example, see the API documentation.
jmockit-coverage-check
" is now supported, enabling checks for minimum coverage
percentages to be performed.
For details, see the relevant section in the JMockit Tutorial.
This solves issue 235.
getInvokedArguments()
method to the Invocation
class.
Together with a related enhancement which allows "forEachInvocation
" handler methods to only have the
Invocation
parameter, this further enables the creation of reusable delegate and handler
objects for use with the Delegate
interface and the result
and
forEachInvocation
fields.
@Tested
class to have
an accessible constructor.
This helps in the case where a public class is only meant to be instantiated by a DI container, allowing it to
have non-public constructors only.
@Mock
methods now also apply to the super-classes of
the specified class to be mocked, when the latter doesn't define a matching method.
This avoids the need to set up two or more separate mock classes when the methods to be method are defined in
multiple levels of a class hierarchy.
Object
.
This is still not supported when the mocked type is a generic interface, however.
See issue 229.
Delegate
method invoked another mocked
method/constructor, it would cause the real implementation of that method/constructor to be executed; now such an
invocation gets the mocked behavior, which is what a user would intuitively expect.
jmockit-coverage-{htmlbasic|htmlfull|serial|merge}.jar
files from the distribution zip file, and dropped support for output selection through the addition of such files
to the runtime classpath.
This was done because few users relied on this feature, and it wasn't applicable to Maven runs; also, some users
add every jar file to the classpath by default.
Therefore, the only way now to select the desired coverage output is by setting the
jmockit-coverage-output
system property.
-javaagent
" parameter when using JDK 1.6+ on this
OS.)
jmockit-mockParameters=annotated
" system property, to be set when
automatic (non-annotated) mock parameters in test methods would conflict with some other JUnit/TestNG integration.
When set, only those test method parameters that are explicitly annotated with
@Mocked
, @NonStrict
,
@Cascading
, @Capturing
, and/or
@Injectable
are considered to be mock parameters.
See issue 232.
proceed()
method to
mockit.Invocation
, to be used in @Mock
or delegate
methods.
WEB-INF/classes
.)
-javaagent:<proper path>/jmockit-coverage.jar
";
there is no need to add any jar to any classpath.
CATALINA_OPTS
" environment
variable with a value like
"-javaagent:/jmockit/jmockit-coverage.jar -Djmockit-coverage-outputDir=/dir/for/coverage/report
"
(as shown here, "jmockit-coverage-" system properties can optionally be set as well).
java.lang.AssertionError
, JMockit will
now throw a custom java.lang.Error
subclass -
see issue 213.
-javaagent:jmockit.jar
, among other reasons.
jmockit-hibernate3emul.jar
), Incremental Test Runner
(jmockit-incremental.jar
), and Multicore Test Runner (jmockit-multicore.jar
).
The development of these tools will be eventually completed, as part of the
JMockit 2 project.
Mocked#capture
" and "Capturing#baseType
" annotation
attributes, which were deprecated in the previous release.
Existing tests still using them will have to be changed as described in the deprecation comments.
value
" attribute to
@Injectable
, to enable the injection of primitive values and strings into
"@Tested
" objects from mock parameters (previously, it was only possible
with mock fields).
@Tested
objects:
a) constructor injection now selects among multiple constructors when more than one can be satisfied by the
available @Injectable
's, by choosing the one with the most parameters;
b) for constructor injection, the names of eligible constructors are now matched against the names of
the injectable fields and test method parameters having the same type as the constructor parameter;
c) the names of injectable parameters, as declared in test methods, are considered when searching for matching
constructor parameters and instance fields in the tested class;
d) field injection is now always performed, even if constructor injection was not (ie, the tested class
was explicitly instantiated).
forEachInvocation
" validation methods can now return
boolean
to indicate whether the received invocation arguments are valid (true
) or not
(false
).
In the last case, a descriptive error message is generated from the validation method name and the actual argument
values.
forEachInvocation
class whose method
happens to return a value to be returned from the associated recorded expectation.
Instead, an identical Delegate
object should be assigned to the
result
field.
onInstance(mock)
in verification blocks didn't work when
multiple instances of the mocked type were involved; c) dynamically mocked constructors could not invoke private
methods.
capture
" and "baseType
" annotation attributes, used in
the @Mocked
and @Capturing
annotations,
respectively.
Existing uses of "@Mocked(capture = n)
" should be replaced with
"@Capturing
" or "@Capturing(maxInstances = n)
", as needed.
Applications of "@Capturing(baseType = BaseType.class)
" to a test class
should be replaced with "@Capturing BaseType xyz;
" mock fields.
jmockit-mocks
" and
"jmockit-stubs
" system properties, respectively.
These properties can also be defined in custom jmockit.properties
files, which may appear in the
classpath in any number; if more than one such file defines one of those properties, the values are added
together.
mockit.external.hamcrest
) were
replaced with new code, for reasons of simplicity and efficiency.
At the same time, the with(Delegate<T>)
method was improved to return a non-null
default value when T
is a primitive wrapper type.
mockit.external.asm4
), which began a
few releases ago.
"...IntegrationTest"
so they can be executed separately.
In addition to that, the integration tests can be executed in two different "modes": as pure integration tests
accessing an external Web site, or with faked network access simulating the responses from the Web site.
VerifyError
that could occur before;
2) break
statements inside loops are now handled properly (there is still an issue with
continue
statements, though);
3) certain simple constructs such as return !b; // (b == a boolean)
caused an unexpected path to be
detected and measured, which is now disregarded.
From this version on, JMockit artifacts are deployed to the Maven Central
repository, under a different "<groupId>
" of "com.googlecode.jmockit
".
Therefore, Maven users should change JMockit dependencies in their pom.xml
files accordingly.
Expectations(Object...)
and
NonStrictExpectations(Object...)
constructors so that the Class
literals
and/or instances passed in are (dynamically) mocked in a more intuitive way:
a) for a given Class
, the super-classes are now also considered for mocking, rather than
only the specified class;
b) for a given object, only method invocations made on the specified instance will be able to match
expectations (invocations on other instances will execute the real implementation).
mockit.integration.testng.Initializer
listener.
When running on Java 6+ with TestNG 6.2+, the listener will be automatically registered.
(The use of -javaagent:jmockit.jar
is still required with Java 5, though.)
@Cascading
mock fields declared in test
classes, where cascaded instances created during the execution of a test would remain in effect for a different
test class, or would not be recreated for a second test in the same test class.
See issues 182 and
185.
@Tested
fields:
1) non-public classes with a package-private constructor are now accepted as well;
2) @Injectable
fields of non-mockable types (primitives and arrays) are
now considered when injecting values into the tested object;
3) multiple parameters of the same type are now supported when doing constructor injection, by taking
values from matching injectable fields declared in the same relative order;
4) a varargs constructor parameter is now supported, taking the values of all injectable fields having
the same type.
@Input
fields:
1) multiple fields of the same type can be declared, allowing consecutive results to be
specified;
2) the new invocations = n
attribute can be used to specify a fixed number
of matching invocations for a given input field;
3) auto-instantiation of values can now be done with a non-public no-args constructor;
4) it now also works when combined with dynamic partial mocking.
mockit.Invocation
class can now be used as the type of
the first parameter in @Mock
methods (it was already supported in delegate and
validation methods).
See issue 16.
@Injectable
and @Tested
annotations.
throws
clause.
Each default result is specified through an instance field annotated with
@Input
.
See here for examples.
Expectations
or
Verifications
must have a name ending in "Expectations" or "Verifications",
respectively.
Any such classes in existing test suites will have to be renamed if needed to fit this new rule.
See issue 161.
verifiedInvocations(Verifications)
method to
the VerificationsInOrder
class.
With this, new scenarios involving partially ordered verification are now supported.
See issue 153.
endRecording()
method of the
Expectations
class.
This method was deprecated in the previous release. Existing tests still using it will have to be changed as
described in the deprecation comment.
mockit.integration.testng.Initializer
listener to be configured, as long as the "-javaagent:jmockit.jar
" JVM parameter is
specified. Otherwise, the listener is still needed.
ClassFormatError
would occur in classes instrumented by the
EMMA code coverage tool, when they were mocked with reentrant mock methods (Annotations API).
$init
"
(which already was the recommended way).
Therefore, any mock classes containing constructors annotated with @Mock
must be changed to use
void $init
methods instead.
endRecording()
method of the
Expectations
class.
Normally, this method would only be used in rare situations, and with local mock fields.
Any such tests should be changed to make use of mock parameters or mock fields of the test class instead.
toString()
methods on non-mocked arguments will always be called to provide a more useful/readable
message.
See issue 146.
@Tested
annotation for tested classes,
with support for constructor and field injection of @Injectable
mocks.
stubOutClassInitialization
attribute of the @Mocked
annotation is now
false
.
The jmockit-retainStaticInitializers
system property is no longer supported, given that in practice
it was only used to change the global default for that attribute to false
.
This change can break existing tests which happened to mock a class containing static initialization code, when
such code performed operations that could potentially fail in the test environment (such as connecting to a remote
database, for example).
In such a case, the @Mocked(stubOutClassInitialization = true)
annotation will have to be applied to
the appropriate mock field/parameter.
equals
,
hashCode
and toString
methods so they are always considered non-strict, even
when the recording is done on an otherwise strict mocked instance.
This allows such methods to be invoked freely while still having strict verification of expected/unexpected
invocations on a strict mock.
result
field and the returns(Object)
method (both
available in expectation blocks) now also accept arrays and Iterable
's containing values to
be returned by consecutive invocations (collections and iterators were already supported).
Mockit.tearDownMocks(...)
in an "after"/tearDown
method.
jmockit.properties
file.
(The default version of this file can be found inside jmockit.jar
.)
Several tools in the JMockit toolkit allow configuration through "jmockit-xyz" system properties, which previously
had to be defined with the "-D" JVM parameter (or the equivalent Ant/Maven XML code).
Now such properties can also be defined by adding a [jmockit-]xyz=some value
line in the custom
properties file, which should be added to the classpath before jmockit.jar
in order to
override it. The "jmockit-" prefix is optional when using the file, but will be added in the actual system
property so that tools can always look for "jmockit-xyz" properties.
equals
, hashCode
and toString
methods, so that they are mocked by default but still behave according to the standard
behavior inherited from java.lang.Object
.
See issue 130.
Although unlikely, this change can cause existing tests to break.
System.setProperties(Properties)
), or that expects only
String
instances to be stored in it.
See issues 123 and
See 129.
ArrayIndexOutOfBoundsException
when
mocking an interface containing static initializers.
See issue 127.
jmockit-multicore.jar
to the test execution classpath, before the
jar for JUnit. (The presence of jmockit.jar
is not required.)
From this version on, the Java.net Maven 2 repository is no longer used.
Project artifacts are now deployed here.
Therefore, Maven users should configure the new repository in their pom.xml
files.
ClassFormatError
would occur when dynamic mocking was used.
See issue 30.
@Injectable
with captured
mocked instances that are created inside tested code.
(Capturing of internal instances is enabled by annotating the mock field/parameter with
@Mocked(capture = n)
or @Capturing(maxInstances = n)
.)
This new behavior allows captured instances to "take the place" of the original injectable mock instance.
See issue 119.
minTimes
and maxTimes
fields. See issue 121.
mockit.Expectations
, mockit.Verifications
,
etc. to make them abstract
base classes, in order to avoid a content assist issue with Eclipse JDT.
See issue 122.
final
mock fields annotated as @NonStrict
or
@Injectable
, in particular the local ones (declared inside an expectation block).
@Injectable
annotation. It can be used together with @Mocked
or by
itself.
Previously, it was necessary to use dynamic partial mocking, often combined with calls to
onInstance(mock)
, in order to restrict mock/stub behavior to a single mocked instance.
This is important in cases where the behavior of other instances of the same mocked type could be inadvertently
affected. (For example, when mocking standard JRE classes which might be used internally by other JRE classes.)
See issue 113.
constructorArgsMethod
attribute from the @Mocked
annotation. This attribute was only rarely, if ever, actually useful. Existing tests that use it (hopefully no
more than a few, if any at all) can be modified to directly instantiate the mocked class with the desired
constructor.
@Cascading
mocked type
will now behave like @Injectable
ones, so that other instances of the same type are not inadvertently
affected. This also allows a regular (non-mocked) instance of the cascaded type to take the place of the default
mocked instance; simply assign the regular object to the result
field, after a call to the
appropriate non-void method.
java.lang.Object
class through the
Expectations API (the wait
and notify
methods, in particular, can now be mocked by
declaring a mock field/parameter of type Object
).
withEqual(arrayValue)
was required for this.
UnsatisfiedLinkError
could occur when mocking native methods from the JRE.
See issue 106.
stubOutClassInitialization
added to the
@Mocked
annotation, with support for a new jmockit-retainStaticInitializers
system
property which allows global configuration of the default behavior.
See issues 96 and
103.
JMockit
, JMockitTest
,
JMockitTestCase
, and JMockitTestNG
.
Note that instructions to replace these classes in existing tests are included as deprecation
comments in the corresponding API documentation of previous releases.
MockUp<T>
class,
which takes the class to be mocked as an argument, instead of obtaining it from the type
variable T
. Useful when the class to mock is unknown or non-accessible.
See issue 95.
Object
methods
(equals
, hashCode
, toString
, finalize
),
when they happened to have an abstract override in a subclass, would get mocked by default
when the concrete mock subclass was created; now, they get empty implementations unless
explicitly selected for mocking through mock filters.
ConcurrentModificationException
could occur.
Deencapsulation
or Expectations
) were not correctly
finding constructors with parameters for which a subtype argument could be passed (for
example, when passing an ArrayList
instance to a List
parameter).
See issue 77.
"No current invocation available"
).
java.net.URL
and java.io.FileInputStream
, unexpected test failures
could occur.
Mockit
class: redefineMethods(...)
(all four variations),
restoreOriginalDefinition(...)
, and restoreAllOriginalDefinitions()
.
If tests using these methods still exist, they will have to be changed according to the
instructions provided in the API documentation (from release 0.997, in which the methods were
deprecated).
JMockitTestCase
, JMockitTest
, JMockit
(custom runner
for JUnit 4.5+ tests), and JMockitTestNG
. All they ever did was make sure that
JMockit got initialized at start-up. This is best done through other means, which have been
available for some time.
@BeforeClass
JUnit method.
Delegate
objects: when there is only
one delegate method, it is allowed to have no parameters even if the corresponding mocked
method has them.
Mockit.assertExpectations()
;
throwsException(Exception)
and throwsError(Error)
from the
Expectations
class;
repeats(int)
, repeatsAtLeast(int)
, repeatsAtMost(int)
,
and repeats(int, int)
from the Invocations
base class;
and withAny()
also from the Invocations
class.
The Invocations#withAny(T)
method is no longer deprecated, as it is useful in
certain situations where a non-null argument value is needed.
Expectations#returns(Object firstValue, Object... remainingValues)
method:
when used for methods of return type Set
, SortedSet
,
Iterator
, or array, the individual elements contained in the collection,
iterator or array will be the ones directly specified as arguments.
IllegalArgumentException
to be thrown.
Note that this change can cause existing tests to break, if they inadvertently recorded
duplicate non-strict expectations; to fix such tests, the duplicate expectations will have to be removed.
See issue 42.
TestCase
subclasses overriding the
runTest()
method (such as GWTTestCase
) would not work properly with JMockit in the
classpath. See issue 37.
@Cascading
, when expectations are recorded on a cascaded mock
through a separate mock field/parameter, and there are two or more mocks of the same cascaded type.
See issue 38.
@NonStrict
. The issue was that all other mocks were also considered non-strict, when they should be
strict. See issue 39.
result
field or the returns(...)
varargs method.
jmockit-coverage-metrics
system property can now be used to select the desired combination of the three available code
coverage metrics. Its value should be a comma-separated list containing one or more of the
following words: "line", "path", "data", and "all".
withAny
" methods defined in
the base Invocations
class.
The newer "any
" fields should be used instead.
Mockit
class which belong to the Core API:
redefineMethods(...)
, restoreOriginalDefinition(...)
, and
restoreAllOriginalDefinitions()
.
Equivalent methods to be used are indicated in the API documentation for the deprecated methods.
Usually, however, it's best to use the MockUp<T>
generic base class
when a state-oriented mock class is needed. The deprecated methods will eventually be removed.
(Object[]) any
" argument matching constraint to
a recorded/verified expectation ("(Object[]) null
" can
also be used when another argument matcher is specified for the same invocation).
jmockit.jar
(or a versioned jar name) can now be loaded from a remote file system without triggering
a security-related exception; when running under JDK 1.5, the presence of jmockit.jar
in the
classpath when -javaagent:jmockit.jar
was not used will no longer cause a JMockit-specific exception
to be thrown, unless the mocking API is actually used in a test.
main
method added to the mockit.coverage.CodeCoverage
class (in the main coverage
jar).
The first argument (args[0]
) to the program must be a comma-separated list of paths to
directories containing "coverage.ser" data files.
These data files are merged together and an aggregate report is immediately generated.
jmockit-coverage-serial.jar
file and
the serial
output specifier were created as an alternative to "merge".
The difference is that "merge" reads in an existing data file, while "serial" only writes it out at the end.
"<clinit>"
specifies static initializers) were not
considering the inclusion/exclusion of static initializers.
In particular, the empty filter @Mocked("")
previously excluded all methods and constructors from
being mocked, but still caused static initializers to be stubbed out; now they are also ignored.
@Mock(...)
were not being verified after the execution of a test method.
throwsException(e)
, throwsError(e)
, repeats(n)
,
repeats(m, n)
, repeatsAtLeast(n)
, repeatsAtMost(n)
.
Calls to these methods in existing tests should be replaced with assignments to the corresponding
fields result
, times
, minTimes
, and maxTimes
.
forEachInvocation
field was created, for use both in expectation
and verification blocks. It's similar to Delegate
objects, but more convenient and capable (since
delegates can only be used in expectation blocks).
The focus is on invocation argument validation rather than on making invocations produce expected
results.
onInstance(mock)
method, previously only available in expectation blocks, now can also be
used in verification blocks.
onInstance(mock)
are now implied whenever a test method has in
its scope two or more mock fields/parameters of the exact same mocked type.
This change greatly reduces the cases where explicit calls to onInstance(mock)
were needed, but it
may break existing tests.
mockit.Invocation
class (optionally used as the first parameter in delegate
or forEachInvocation
-handler methods) now has a new read-only property,
invokedInstance
.
The getter will return the mock or real object on which the corresponding method/constructor invocation occurred
(except, naturally, for static
methods).
with(matcher)
and with(T, matcher)
methods of the base
Invocations
class now accept arbitrary invocation handler objects in addition to
org.hamcrest.Matcher
implementations.
Such objects are easier to create (they do not require the implementation of a method that generates failure
messages, nor the addition of Hamcrest classes to the classpath) and allow the use of assert
statements or assertXyz(...)
calls instead of returning a boolean
value.
returns(Object, Object...)
method of the Expectations
class can now be
used to easily specify a list of values to be returned from a method whose return type is List
,
Collection
, or Iterable
.
Deencapsulation
class, all of them overloading
existing methods (see issues 23 and
26).
final
fields only.
A field is considered to be covered (shown in green in the formatted source file) if at least one test left
no unread values from previous assignments to the field; otherwise, the field is considered not covered
(shown in red).
Newer releases will expand and improve this metric, with the goal of using it to discover missing assertions
in tests.
jmockit.jar
.
The "withXyz(...)
" argument matching methods are unaffected, except for the two of them which
accepted a custom matcher as an implementation of org.hamcrest.Matcher
: they still exist and work the
same, but the parameter type has been changed to Object
.
Tests using any of these two methods will need to be recompiled.
Note also that to use one of these two methods the proper Hamcrest classes will have to be available in the
classpath (for example, from junit-4.8.jar
).
(See issue 13.)
@Cascading
annotation was created to enable
automatic cascading of invocations to mocked types.
The cascade effect continues indefinitely for the return types of methods invoked on a cascading mocked type;
cascade return values will be mock instances created on demand.
assert
keyword,
independently of assertions being enabled or not through the "-ea"/"-enableassertions" JVM initialization
parameter.
(This doesn't affect assertions in production code, though, which still should be enabled manually if needed.)
result
field was added to the
Expectations
base class, as an alternative to the returns
and
throwsException/throwsError
methods.
Note that this new field will cause compilation errors in tests that already use a field of the same name inside
an expectation block; such tests will need to be changed to use a different field name.
times
, minTimes
and
maxTimes
fields were added to the Invocations
base class, as an
alternative to the repeats/repeatsAtLeast/repeatsAtMost
methods.
The same warning in the previous item about potential conflicts with existing fields applies here.
$
special field, of type
java.lang.CharSequence
, was added to the Invocations
base class to allow the
specification of custom error messages for specific expectations.
jmockit-tools
system property can now be used to
specify which external tools JMockit should load at startup.
More than one tool can be specified, by separating the tool names with commas.
A tool name must be the fully qualified name of a mock class, or a "startup tool" mnemonic configured in the
jmockit.properties
file.
For example, "coverage" stands for JMockit Coverage. (See issue 22.)
TestCase
subclass overriding the
getName()
method could cause JMockit to not find the test method
(issue 21).
jmockit-coverage.jar
file now also refers to jmockit.jar
through the Class-Path
property in META-INF/MANIFEST.MF
.
This makes it possible to generate coverage reports by adding a single jar to the
classpath when running a test suite which makes no use of the JMockit mocking APIs.
All jar files of the JMockit toolkit must still be present in the same directory,
though.
jmockit-coverage-output
system property.
(When not specified, the basic XHTML report will be generated.)
Note that the property can be defined by a
"-Djmockit-coverage-output=fmt1,fmt2,..." JVM command line argument, or by a
<property>
element in a Maven pom.xml
or Ant
build.xml
file.
jmockit-coverage-outputDir
system property.
(When not specified, the current working dir is used.)
jmockit-coverage-srcDirs
system property.
(When not specified, all "src" directories under the current working dir are searched.)
If the property is specified but with an empty value, then no source directories will be
searched and the report will only contain the index page.
jmockit-coverage-classes
system property.
(When not specified, all classes from production code which are loaded during the test
run and are not inside jar files will be considered.)
jmockit-coverage-classes
being specified or not, the
jmockit-coverage-excludes
system property can be used to
specify a regular expression for class names which should be excluded from
consideration.
/test-classes
" (note that this is the default output directory for
test classes used by Maven 2).
try
" blocks.
prettify.js
(from the
Google Code Prettify project)
for syntax coloring in Java source files.
This makes report generation faster and smaller, but requires a JavaScript-enabled
browser for the proper viewing of source file pages.
(JavaScript is also used for other features in such pages.)
The "index.html" page, on the other hand, makes no use of JavaScript so any XHTML+CSS
browser (such as the one embedded in Eclipse) can be used without any loss.
mockit.Invocation
class was created for
optional use in Delegate
methods.
(issue 6).
Mockit.assertExpectations()
, which will be
removed in a later release.
Existing tests which happen to use it should simply remove any calls, since verification of
invocation count constraints specified on @Mock
methods is done automatically by
JMockit.
mockit.RealMethodNotFoundForMockException
class.
This runtime exception was thrown when an attempt was made to apply a mock class (using either
the Core or Annotations API) to a production class, but there was at least one mock method in
the mock class for which no matching real method could be found in the production class.
Now an IllegalArgumentException
will be thrown instead for the same situation,
with no loss of information (which is fully captured in the exception message).
Expectations
block will now throw an IllegalStateException
if there
are no mocked types in scope.
Note that this change may break existing tests, although it should be rare to have expectation
blocks for which no mocked type is available.
junit.framework.TestCase#runBare()
method, a duplicate execution of this overridden method would
occur. The integration was changed so that runBare()
can now safely be overridden.
-javaagent
JVM parameter, two simplifications were introduced:
<jdkDir>/lib/tools.jar
file no longer needs to be added to
classpath.
@RunWith(JMockit.class)
(for JUnit 4 tests), nor extend a JUnit/TestNG integration base class
(JMockitTest
, JMockitTestCase
, JMockitTestNG
).
jmockit.jar
needs to come before junit-4.x.jar
in the classpath.
@MockField
annotation: simply replace with @Mocked
.Verifications#neverHappens()
method: replace with a
repeats(0);
call right after the invocation to be verified.
Expectations#invokeReturning
generic method: use the
returns
method instead.
Expectations#endReplay()
method: simply remove any calls to it.Expectations.assertSatisfied()
static method: this method was
deprecated in the previous release, and is also being removed now because it does the
same as endReplay()
.
Expectations.restoreFieldTypeDefinitions()
static method: either remove
any calls to it, or replace them with calls to
Mockit.restoreAllOriginalDefinitions()
, which has the same effect.
java.io.File
) that
are used during the class loading process triggered by the JVM.
This avoids the occurrence of a ClassCircularityError
under certain situations
(in particular, when classes used in a test are loaded on demand by the JVM and a critical
JRE class is mocked at the same time).
jmockit-coverage.jar
in the Java.net Maven 2 repository.
mockit.Invocations
base
class; they are equivalent to the T withAny()
/T withAny(T)
methods:
any
, anyInt
, anyBoolean
, etc.
null
reference can now be used to match any object reference, instead
of withAny()
(or instead of the new any
field), as long as
there is at least one explicit matcher specified for the invocation.
java.lang.System
or java.io.InputStreamReader
), all methods
can safely be mocked even if JMockit itself or other parts of the JRE need to execute the
original code (see issue 2).
Delegate
implementation classes can now define a method named differently from the
recorded method to which the delegation applies, provided it's the only method in the delegate class.
Mockit.setUpMock(Object)
now also
accepts a Class
object for the mock class, instead of only an instance of the
mock class. This should avoid confusion with the Mockit.setUpMocks(Object...)
method, which always accepted both ways of passing the mock class.
Expectations
or NonStrictExpectations
constructor which has a
"varargs" parameter, only methods are now considered for mocking, not the
constructors of the classes to which the given object belongs.
This change can break existing tests, but is not likely to do so because in such cases the
test should not be recording expectations on constructors which were used to create the
partially mocked object in the first place.
tearDown
, @After
, or @AfterMethod
).
Expectations.assertSatisfied()
(which has been unnecessary for a
long time already), was deprecated in this release and will be removed for version 1.0.
pom.xml
) for
jmockit.jar
: internal dependencies (on JUnit, TestNG, etc.) were made
optional so they won't be transitively added as dependencies in client Maven
projects.
Mockit#stubOutClass
method which take a class
name instead of a Class
object, for cases where the real class is not accessible
from the test class.
@Mock
annotation can now be applied to methods in reusable mock
classes that are extended by more specific ones. The mock methods in the base mock class will
be inherited by the mock subclass.
@Mocked(realClassName = "...")
annotation attribute to specify the class of the
mock object to be instantiated. The actual field/parameter type will not be considered for
mocking. This can be used to mock non-accessible classes (for example, private nested
classes), by declaring the field/parameter as being of type Object
.
@Capturing
or @Mocked(capture = n)
is used with
@Mocked(methods = "...")
for the same field or parameter).
@Mock
annotation: when the same test applied two different mock classes which
both specify such constraints for the same real class, only one set of constraints
was discarded at the end of the test; this could then cause other tests to fail later.
IllegalAccessError
would occur.
The mocking bridge is now used internally to delegate such mock invocations, in order to avoid
the JVM error.
Therefore, anonymous inner classes can now be safely used as mock classes, thereby avoiding
the need to define them as separate named classes.
mockit.MockUp<T>
class to the Annotations API, in order to facilitate the definition of state-based mock
classes. This class will be most useful inside individual test methods.
returns(...)
methods that will throw an
IllegalArgumentException
whenever a non-null return value is specified for a
mocked constructor or void method.
Specifying null values to be returned from constructor or void methods is valid
though, in order to allow multiple consecutive results to be recorded when one or more of the
invocations should do nothing.
Notice that this change will break any existing tests that happen to violate this validation
rule.
static
methods which otherwise qualify as test methods are ignored.
tearDown()
method, and mocks applied by a setUp()
method were restored automatically after each test method execution (when they should need to
be restored manually, for consistency).
@Mock
annotation), so that the real class/interface name is also included.
IndexOutOfBoundsException
in a test method containing
two expectation blocks, where the first one records strict expectations which are fully
replayed before the second block starts (issue 35).
This actually amounts to a test with two replay phases, which isn't proper use of the
API, even though it is allowed.
jmockit.jar
have been removed, except for those that JMockit itself needs for the
withXyz(...)
argument matching methods available in the
Expectations & Verifications
API.
This means that existing test suites that make use of Hamcrest matchers no longer available in
jmockit.jar
will now need to find those extra classes somewhere else (usually in
hamcrest-library-1.x.jar
).
This change was made to avoid conflicts with potentially different versions of Hamcrest that
may happen to be in the classpath used for running tests.
Delegate
interface. The corresponding delegate method must be named "$init".
Verifications
block) of
invocations that should not have happened through a regular call to repeats(0)
.
Previously, this was achieved through a call to neverHappens()
that should be
made before the verified invocation (the repeats
methods are always to
be called after the corresponding invocations).
Verifications#neverHappens()
method is now deprecated, and will be removed before version 1.0 is released.
FullVerifications
or FullVerificationsInOrder
block, a call to repeatsAtLeast(0)
(or repeats(0, <big number>)
)
will now allow the preceding invocation to be ignored.
This can be useful when a test needs to verify that certain invocations did not occur in the
replay phase, while at the same time allowing other invocations to have occurred any number of
times (including zero).
Expectations
class have been moved to the base Invocations
class, so
they can also be used from Verifications
subclasses.
ClassCastException
in the capturing of new instances
(for example, @Mocked(capture = 1) Callable> mock;
) when the mocked type is
parameterized.
Expectations#endReplay()
(which has become unnecessary),
Expectations#invokeReturning
(which is redundant and inconsistent), and
Expectations#restoreFieldTypeDefinitions()
(also redundant and normally
unnecessary) were deprecated in this release and will be removed for version 1.0.
Expectations#endRecording()
and
Expectations#assertSatisfied()
were not deprecated, even though they
should be rarely, if ever, used. This is emphasized in the API documentation, though.
$init
mock method.
@org.testng.annotations.DataProvider
were being inadvertently mocked.
@Test(invocationCount=5, threadPoolSize=2)
, for example, should not
cause a NPE inside mockit.integration.testng.TestNGTestRunnerDecorator
anymore.
Delegate
support, where null arguments passed to a delegated
method caused an exception to be thrown.
@MockClass
annotation now has an
"instantiation" attribute which controls when a mock instance is created (for each invocation
of an instance mock method, only once for every time the mock class is applied/set up, or
one mock instance for each mocked instance).
JMockitTest
base class can also
be used by @Suite
classes (those annotated with
@RunWith(Suite.class)
), in order to get JMockit initialized before the first
test in the custom suite is executed.
ProtectionDomain#getCodeSource()
returns null
. This is used by
JMockit to discover the local path to "jmockit.jar", needed to auto-load the "java agent".
If that method returns null
, the entries in the execution classpath will be
examined instead.
isAnonymousClass()
in a nested class could lead to a failed attempt to load a
sibling nested class.
@BeforeClass
method, when defined
inside a base test class, to be discarded.
org.junit.Assert
from an internal
class in the Expectations API (issue 26).
@RunWith(Suite.class)
, but without using either "-javaagent" or one of the
mechanisms for on-demand initialization (@RunWith(JMockit.class)
,
extends JMockitTest
, etc.).
Mockit.setUpMocks(...)
, or through the
@UsingMocksAndStubs(...)
annotation.
This means that any mock class (@MockClass
) applied in a JUnit 4.5+ test suite
class (annotated with @Suite.SuiteClasses(...)
) will remain in effect for all
tests in the suite.
Expectations
or
Verifications
, which caused final subclasses to not be modified as they should.
Expectations#returns(value)
method, to facilitate returning
multiple values for a single recorded method. Now two or more return values can be specified
through "varargs" syntax, in a collection, or from an iterator. (Previously, this was possible
only by calling the returns
method multiple times.)
Expectations
,
VerificationsInOrder
, FullVerificationsInOrder
) and unordered ones
(NonStrictExpectations
, Verifications
,
FullVerifications
), to allow the specification of the number of expected
iterations for the whole set of invocations inside each block.
Mockit.setUpStartupMocks(mock classes...)
method to facilitate the
use of startup mocks, which allow applying arbitrary mock classes (annotated with
@MockClass
) at JMockit startup. This can be used to mock or stub out classes
for an entire test suite run. The associated "jmockit.properties" configuration file even
allow the creation of reusable jar files containing mock classes, that can be applied to a
test suite simply by adding the jar file to the classpath.
ClassLoader
first used when reading class files from disk, from the
"System" class loader (the one that regularly loads classes from production/test code) to the
"Context" class loader associated with the current thread (which runs a test).
This allows the execution of test suites in runtime environments (such as the JBoss
application server) that load regular classes through a custom class loader.
Expectations#returns(...)
method when the return type was
SortedSet
or SortedMap
.
new Expectations(true)
instantiation to throw a StackOverflowError
.
<M extends Runnable & Collection<?>>
).
Any mock field or parameter declared with this type variable (as in M mock;
) will
implement all interfaces.
VerificationsInOrder
to support partial ordering.
This allows (for example) the verification that one given method was executed first or last.
It also allows the verification of arbitrary sequences of consecutive invocations.
@Mocked
, @NonStrict
, and @Capturing
)
are considered, as well as non-private fields in subclasses of the Expectations
class, which may or may not be annotated.
Expectations#with(Matcher<T> argumentMatcher)
, so that
it won't return null
in most cases; now, calls like with(is(false))
actually work as expected, passing false
to the parameter.
Expectations/NonStrictExpectations
subclasses:
now all such subclasses that are nested and final
, even those that extend an intermediate
Expectations/NonStrictExpectations
subclass, will automatically call endRecording()
at
the end of the initialization block;
those subclasses which are not final
(and are nested or not) will be considered as intended for reuse
through extension in individual tests, and therefore won't call endRecording()
at the end of their
own instance initialization.
FullVerifications
created as a subclass of
Verifications
, that allows the developer to write a full set of verifications for
the mocked types used in a given test. Non-strict invocations that occur inside code under
test but are not explicitly verified are considered unexpected, causing the test to fail.
Also created the class FullVerificationsInOrder
, which combines
FullVerifications
and VerificationsInOrder
.
mockit.integration.logging
with mock classes for popular logging
frameworks: JDK logging, Log4j, Commons-Logging, SLF4J.
The mock classes can be used with the @UsingMocksAndStubs
annotation.
Expectations#returns(Object)
method now accepts instances of the
new mockit.Delegate
interface. This allows test code to define return values or
thrown errors/exceptions at replay time, based on test-specific logic. Works even for final
and static methods of a mocked type.
Verifications
block.
Fixed an issue with dynamic partial mocking.
Fixed an issue in the stubbing out of abstract/native methods.
Other fixes and small enhancements.
The following changes need to be made to existing JUnit test suites, when migrating from JMockit release 0.97 (or older) to newer releases.
junit.framework.TestCase
now need to extend
mockit.integration.junit3.JMockitTestCase
, unless the test suite is always run
with "-javaagent:jmockit.jar".
Alternatively, the test class can be converted to JUnit 4, with the addition of
@RunWith(JMockit.class)
to the class and of @Test
to its test
methods.
mockit.Expectations
, if there is any
initialization of instance fields outside of a @Before/setUp
method, then a JUnit
fixture setup method will have to be created to perform the initialization.
This is necessary because now any mock fields of the test class will only be assigned
after the test class instance is created (but before any setup or test methods are
executed).
Expectations
subclass (which can be a test class, an anonymous inner class
inside a test method, and so on) declares two or more mock fields of the same type or with a
common base type, then these fields must mock exactly the same set of methods and constructors
belonging to the common class types.
By default, all methods and constructors are mocked, so this issue can only happen when
(static) partial mocking is used, through the methods
or value
attribute of the MockField/Mocked
annotation.
So, if that's the case, simply copy the mock filters specified in one mock field to the
others.
Mockit.tearDownMocks()
,
Mockit.restoreAllOriginalDefinitions()
, or
Mockit.restoreOriginalDefinition(...)
need to be explicitly called anymore,
unless a given test method really needs to restore some mocked class before the test completes
its execution.
This also means that classes that remained mocked between tests or from one test class to the
next in the suite, will not remain mocked as before, but will be restored
automatically either between individual tests, or from one test class to the next.
Therefore, it will be necessary to set up the mocks again at the appropriate point (for
example, in a @Before
or @BeforeClass
method when using JUnit 4).
It should be easy enough to adapt existing tests according to the incompatibilities listed above. If after making such changes some tests remain broken that weren't before, please let me know.
Expectations
anonymous subclass instance, the
endRecording()
method is automatically called at the end of the initialization
block.
Accordingly, the Expectations
constructors which took a
boolean autoEndRecording
parameter were removed (a breaking API change).
Expectations
now will be assigned mock instances as soon as the test class is
instantiated (before any tests or setup methods are executed).
Expectations
subclass to the end of the test, while mocking
the concrete class, whichever it may be; each captured instance is assigned to the appropriate
mock field (one or more times, with a specified upper limit). For example, this allows the
mocking of a concrete class that implements an interface (used as the type of a mock field)
and is dynamically loaded by production code sometime during the test.
@Capturing
annotation which, similarly to the previous item, allows
implementations of abstract types (interfaces or base classes) to be mocked on-demand,
either when the implementation class is loaded by the JVM, or when the targeted scope (test
class, test method) is entered during test suite execution.
onInstance(mock)
in Expectations
to match the mock
instance on which invocations occur between corresponding calls in the record and replay
phases.
By default, such instances can be different, so this method allows a test to compare them when
they must be the same.
stubOut(classes)
in Mockit
that stubs out the
implementation of all methods, constructors, and static initializers in one or more given
classes.
Individual stubbed out methods/constructors can later be mocked by regular means
(setUpMocks
, Expectations
).
@UsingMocksAndStubs(classes)
that can be applied to test classes
so that one or more mock classes (annotated with @MockClass
) are applied, and/or
one or more regular classes are stubbed out. The scope for such mocks and stubs is the set of
all tests in the annotated test class.
@NonStrict
annotation indicates a mock on which all invocations will
be considered non-strict;
2) the new NonStrictExpectations
class extends Expectations
so that all invocations to mocked types inside the initialization block will be considered
non-strict.
Verifications
class, which shares many of the methods provided by the
Expectations
class.
In addition, there is a VerificationsInOrder
subclass which also verifies the
order of invocation to the expectations of one or more mocked types.
@MockField
annotation was
deprecated in favor of a new @Mocked
annotation which can be applied to either
fields or parameters.
Deencapsulation
created, with static methods to access fields,
methods and constructors non-accessible to the test, mirroring the previously existing methods
in the Expectations
class (which continue to exist).