
ClockTest.pudu
Pudu64 lines3.2 KB
1/** @Test.Clock.Suite — manual and system clocks, and randomizers */2module PuduLangResilience.ClockTest34import Std.Concurrent.Cancel as Cancel5import Std.Io as Io6import Std.Test as Test7import PuduLangResilience.Clock as Clock8import PuduLangResilience.Randomizer as Randomizer91011fn draws(source: &Randomizer.Randomizer, bound: Int, count: Int) -> Array[Int] {12 var drawn: Array[Int] = []13 while drawn.length() < count { drawn = drawn.push(Randomizer.below(source, bound)) }14 drawn15}161718fn main() -> Int {19 let manual = Clock.manual(100)20 let clock = Clock.ofManual(&manual)21 let startedAt = Clock.now(&clock)22 let slept = Clock.sleep(&clock, 50, &Cancel.token())23 let negative = Clock.sleep(&clock, -5, &Cancel.token())24 Clock.advance(&manual, 10)25 Clock.advance(&manual, -10)26 let stopped = Cancel.token()27 let _fired = Cancel.cancel(&stopped, "no")28 let refused = Clock.sleep(&clock, 30, &stopped)29 let system = Clock.system()30 let before = Clock.now(&system)31 let systemSlept = Clock.sleep(&system, 5, &Cancel.token())32 let after = Clock.now(&system)33 let seeded = draws(&Randomizer.seeded(42), 100, 20)34 let again = draws(&Randomizer.seeded(42), 100, 20)35 let other = draws(&Randomizer.seeded(-7), 100, 20)36 let live = Randomizer.system()37 let fixedHalf = Randomizer.fixed(0.5d)38 let checks = Test.suite("Clock", &[39 Test.equals("a manual clock starts where told", &startedAt, &100),40 Test.equals("sleeping on a manual clock advances it", &(slept, Clock.now(&clock)), &(Ok(()), 160)),41 Test.equals("a negative sleep is recorded as none", &(negative, Clock.sleeps(&manual)), &(Ok(()), [50, 0])),42 Test.that("a fired token refuses to sleep", match refused { case Err(_) => true case Ok(_) => false }),43 Test.equals("a refused sleep is not recorded", &Clock.sleeps(&manual).length(), &2),44 Test.that("the system clock waits", systemSlept == Ok(()) && after - before >= 5),45 Test.equals("a seed repeats its sequence", &seeded, &again),46 Test.differs("different seeds differ", &seeded, &other),47 Test.all("draws stay below their bound", &draws(&live, 7, 200), |drawn: Int| drawn >= 0 && drawn < 7),48 Test.equals("a bound below one draws zero", &Randomizer.below(&live, 0), &0),49 Test.equals("a fixed ratio draws that share of the bound", &draws(&fixedHalf, 10, 2), &[5, 5]),50 Test.equals("a fixed ratio is clamped", &(Randomizer.below(&Randomizer.fixed(-1d), 10), Randomizer.below(&Randomizer.fixed(2d), 10)), &(0, 9)),51 Test.equals("a fraction is parts of the scale", &Randomizer.fraction(&fixedHalf), &(Randomizer.SCALE / 2)),52 Test.that("a unit draw is a fraction of one", Randomizer.unit(&fixedHalf) == 0.5),53 Test.that("a rate of one always holds", Randomizer.chance(&Randomizer.fixed(0.999999d), 1d)),54 Test.not("a rate of zero never holds", Randomizer.chance(&Randomizer.fixed(0d), 0d)),55 Test.that("a draw below the rate holds", Randomizer.chance(&fixedHalf, 0.500001d)),56 Test.not("a draw at the rate does not hold", Randomizer.chance(&fixedHalf, 0.5d))57 ])58 let ran = Test.run(&checks)59 for failure in Test.failuresOf(&ran) {60 let _reported = Io.writeErrorLine(failure)61 }62 Test.report(&ran)63}64