Skip to content

Commit 531314a

Browse files
authored
Merge pull request #336 from jmid/add-corner-warning
Documentation: Add notes to corner-case generators and fix some broken documentation references
2 parents 858fb07 + ebdfa86 commit 531314a

File tree

7 files changed

+62
-28
lines changed

7 files changed

+62
-28
lines changed

CHANGELOG.md

+2
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,8 @@
88
workaround MinGW float printing to also pass expect tests
99
- Fix dune snippets missing a language specifier in README.adoc
1010
causing `asciidoc` to error
11+
- Add a note to `QCheck{,2.Gen}.small_int_corners` and `QCheck{,2}.Gen.graft_corners`
12+
about internal state, and fix a range of documentation reference warnings
1113

1214
## 0.24
1315

doc/qcheck-core/index.mld

+2-2
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ The [qcheck-core] opam package contains two libraries:
55
- The [qcheck-core] library for defining property-based tests
66
- The [qcheck-core.runner] library for running property-based tests
77

8-
{1: The [qcheck-core] library}
8+
{1 The [qcheck-core] library}
99

1010
The [qcheck-core] library exposes two toplevel modules:
1111

@@ -21,7 +21,7 @@ removing the need for having to hand-write shrinkers.
2121
file an issue if you encounter problems using either of the two
2222
modules.
2323

24-
{1: The [qcheck-core.runner] library}
24+
{1 The [qcheck-core.runner] library}
2525

2626
The entry point of the [qcheck-core.runner] library is the {!QCheck_base_runner} module.
2727

src/core/QCheck.mli

+24-7
Original file line numberDiff line numberDiff line change
@@ -78,7 +78,7 @@ all rights reserved.
7878
]}
7979
8080
More complex and powerful combinators can be found in Gabriel Scherer's
81-
{!Generator} module. Its documentation can be found
81+
{{:https://github.com/gasche/random-generator}[Generator]} module. Its documentation can be found
8282
{{:http://gasche.github.io/random-generator/doc/Generator.html } here}.
8383
*)
8484

@@ -325,6 +325,12 @@ module Gen : sig
325325
val graft_corners : 'a t -> 'a list -> unit -> 'a t
326326
(** [graft_corners gen l ()] makes a new generator that enumerates
327327
the corner cases in [l] and then behaves like [g].
328+
329+
Note that [graft_corners gen l ()] is stateful, meaning that once the
330+
elements of [l] have been emitted, subsequent calls will not reproduce
331+
them. It is therefore recommended that separate tests each use a fresh
332+
generator.
333+
328334
@since 0.6 *)
329335

330336
val int_pos_corners : int list
@@ -415,7 +421,7 @@ module Gen : sig
415421
val bytes : ?gen:char t -> bytes t
416422
(** Builds a bytes generator. Bytes size is generated by {!nat}.
417423
Accepts an optional character generator (the default is {!char}).
418-
See also {!bytes_of} and {!bytes_readable} for versions without
424+
See also {!bytes_of} and {!bytes_printable} for versions without
419425
optional parameters.
420426
@since 0.20 *)
421427

@@ -640,7 +646,7 @@ module Gen : sig
640646
(** {{: https://ocaml.org/manual/bindingops.html} Binding operator} alias for {!pair}. *)
641647

642648
val ( let* ) : 'a t -> ('a -> 'b t) -> 'b t
643-
(** {{: https://ocaml.org/manual/bindingops.html} Binding operator} alias for {!bind}. *)
649+
(** {{: https://ocaml.org/manual/bindingops.html} Binding operator} alias for {!(>>=)}. *)
644650

645651
val ( and* ) : 'a t -> 'b t -> ('a * 'b) t
646652
(** {{: https://ocaml.org/manual/bindingops.html} Binding operator} alias for {!pair}. *)
@@ -1144,7 +1150,18 @@ val pos_int : int arbitrary
11441150

11451151
val small_int_corners : unit -> int arbitrary
11461152
(** As [small_int], but each newly created generator starts with
1147-
a list of corner cases before falling back on random generation. *)
1153+
a list of corner cases before falling back on random generation.
1154+
1155+
Note that [small_int_corners ()] is stateful, meaning that once the list of
1156+
corner cases has been emitted, subsequent calls will not reproduce them.
1157+
As a consequence, in the following example, the first test fails with a
1158+
counter example, whereas the second rerun does not:
1159+
{[
1160+
let gen = QCheck.small_int_corners ()
1161+
let t = QCheck.Test.make ~name:"never max_int" gen (fun i -> i <> max_int)
1162+
let _ = QCheck_base_runner.run_tests ~verbose:true [t;t]
1163+
]}
1164+
*)
11481165

11491166
val neg_int : int arbitrary
11501167
(** Negative int generator (0 included, see {!Gen.neg_int}).
@@ -1400,7 +1417,7 @@ val tup9 :
14001417

14011418
val choose : 'a arbitrary list -> 'a arbitrary
14021419
(** Choose among the given list of generators. The list must not
1403-
be empty; if it is Invalid_argument is raised. *)
1420+
be empty; if it is [Invalid_argument] is raised. *)
14041421

14051422
val oneofl : ?print:'a Print.t -> ?collect:('a -> string) ->
14061423
'a list -> 'a arbitrary
@@ -1878,7 +1895,7 @@ module Tuple : sig
18781895
val nil : unit t
18791896
val cons : 'a -> 'b t -> ('a * 'b) t
18801897

1881-
(** How to observe a {!'a t} *)
1898+
(** How to observe a {{!t}['a t]} *)
18821899
type 'a obs
18831900

18841901
val o_nil : unit obs
@@ -1889,7 +1906,7 @@ module Tuple : sig
18891906
(** Alias to {!cons}. *)
18901907

18911908
val (@->) : 'a Observable.t -> 'b obs -> ('a * 'b) obs
1892-
(** Alias to {!B_cons}. *)
1909+
(** Alias to {!o_cons}. *)
18931910
end
18941911

18951912
include module type of Infix

src/core/QCheck2.mli

+26-11
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ content will appear. *)
3434
3535
{1 Examples}
3636
37-
- "{!List.rev} is involutive" (the test passes so [check_exn] returns [()]):
37+
- "[List.rev] is involutive" (the test passes so [check_exn] returns [()]):
3838
3939
{[
4040
let test =
@@ -233,8 +233,18 @@ module Gen : sig
233233

234234
val small_int_corners : unit -> int t
235235
(** As {!small_int}, but each newly created generator starts with
236-
a list of corner cases before falling back on random generation. *)
236+
a list of corner cases before falling back on random generation.
237237
238+
Note that [small_int_corners ()] is stateful, meaning that once the list of
239+
corner cases has been emitted, subsequent calls will not reproduce them.
240+
As a consequence, in the following example, the first test fails with a
241+
counter example, whereas the second rerun does not:
242+
{[
243+
let gen = QCheck2.Gen.small_int_corners ()
244+
let t = QCheck2.Test.make ~name:"never max_int" gen (fun i -> i <> max_int)
245+
let _ = QCheck_base_runner.run_tests ~verbose:true [t;t]
246+
]}
247+
*)
238248

239249
val int32 : int32 t
240250
(** Generates uniform {!int32} values.
@@ -417,7 +427,7 @@ module Gen : sig
417427

418428
val make_primitive : gen : (Random.State.t -> 'a) -> shrink : ('a -> 'a Seq.t) -> 'a t
419429
(** [make_primitive ~gen ~shrink] creates a generator from a function [gen] that creates
420-
a random value (this function must only use the given {!Random.State.t} for randomness)
430+
a random value (this function must only use the given [Random.State.t] for randomness)
421431
and a function [shrink] that, given a value [a], returns a lazy list of
422432
"smaller" values (used when a test fails).
423433
@@ -624,6 +634,11 @@ module Gen : sig
624634
Does not shrink if the test fails on a grafted value.
625635
Shrinks towards [gen] otherwise.
626636
637+
Note that [graft_corners gen l ()] is stateful, meaning that once the
638+
elements of [l] have been emitted, subsequent calls will not reproduce
639+
them. It is therefore recommended that separate tests each use a fresh
640+
generator.
641+
627642
@since 0.6 *)
628643

629644
val int_pos_corners : int list
@@ -691,7 +706,7 @@ module Gen : sig
691706
val option : ?ratio:float -> 'a t -> 'a option t
692707
(** [option gen] is an [option] generator that uses [gen] when generating [Some] values.
693708
694-
Shrinks towards {!None} then towards shrinks of [gen].
709+
Shrinks towards [None] then towards shrinks of [gen].
695710
696711
@param ratio a float between [0.] and [1.] indicating the probability of a sample to be [Some _]
697712
rather than [None] (value is [0.85]).
@@ -782,7 +797,7 @@ module Gen : sig
782797
val flatten_opt : 'a t option -> 'a option t
783798
(** Generate an option from an optional generator.
784799
785-
Shrinks towards {!None} then shrinks on the value.
800+
Shrinks towards [None] then shrinks on the value.
786801
787802
@since 0.13 *)
788803

@@ -1272,16 +1287,16 @@ module Shrink : sig
12721287
*)
12731288

12741289
val int_towards : int -> int -> int Seq.t
1275-
(** {!number_towards} specialized to {!int}. *)
1290+
(** {!number_towards} specialized to [int]. *)
12761291

12771292
val int32_towards : int32 -> int32 -> int32 Seq.t
1278-
(** {!number_towards} specialized to {!int32}. *)
1293+
(** {!number_towards} specialized to [int32]. *)
12791294

12801295
val int64_towards : int64 -> int64 -> int64 Seq.t
1281-
(** {!number_towards} specialized to {!int64}. *)
1296+
(** {!number_towards} specialized to [int64]. *)
12821297

12831298
val float_towards : float -> float -> float Seq.t
1284-
(** {!number_towards} specialized to {!float}.
1299+
(** {!number_towards} specialized to [float].
12851300
12861301
There are various ways to shrink a float:
12871302
- try removing floating digits, i.e. towards integer values
@@ -2027,8 +2042,8 @@ val find_example_gen :
20272042
Below are the most common situations you may encounter:
20282043
- as shrinking is now integrated, several function arguments like [~shrink] or [~rev] have been removed: you
20292044
can remove such reverse functions, they will no longer be necessary.
2030-
- accessor functions like {!QCheck.gen} have been renamed to consistent names like {!get_gen}.
2031-
- {!QCheck.map_keep_input} has been removed: you can use {!map} directly.
2045+
- accessor functions like {!val:QCheck.gen} have been renamed to consistent names like {!Test.get_gen}.
2046+
- {!QCheck.map_keep_input} has been removed: you can use {!Gen.map} directly.
20322047
- {!Gen.t} is no longer public, it is now abstract: it is recommended to use
20332048
{{!section:Gen.composing_generators} generator composition} to make generators. {!Gen.make_primitive}
20342049
was added to create generators with finer control (in particular of shrinking).

src/ppx_deriving_qcheck/QCheck_generators.ml

+6-6
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ open Ppxlib
33
(** This module contains all generators from QCheck used to
44
derive a type declaration *)
55

6-
(** {2. Version} *)
6+
(** {2 Version} *)
77

88
type version = [`QCheck | `QCheck2]
99

@@ -28,11 +28,11 @@ let apply3 loc f a b c = [%expr [%e f] [%e a] [%e b] [%e c]]
2828

2929
let apply4 loc f a b c d = [%expr [%e f] [%e a] [%e b] [%e c] [%e d]]
3030

31-
(** {2. Type} *)
31+
(** {2 Type} *)
3232

3333
let ty version = Ldot (Ldot (Lident (to_module version), "Gen"), "t")
3434

35-
(** {2. Primitive generators} *)
35+
(** {2 Primitive generators} *)
3636

3737
let unit loc version = with_prefix_gen loc version "unit"
3838

@@ -62,7 +62,7 @@ let array ~loc ~version e =
6262
let gen = with_prefix_gen loc version "array" in
6363
apply1 loc gen e
6464

65-
(** {2. Generator combinators} *)
65+
(** {2 Generator combinators} *)
6666

6767
let pure ~loc ~version e =
6868
let gen = with_prefix_gen loc version "pure" in
@@ -101,7 +101,7 @@ let fix ~loc ~version e =
101101

102102
(** Observable generators *)
103103
module Observable = struct
104-
(** {2. Primitive generators} *)
104+
(** {2 Primitive generators} *)
105105
let unit loc version = with_prefix_obs loc version "unit"
106106

107107
let int loc version = with_prefix_obs loc version "int"
@@ -130,7 +130,7 @@ module Observable = struct
130130
let obs = with_prefix_obs loc version "array" in
131131
apply1 loc obs e
132132

133-
(** {2. Observable combinators} *)
133+
(** {2 Observable combinators} *)
134134
let pair ~loc ~version a b =
135135
let obs = with_prefix_obs loc version "pair" in
136136
apply2 loc obs a b

src/ppx_deriving_qcheck/tuple.ml

+1-1
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ open Ppxlib
22
module G = QCheck_generators
33
module O = G.Observable
44

5-
(** {1. Tuple } *)
5+
(** {1 Tuple } *)
66

77
(** This module implements nested tuples based on QCheck tuples generators (or observables):
88
- [Gen.pair]

src/runner/QCheck_base_runner.mli

+1-1
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ all rights reserved.
2525
will be 0 if all tests pass, 1 otherwise.
2626
2727
{!run_tests_main} can be used as a shortcut for that, also
28-
featuring command-line parsing (using {!Arg}) to activate
28+
featuring command-line parsing (using [Arg]) to activate
2929
verbose mode and others.
3030
*)
3131

0 commit comments

Comments
 (0)