Documentation
¶
Overview ¶
Package prop contains the most common implementations of a gopter.Prop.
Example (Invalidconcat) ¶
Example_invalidconcat demonstrates shrinking of string Kudos to @exarkun and @itamarst for finding this issue
package main import ( "strings" "unicode" "github.com/leanovate/gopter" "github.com/leanovate/gopter/gen" "github.com/leanovate/gopter/prop" ) func MisimplementedConcat(a, b string) string { if strings.IndexFunc(a, unicode.IsDigit) > 5 { return b } return a + b } // Example_invalidconcat demonstrates shrinking of string // Kudos to @exarkun and @itamarst for finding this issue func main() { parameters := gopter.DefaultTestParametersWithSeed(1234) // Example should generate reproducible results, otherwise DefaultTestParameters() will suffice properties := gopter.NewProperties(parameters) properties.Property("length is sum of lengths", prop.ForAll( func(a, b string) bool { return MisimplementedConcat(a, b) == a+b }, gen.Identifier(), gen.Identifier(), )) // When using testing.T you might just use: properties.TestingRun(t) properties.Run(gopter.ConsoleReporter(false)) }
Output: ! length is sum of lengths: Falsified after 17 passed tests. ARG_0: bahbxh6 ARG_0_ORIGINAL (2 shrinks): pkpbahbxh6 ARG_1: l ARG_1_ORIGINAL (1 shrinks): dl
Example (Quadratic) ¶
package main import ( "errors" "math" "github.com/leanovate/gopter" "github.com/leanovate/gopter/gen" "github.com/leanovate/gopter/prop" ) func solveQuadratic(a, b, c float64) (float64, float64, error) { if a == 0 { return 0, 0, errors.New("No solution") } v := b*b - 4*a*c if v < 0 { return 0, 0, errors.New("No solution") } v = math.Sqrt(v) return (-b + v) / 2 / a, (-b - v) / 2 / a, nil } func main() { parameters := gopter.DefaultTestParametersWithSeed(1234) // Example should generate reproducible results, otherwise DefaultTestParameters() will suffice properties := gopter.NewProperties(parameters) properties.Property("solve quadratic", prop.ForAll( func(a, b, c float64) bool { x1, x2, err := solveQuadratic(a, b, c) if err != nil { return true } return math.Abs(a*x1*x1+b*x1+c) < 1e-5 && math.Abs(a*x2*x2+b*x2+c) < 1e-5 }, gen.Float64(), gen.Float64(), gen.Float64(), )) properties.Property("solve quadratic with resonable ranges", prop.ForAll( func(a, b, c float64) bool { x1, x2, err := solveQuadratic(a, b, c) if err != nil { return true } return math.Abs(a*x1*x1+b*x1+c) < 1e-5 && math.Abs(a*x2*x2+b*x2+c) < 1e-5 }, gen.Float64Range(-1e8, 1e8), gen.Float64Range(-1e8, 1e8), gen.Float64Range(-1e8, 1e8), )) // When using testing.T you might just use: properties.TestingRun(t) properties.Run(gopter.ConsoleReporter(false)) }
Output: ! solve quadratic: Falsified after 0 passed tests. ARG_0: -1.4667384313385178e-05 ARG_0_ORIGINAL (187 shrinks): -1.0960555181801604e+51 ARG_1: 0 ARG_1_ORIGINAL (1 shrinks): -1.1203884793568249e+96 ARG_2: 6.481285637227244e+10 ARG_2_ORIGINAL (905 shrinks): 1.512647219322138e+281 + solve quadratic with resonable ranges: OK, passed 100 tests.
Example (Shrink) ¶
package main import ( "github.com/leanovate/gopter" "github.com/leanovate/gopter/gen" "github.com/leanovate/gopter/prop" ) func main() { parameters := gopter.DefaultTestParametersWithSeed(1234) // Example should generate reproducible results, otherwise DefaultTestParameters() will suffice properties := gopter.NewProperties(parameters) properties.Property("fail above 100", prop.ForAll( func(arg int64) bool { return arg <= 100 }, gen.Int64(), )) properties.Property("fail above 100 no shrink", prop.ForAllNoShrink( func(arg int64) bool { return arg <= 100 }, gen.Int64(), )) // When using testing.T you might just use: properties.TestingRun(t) properties.Run(gopter.ConsoleReporter(false)) }
Output: ! fail above 100: Falsified after 0 passed tests. ARG_0: 101 ARG_0_ORIGINAL (56 shrinks): 2041104533947223744 ! fail above 100 no shrink: Falsified after 0 passed tests. ARG_0: 6006156956070140861
Example (TimeGen) ¶
package main import ( "time" "github.com/leanovate/gopter" "github.com/leanovate/gopter/gen" "github.com/leanovate/gopter/prop" ) func main() { parameters := gopter.DefaultTestParametersWithSeed(1234) // Example should generate reproducible results, otherwise DefaultTestParameters() will suffice time.Local = time.UTC // Just for this example to generate reproducible results properties := gopter.NewProperties(parameters) properties.Property("time in range format parsable", prop.ForAll( func(actual time.Time) (bool, error) { str := actual.Format(time.RFC3339Nano) parsed, err := time.Parse(time.RFC3339Nano, str) return actual.Equal(parsed), err }, gen.TimeRange(time.Now(), time.Duration(100*24*365)*time.Hour), )) properties.Property("regular time format parsable", prop.ForAll( func(actual time.Time) (bool, error) { str := actual.Format(time.RFC3339Nano) parsed, err := time.Parse(time.RFC3339Nano, str) return actual.Equal(parsed), err }, gen.Time(), )) properties.Property("any time format parsable", prop.ForAll( func(actual time.Time) (bool, error) { str := actual.Format(time.RFC3339Nano) parsed, err := time.Parse(time.RFC3339Nano, str) return actual.Equal(parsed), err }, gen.AnyTime(), )) properties.Run(gopter.ConsoleReporter(false)) }
Output: + time in range format parsable: OK, passed 100 tests. + regular time format parsable: OK, passed 100 tests. ! any time format parsable: Error on property evaluation after 0 passed tests: parsing time "10000-01-01T00:00:00Z" as "2006-01-02T15:04:05.999999999Z07:00": cannot parse "0-01-01T00:00:00Z" as "-" ARG_0: 10000-01-01 00:00:00 +0000 UTC ARG_0_ORIGINAL (45 shrinks): 237903042092-02-10 19:15:18.148265469 +0000 UTC
Index ¶
- func ErrorProp(err error) gopter.Prop
- func ForAll(condition interface{}, gens ...gopter.Gen) gopter.Prop
- func ForAll1(gen gopter.Gen, check func(v interface{}) (interface{}, error)) gopter.Prop
- func ForAllNoShrink(condition interface{}, gens ...gopter.Gen) gopter.Prop
- func ForAllNoShrink1(gen gopter.Gen, check func(interface{}) (interface{}, error)) gopter.Prop
Examples ¶
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
func ErrorProp ¶
ErrorProp creates a property that will always fail with an error. Mostly used as a fallback when setup/initialization fails
func ForAll ¶
ForAll creates a property that requires the check condition to be true for all values, if the condition falsiies the generated values will be shrunk.
"condition" has to be a function with the same number of parameters as the provided generators "gens". The function may return a simple bool (true means that the condition has passed), a string (empty string means that condition has passed), a *PropResult, or one of former combined with an error.
func ForAllNoShrink ¶
ForAllNoShrink creates a property that requires the check condition to be true for all values. As the name suggests the generated values will not be shrunk if the condition falsiies.
"condition" has to be a function with the same number of parameters as the provided generators "gens". The function may return a simple bool (true means that the condition has passed), a string (empty string means that condition has passed), a *PropResult, or one of former combined with an error.
Types ¶
This section is empty.