File: README.md

package info (click to toggle)
r-cran-mockery 0.4.2+dfsg-2
  • links: PTS, VCS
  • area: main
  • in suites: bullseye, sid
  • size: 172 kB
  • sloc: sh: 13; makefile: 2
file content (153 lines) | stat: -rw-r--r-- 4,419 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
# mockery
[![Travis-CI Build Status](https://travis-ci.org/r-lib/mockery.svg?branch=master)](https://travis-ci.org/r-lib/mockery)
[![Coverage Status](https://img.shields.io/codecov/c/github/r-lib/mockery/master.svg)](https://codecov.io/github/r-lib/mockery?branch=master)
[![CRAN version](http://www.r-pkg.org/badges/version/mockery)](https://CRAN.r-project.org/package=mockery)
[![Downloads](http://cranlogs.r-pkg.org/badges/mockery)](https://CRAN.r-project.org/package=mockery)

A mocking library for R.

### Installation

To install the latest CRAN release:

```R
install.packages('mockery')
```

To install directly from the source code in this GitHub repository:

```R
# If you don't have devtools installed yet:
install.packages('devtools')

# Then:
devtools::install_github('r-lib/mockery')
```

### Testing

Mockery provides the capacity for stubbing out functions and for verifying
function calls during testing.

#### Stubbing

Mockery's `stub` function will let you stub out a function with another
function or simply a return value.  Note that if you choose to replace the
function with another function, the signatures of the two functions should be
compatible.

##### Examples

```R
g = function(y) y
f = function(x) g(x) + 1
test_that('demonstrate stubbing', {
    # replaces 'g' with a function that always returns 100
    # but only when called from f
    stub(f, 'g', 100)

    # this can also be written
    stub(f, 'g', function(...) 100)
    expect_equal(f(1), 101)
})
```

Stubbing works with classes of all descriptions and namespaced functions:

```R
# this stubs the 'request_perform' function, but only
# for httr::get, and only when it is called from within this
# test function
stub(httr::GET, 'request_perform', 'some html')
        
# it is also possible to stub out a namespaced function call
stub(some_function, 'namespace::function', 'some return value')
```

This also works with R6 classes and methods.

###### Depth

It's possible to specify the depth of stubbing. This is useful if you
want to stub a function that isn't called directly by the function you call in
your test, but is instead called by a function that that function calls. 

In the example below, the function `g` is both called directly from `r`, which
we call from the test, and from `f`, which `r` calls. By specifying a depth of
2, we tell mockery to stub `g` in both places.

```R
g = function(y) y
f = function(x) g(x) + 1
r = function(x) g(x) + f(x)
test_that('demonstrate stubbing', {
    stub(r, 'g', 100, depth=2)
    expect_equal(r(1), 201)
})
```

For more examples, please see the test code contained in this repository.

##### Comparison to with_mock

Mockery's `stub` function has similar functionality to testthat's `with_mock`.

There are several use cases in which mockery's `stub` function will work, but
testthat's `with_mock` will not.

First, unlike `with_mock`, it seamlessly allows for mocking out primitives.

Second, it is easy to stub out functions from base R packages with mockery's `stub`.
Because of how `with_mock` works, you can get into trouble if you mock such functions 
that the JIT compiler might try to use. These kinds of problems are avoided by `stub`'s
design. As of version 2.0.0 of testthat, it will be impossible to mock functions from
base R packages `with_mock`.

The functionality of `stub` is just slightly different than that of `with_mock`. Instead
of mocking out the object of interest for the duration of some code block, it mocks it
out only when it is called from a specified function.

#### Mocking

Mock objects allow you to specify the behavior of the function you've stubbed
out while also verifying how that function was used. 

```R
g = function(y) y
f = function(x) g(x) + 1
test_that('demonstrate mock object usage', {
    # mocks can specify behavior
    mock = mock(100)
    stub(f, 'g', mock)
    result = f(5)
    expect_equal(result, 101)

    # and allow you to make assertions on the mock was treated
    expect_called(mock, 1)
    expect_args(mock, 1, 5)
})
```

You can also specify multiple return values

```R
mock = mock(1, "a", sqrt(3))
```

and access the arguments with which it was called.

```R
mock <- mock()
mock(x = 1)
mock(y = 2)

expect_equal(length(mock), 2)
args <- mock_args(mock)

expect_equal(args[[1]], list(x = 1))
expect_equal(args[[2]], list(y = 2))
```

---

Please report bugs and feature requests through github issues.