• Home
  • History
  • Annotate
Name Date Size #Lines LOC

..03-May-2022-

.github/H18-Oct-2021-

qtsuite/H18-Oct-2021-

.gitignoreH A D18-Oct-20218

.godocdown.templateH A D18-Oct-2021546

LICENSEH A D18-Oct-20211 KiB

README.mdH A D18-Oct-20219.9 KiB

checker.goH A D18-Oct-202123.7 KiB

checker_go1.13.goH A D18-Oct-20212.2 KiB

checker_go1.13_test.goH A D18-Oct-20213.9 KiB

checker_test.goH A D18-Oct-202155.6 KiB

cleanup_test.goH A D18-Oct-20211.3 KiB

comment.goH A D18-Oct-2021908

comment_test.goH A D18-Oct-2021656

deferpanic_test.goH A D18-Oct-2021863

doc.goH A D18-Oct-20219.3 KiB

error.goH A D18-Oct-20211.1 KiB

error_test.goH A D18-Oct-20211.1 KiB

export_test.goH A D18-Oct-2021733

format.goH A D18-Oct-20212.4 KiB

format_test.goH A D18-Oct-20212.9 KiB

go.modH A D18-Oct-2021121

go.sumH A D18-Oct-20211.4 KiB

iter.goH A D18-Oct-20211.1 KiB

mapiter.goH A D18-Oct-2021529

mapiter_go1.11.goH A D18-Oct-2021900

patch.goH A D18-Oct-20211.9 KiB

patch_go1.14.goH A D18-Oct-20211.3 KiB

patch_go1.14_test.goH A D18-Oct-2021945

patch_go1.17.goH A D18-Oct-2021641

patch_go1.17_test.goH A D18-Oct-2021750

patch_test.goH A D18-Oct-20212.5 KiB

quicktest.goH A D18-Oct-202110.3 KiB

quicktest_test.goH A D18-Oct-202115.4 KiB

race_test.goH A D18-Oct-20211.9 KiB

report.goH A D18-Oct-20215.4 KiB

report_test.goH A D18-Oct-20213 KiB

README.md

1[![GoDoc](https://godoc.org/github.com/frankban/quicktest?status.svg)](https://godoc.org/github.com/frankban/quicktest)
2[![Build Status](https://github.com/frankban/quicktest/actions/workflows/ci.yaml/badge.svg)](https://github.com/frankban/quicktest/actions/workflows/ci.yaml)
3
4[//]: # (Generated with: godocdown -template=.godocdown.template -o README.md)
5
6# quicktest
7
8`go get github.com/frankban/quicktest`
9
10Package quicktest provides a collection of Go helpers for writing tests.
11
12Quicktest helpers can be easily integrated inside regular Go tests, for
13instance:
14
15    import qt "github.com/frankban/quicktest"
16
17    func TestFoo(t *testing.T) {
18        t.Run("numbers", func(t *testing.T) {
19            c := qt.New(t)
20            numbers, err := somepackage.Numbers()
21            c.Assert(numbers, qt.DeepEquals, []int{42, 47})
22            c.Assert(err, qt.ErrorMatches, "bad wolf")
23        })
24        t.Run("nil", func(t *testing.T) {
25            c := qt.New(t)
26            got := somepackage.MaybeNil()
27            c.Assert(got, qt.IsNil, qt.Commentf("value: %v", somepackage.Value))
28        })
29    }
30
31
32### Assertions
33
34An assertion looks like this, where qt.Equals could be replaced by any available
35checker. If the assertion fails, the underlying Fatal method is called to
36describe the error and abort the test.
37
38    c := qt.New(t)
39    c.Assert(someValue, qt.Equals, wantValue)
40
41If you don’t want to abort on failure, use Check instead, which calls Error
42instead of Fatal:
43
44    c.Check(someValue, qt.Equals, wantValue)
45
46For really short tests, the extra line for instantiating *qt.C can be avoided:
47
48    qt.Assert(t, someValue, qt.Equals, wantValue)
49    qt.Check(t, someValue, qt.Equals, wantValue)
50
51The library provides some base checkers like Equals, DeepEquals, Matches,
52ErrorMatches, IsNil and others. More can be added by implementing the Checker
53interface. Below, we list the checkers implemented by the package in
54alphabetical order.
55
56
57### All
58
59All returns a Checker that uses the given checker to check elements of slice or
60array or the values of a map. It succeeds if all elements pass the check. On
61failure it prints the error from the first index that failed.
62
63For example:
64
65    c.Assert([]int{3, 5, 8}, qt.All(qt.Not(qt.Equals)), 0)
66    c.Assert([][]string{{"a", "b"}, {"a", "b"}}, qt.All(qt.DeepEquals), []string{"c", "d"})
67
68See also Any and Contains.
69
70
71### Any
72
73Any returns a Checker that uses the given checker to check elements of a slice
74or array or the values from a map. It succeeds if any element passes the check.
75
76For example:
77
78    c.Assert([]int{3,5,7,99}, qt.Any(qt.Equals), 7)
79    c.Assert([][]string{{"a", "b"}, {"c", "d"}}, qt.Any(qt.DeepEquals), []string{"c", "d"})
80
81See also All and Contains.
82
83
84### CmpEquals
85
86CmpEquals checks equality of two arbitrary values according to the provided
87compare options. DeepEquals is more commonly used when no compare options are
88required.
89
90Example calls:
91
92    c.Assert(list, qt.CmpEquals(cmpopts.SortSlices), []int{42, 47})
93    c.Assert(got, qt.CmpEquals(), []int{42, 47}) // Same as qt.DeepEquals.
94
95
96### CodecEquals
97
98CodecEquals returns a checker that checks for codec value equivalence.
99
100    func CodecEquals(
101        marshal func(interface{}) ([]byte, error),
102        unmarshal func([]byte, interface{}) error,
103        opts ...cmp.Option,
104    ) Checker
105
106It expects two arguments: a byte slice or a string containing some
107codec-marshaled data, and a Go value.
108
109It uses unmarshal to unmarshal the data into an interface{} value. It marshals
110the Go value using marshal, then unmarshals the result into an interface{}
111value.
112
113It then checks that the two interface{} values are deep-equal to one another,
114using CmpEquals(opts) to perform the check.
115
116See JSONEquals for an example of this in use.
117
118
119### Contains
120
121Contains checks that a map, slice, array or string contains a value. It's the
122same as using Any(Equals), except that it has a special case for strings - if
123the first argument is a string, the second argument must also be a string and
124strings.Contains will be used.
125
126For example:
127
128    c.Assert("hello world", qt.Contains, "world")
129    c.Assert([]int{3,5,7,99}, qt.Contains, 7)
130
131
132### ContentEquals
133
134ContentEquals is is like DeepEquals but any slices in the compared values will
135be sorted before being compared.
136
137For example:
138
139    c.Assert([]string{"c", "a", "b"}, qt.ContentEquals, []string{"a", "b", "c"})
140
141
142### DeepEquals
143
144DeepEquals checks that two arbitrary values are deeply equal. The comparison is
145done using the github.com/google/go-cmp/cmp package. When comparing structs, by
146default no exported fields are allowed. If a more sophisticated comparison is
147required, use CmpEquals (see below).
148
149Example call:
150
151    c.Assert(got, qt.DeepEquals, []int{42, 47})
152
153
154### Equals
155
156Equals checks that two values are equal, as compared with Go's == operator.
157
158For instance:
159
160    c.Assert(answer, qt.Equals, 42)
161
162Note that the following will fail:
163
164    c.Assert((*sometype)(nil), qt.Equals, nil)
165
166Use the IsNil checker below for this kind of nil check.
167
168
169### ErrorAs
170
171ErrorAs checks that the error is or wraps a specific error type. If so, it
172assigns it to the provided pointer. This is analogous to calling errors.As.
173
174For instance:
175
176    // Checking for a specific error type
177    c.Assert(err, qt.ErrorAs, new(*os.PathError))
178
179    // Checking fields on a specific error type
180    var pathError *os.PathError
181    if c.Check(err, qt.ErrorAs, &pathError) {
182        c.Assert(pathError.Path, Equals, "some_path")
183    }
184
185
186### ErrorIs
187
188ErrorIs checks that the error is or wraps a specific error value. This is
189analogous to calling errors.Is.
190
191For instance:
192
193    c.Assert(err, qt.ErrorIs, os.ErrNotExist)
194
195
196### ErrorMatches
197
198ErrorMatches checks that the provided value is an error whose message matches
199the provided regular expression.
200
201For instance:
202
203    c.Assert(err, qt.ErrorMatches, `bad wolf .*`)
204
205
206### HasLen
207
208HasLen checks that the provided value has the given length.
209
210For instance:
211
212    c.Assert([]int{42, 47}, qt.HasLen, 2)
213    c.Assert(myMap, qt.HasLen, 42)
214
215
216### Implements
217
218Implements checks that the provided value implements an interface. The interface
219is specified with a pointer to an interface variable.
220
221For instance:
222
223    var rc io.ReadCloser
224    c.Assert(myReader, qt.Implements, &rc)
225
226
227### IsFalse
228
229IsFalse checks that the provided value is false. The value must have a boolean
230underlying type.
231
232For instance:
233
234    c.Assert(false, qt.IsFalse)
235    c.Assert(IsValid(), qt.IsFalse)
236
237
238### IsNil
239
240IsNil checks that the provided value is nil.
241
242For instance:
243
244    c.Assert(got, qt.IsNil)
245
246As a special case, if the value is nil but implements the error interface, it is
247still considered to be non-nil. This means that IsNil will fail on an error
248value that happens to have an underlying nil value, because that's invariably a
249mistake. See https://golang.org/doc/faq#nil_error.
250
251So it's just fine to check an error like this:
252
253    c.Assert(err, qt.IsNil)
254
255
256### IsNotNil
257
258IsNotNil is a Checker checking that the provided value is not nil. IsNotNil is
259the equivalent of qt.Not(qt.IsNil)
260
261For instance:
262
263    c.Assert(got, qt.IsNotNil)
264
265
266### IsTrue
267
268IsTrue checks that the provided value is true. The value must have a boolean
269underlying type.
270
271For instance:
272
273    c.Assert(true, qt.IsTrue)
274    c.Assert(myBoolean(false), qt.IsTrue)
275
276
277### JSONEquals
278
279JSONEquals checks whether a byte slice or string is JSON-equivalent to a Go
280value. See CodecEquals for more information.
281
282It uses DeepEquals to do the comparison. If a more sophisticated comparison is
283required, use CodecEquals directly.
284
285For instance:
286
287    c.Assert(`{"First": 47.11}`, qt.JSONEquals, &MyStruct{First: 47.11})
288
289
290### Matches
291
292Matches checks that a string or result of calling the String method (if the
293value implements fmt.Stringer) matches the provided regular expression.
294
295For instance:
296
297    c.Assert("these are the voyages", qt.Matches, `these are .*`)
298    c.Assert(net.ParseIP("1.2.3.4"), qt.Matches, `1.*`)
299
300
301### Not
302
303Not returns a Checker negating the given Checker.
304
305For instance:
306
307    c.Assert(got, qt.Not(qt.IsNil))
308    c.Assert(answer, qt.Not(qt.Equals), 42)
309
310
311### PanicMatches
312
313PanicMatches checks that the provided function panics with a message matching
314the provided regular expression.
315
316For instance:
317
318    c.Assert(func() {panic("bad wolf ...")}, qt.PanicMatches, `bad wolf .*`)
319
320
321### Satisfies
322
323Satisfies checks that the provided value, when used as argument of the provided
324predicate function, causes the function to return true. The function must be of
325type func(T) bool, having got assignable to T.
326
327For instance:
328
329    // Check that an error from os.Open satisfies os.IsNotExist.
330    c.Assert(err, qt.Satisfies, os.IsNotExist)
331
332    // Check that a floating point number is a not-a-number.
333    c.Assert(f, qt.Satisfies, math.IsNaN)
334
335
336### Deferred Execution
337
338The testing.TB.Cleanup helper provides the ability to defer the execution of
339functions that will be run when the test completes. This is often useful for
340creating OS-level resources such as temporary directories (see c.Mkdir).
341
342When targeting Go versions that don't have Cleanup (< 1.14), the same can be
343achieved using c.Defer. In this case, to trigger the deferred behavior, calling
344c.Done is required. For instance, if you create a *C instance at the top level,
345you’ll have to add a defer to trigger the cleanups at the end of the test:
346
347    defer c.Done()
348
349However, if you use quicktest to create a subtest, Done will be called
350automatically at the end of that subtest. For example:
351
352    func TestFoo(t *testing.T) {
353        c := qt.New(t)
354        c.Run("subtest", func(c *qt.C) {
355            c.Setenv("HOME", c.Mkdir())
356            // Here $HOME is set the path to a newly created directory.
357            // At the end of the test the directory will be removed
358            // and HOME set back to its original value.
359        })
360    }
361
362The c.Patch, c.Setenv, c.Unsetenv and c.Mkdir helpers use t.Cleanup for cleaning
363up resources when available, and fall back to Defer otherwise.
364
365For a complete API reference, see the
366[package documentation](https://pkg.go.dev/github.com/frankban/quicktest).
367