Overview | Package | Class | Deprecated | Index | Help
| Groovy Documentation
| FRAMES NO FRAMES
SUMMARY: NESTED | FIELD | PROPERTY | CONSTR | METHOD | DETAIL: FIELD | PROPERTY | CONSTR | METHOD

## groovy.mock.interceptor
[Groovy] Class MockFor

    java.lang.Object
      groovy.mock.interceptor.MockFor

    class MockFor

MockFor supports (typically unit) testing of classes in isolation by allowing a strictly ordered expectation of the behavior of collaborators to be defined. A typical test scenario involves a class under test (CUT) and one or more collaborators. In such a scenario it is often desirable to just test the business logic of the CUT. One strategy for doing that is to replace the collaborator instances with simplified mock objects to help isolate out the logic in the CUT. MockFor allows such mocks to be created using meta-programming. The desired behavior of collaborators is defined as a behavior specification. The behavior is enforced and checked automatically. With MockFor, a mock's expectation is always sequence dependent and its use automatically ends with a verify(). Typical usage is as follows:

     import groovy.mock.interceptor.MockFor

     class Person {
       String first, last
     }

     class Family {
       Person father, mother
       def nameOfMother() { "$mother.first $mother.last" }
     }

     def mock = new MockFor(Person)
     mock.demand.getFirst{ 'dummy' }
     mock.demand.getLast{ 'name' }
     mock.use {
       def mary = new Person(first:'Mary', last:'Smith')
       def f = new Family(mother:mary)
       assert f.nameOfMother() == 'dummy name'
     }

Here, `Family` is our class under test and `Person` is the collaborator. We are using normal Groovy property semantics here; hence the statement `mother.last` causes a call to `mother.getLast()` to occur. The following features are supported:

- typical mock style of failing early
- mocks instance and class/static methods
- mocks property access using normal getters and setters
- mocks final methods and final Collaborators
- mocks Groovy and Java Collaborators (Caller must normally be Groovy but see `proxyDelegateInstance()`)
- can mock all objects of a given class (or a single Groovy object)
- mocks even if Collaborator cannot be injected into the Caller
- mocks even if Collaborator is not accessible on the Caller (no getter)
- demanded calls specified via recording calls on the Demand object (EasyMock style).
- cardinality specified as Integers or Ranges, default is 1..1; 'optional' can be achieved with 0..1
- behavior specified via Closures, allowing static or calculated return values, throwing exceptions, asserting argument values, etc. (even tricky sequence constraints by sharing state in the testMethod scope between the behavior Closures)
- matching parameter list specified via Closure's parameter list, supporting typed or untyped params, default params, and varargs.
- not dependent on any external mock library
- can mock constructors using an overloaded constructor for MockFor
- can support an instance-style mode rather than the default behaviour-style mode using `proxyInstance()` and `proxyDelegateInstance()`
- can support half-mocks using an `ignore` specification on the mock instead of a demand specification
- can mock non-existing methods if desired

See also: StubFor.

Authors:
  Dierk Koenig
  Paul King

Property Summary
`java.lang.Class` | `clazz`
`Demand` | `demand`
`java.lang.Object` | `expect`
`Ignore` | `ignore`
`java.util.Map` | `instanceExpectations`
`MockProxyMetaClass` | `proxy`

Constructor Summary
`MockFor(java.lang.Class clazz, boolean interceptConstruction = false)` The optional `interceptConstruction` flag allows mocking of constructor calls.

Method Summary
`static GroovyObject` | `getInstance(java.lang.Class clazz, java.lang.Object args)`
`java.lang.Object` | `ignore(java.lang.Object filter, Closure filterBehavior = null)` Allows particular method calls to be ignored and not treated as part of the required behavior specification.
`GroovyObject` | `makeProxyInstance(java.lang.Object args, boolean isDelegate)`
`GroovyObject` | `proxyDelegateInstance(java.lang.Object args = null)` Allows a more traditional instance-style mocking paradigm.
`GroovyObject` | `proxyInstance(java.lang.Object args = null)` Allows a more traditional instance-style mocking paradigm.
`void` | `use(Closure closure)` Identifies the Closure where the mocked collaborator behavior will be applied and verified.
`void` | `use(GroovyObject obj, Closure closure)`
`void` | `verify(GroovyObject obj)` If manual verification is required

Methods inherited from class java.lang.Object
java.lang.Object#wait(long), java.lang.Object#wait(long, int), java.lang.Object#wait(), java.lang.Object#equals(java.lang.Object), java.lang.Object#toString(), java.lang.Object#hashCode(), java.lang.Object#getClass(), java.lang.Object#notify(), java.lang.Object#notifyAll()

Property Detail

### clazz

    java.lang.Class clazz

### demand

    Demand demand

### expect

    java.lang.Object expect

### ignore

    Ignore ignore

### instanceExpectations

    java.util.Map instanceExpectations

### proxy

    MockProxyMetaClass proxy

Constructor Detail

### MockFor

    MockFor(java.lang.Class clazz, boolean interceptConstruction = false)

  The optional `interceptConstruction` flag allows mocking of constructor calls. These are represented in the demand specification using the class name as this example shows:

       import groovy.mock.interceptor.MockFor
       class Person {
         String first, last
       }
       def interceptConstructorCalls = true
       def mock = new MockFor(Person, interceptConstructorCalls)
       def dummy = new Person(first:'Tom', last:'Jones')
       mock.demand.with {
         Person() { dummy } // expect constructor call, return dummy
         getFirst() {'John'}
         getLast() {'Doe'}
       }
       mock.use {
         def p = new Person(first:'Mary', last:'Smith')
         assert p.first == 'John'
         assert p.last == 'Doe'
       }

Method Detail

### getInstance

    static GroovyObject getInstance(java.lang.Class clazz, java.lang.Object args)

### ignore

    java.lang.Object ignore(java.lang.Object filter, Closure filterBehavior = null)

  Allows particular method calls to be ignored and not treated as part of the required behavior specification. If you don't specify a return closure the method call will fall through to the underlying instance, i.e. half-mock style. The `filter` object is invoked using the normal Groovy `isCase()` semantics. Here are some examples:

       import groovy.mock.interceptor.MockFor
       class Person {
         String first, last
         def name() { "$first $last" }
         def ignoreMe() { 'baz' }
         def ignoreMeToo() { ignoreMe() }
         def ignoreMeThree() { ignoreMe() }
       }
       def mock = new MockFor(Person)
       mock.ignore(~'get.*')
       mock.ignore('ignoreMeToo') { 'boo' }
       mock.ignore(~'ignoreMe.*')
       mock.demand.name{ 'John' }
       mock.use {
         def p = new Person(first:'Mary', last:'Smith')
         assert p.first == 'Mary'
         assert p.last == 'Smith'
         assert p.name() == 'John'
         assert p.ignoreMe() == 'baz'
         assert p.ignoreMeToo() == 'boo'
         assert p.ignoreMeThree() == 'baz'
       }

  There is also a convenience form of ignore that matches the same style as demand. E.g. instead of `mock.ignore('hasNext')` you can use `mock.ignore.hasNext()`. A Closure variation is also provided. This convenience shorthand only applies to the `String` form of ignore and cannot be used with methods from `java.lang.Object`. Be careful using this feature while mocking some of the fundamental Java classes like `String` or `Pattern`. As these are used within the implementation of the ignore capability, strange behavior may be observed.

### makeProxyInstance

    GroovyObject makeProxyInstance(java.lang.Object args, boolean isDelegate)

### proxyDelegateInstance

    GroovyObject proxyDelegateInstance(java.lang.Object args = null)

  Allows a more traditional instance-style mocking paradigm. This is the recommended method to call to use the instance-style with Java classes. When mocking interfaces or abstract classes, a compatible proxy instance will be returned. When mocking Java classes, a compatible Groovy class will be generated and proxy instance returned. A MockProxyMetaClass will be instantiated for the class of the instance (i.e. may be on the generated class not the original class).

### proxyInstance

    GroovyObject proxyInstance(java.lang.Object args = null)

  Allows a more traditional instance-style mocking paradigm. This is the recommended method to call to use the instance-style with Groovy classes. When mocking interfaces or abstract classes, a compatible proxy instance will be returned. When mocking Java classes, a compatible Groovy class will be generated and proxy instance returned. A MockProxyMetaClass will be instantiated for the original class. Typical example:

       import groovy.mock.interceptor.MockFor

       class Person {
         String first, last
       }

       class Family {
         Person mother, father
         String nameOfMother() { fullName(mother) }
         String nameOfFather() { fullName(father) }
         private fullName(p) { "$p.first $p.last" }
       }

       def mock = new MockFor(Person)
       mock.demand.with {
         getFirst{ 'dummy' }
         getLast{ 'name' }
       }
       Person john = mock.proxyInstance()
       Person mary = mock.proxyInstance()
       Family f = new Family(father:john, mother:mary)
       assert f.nameOfFather() == 'dummy name'
       assert f.nameOfMother() == 'dummy name'
       [john, mary].each{ mock.verify(it) }

  Normally for mocks, `verify()` is call automatically at the end of the "use" Closure, but with this style, no "use" Closure is present, so `verify()` must be called manually.

### use

    void use(Closure closure)

  Identifies the Closure where the mocked collaborator behavior will be applied and verified.

### use

    void use(GroovyObject obj, Closure closure)

### verify

    void verify(GroovyObject obj)

  If manual verification is required

Groovy Documentation