for all c or all code ode ther here exist p e exist
play

For All C or All Code ode, , Ther here Exist P e Exist Proper - PowerPoint PPT Presentation

For All C or All Code ode, , Ther here Exist P e Exist Proper operties t ties to be Check o be Checked ed (or or, r , random t andom testing with FsCheck) esting with FsCheck) Paulmichael Blasuc aulmichael Blasucci, S ci, Senior S


  1. For All C or All Code ode, , Ther here Exist P e Exist Proper operties t ties to be Check o be Checked ed (or or, r , random t andom testing with FsCheck) esting with FsCheck) Paulmichael Blasuc aulmichael Blasucci, S ci, Senior S enior Sof oftwar are E e Engineer a ngineer at t twitter.com/pblasucci github.com/pblasucci linkedin.com/in/pblasucci

  2. Random andom Testing esting “Proper'es ¡are ¡described ¡as ¡… ¡ func%ons , ¡and ¡can ¡ be ¡ automa%cally ¡tested ¡on ¡random ¡input ... ¡[or] ¡ custom ¡test ¡data ¡generators.” from ¡ICFP’00 ¡– ¡Claessen, ¡Hughes ¡

  3. From Unit om Unit Testing esting… … To P o Proper operty y Testing esting [<Test>] ¡ [<Property>] ¡ let ¡``clone ¡returns ¡a ¡new ¡instance`` ¡() ¡ ¡ let ¡``not ¡equal ¡to ¡original`` ¡data ¡= ¡ ¡ ¡ use ¡msg1 ¡= ¡ new ¡Message("test"B) ¡ ¡ ¡ use ¡msg1 ¡= ¡ new ¡Message ¡(data) ¡ ¡ ¡ use ¡msg2 ¡= ¡Message.clone ¡msg1 ¡ ¡ ¡ use ¡msg2 ¡= ¡Message.clone ¡msg1 ¡ ¡ ¡Assert.That ¡(msg2,Is.Not.EqualTo ¡msg1) ¡ ¡ ¡ ¡msg1 ¡<> ¡msg2 ¡ ¡ ` ¡

  4. FsCheck: P FsCheck: Proper operties ties open ¡ fszmq ¡ open ¡fszmq.Message ¡ ¡ let ¡equalContent ¡(msg1:Message) ¡(msg2:Message) ¡= ¡ ¡ ¡ ¡size ¡msg1 ¡= ¡size ¡msg2 ¡&& ¡data ¡msg1 ¡= ¡data ¡msg2 ¡ ¡ let ¡``clone ¡is ¡idempotent`` ¡(msg:Message) ¡= ¡ ¡ ¡ use ¡once ¡ ¡= ¡clone ¡msg ¡ ¡ ¡ use ¡twice ¡= ¡msg ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡|> ¡clone ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡|> ¡clone ¡ ¡ ¡twice ¡|> ¡equalContent ¡once ¡ ¡ ¡

  5. let ¡ ``copy ¡alters ¡target ¡but ¡not ¡source`` ¡msg1 ¡msg2 ¡= ¡ ¡ ¡let ¡ data1,data2 ¡= ¡data ¡msg1,data ¡msg2 ¡ FsCheck: P FsCheck: Proper operties ties ¡ ¡copy ¡msg1 ¡msg2 ¡ ¡ ¡(data ¡msg1 ¡= ¡data1) ¡&& ¡(data ¡msg2 ¡<> ¡data2) ¡ Combining ¡proper'es ¡(naïvely) ¡

  6. let ¡ ``copy ¡alters ¡target ¡but ¡not ¡source`` ¡msg1 ¡msg2 ¡= ¡ ¡ ¡let ¡ data1,data2 ¡= ¡data ¡msg1,data ¡msg2 ¡ FsCheck: P FsCheck: Proper operties ties ¡ ¡copy ¡msg1 ¡msg2 ¡ ¡ ¡(data ¡msg1 ¡= ¡ ¡data1 ¡|@ ¡"source") ¡ ¡ Combining ¡and ¡ Labeling ¡proper'es ¡ ¡ ¡.&. ¡ ¡ ¡ ¡(data ¡msg2 ¡<> ¡data2 ¡|@ ¡"target") ¡

  7. let ¡ ``copy ¡alters ¡target ¡but ¡not ¡source`` ¡msg1 ¡msg2 ¡= ¡ ¡ ¡ (data ¡msg1 ¡<> ¡data ¡msg2) ¡==> ¡ ¡ FsCheck: P FsCheck: Proper operties ties ¡ ¡ ¡ ¡let ¡ data1,data2 ¡= ¡data ¡msg1, ¡data ¡msg2 ¡ ¡ ¡ ¡ ¡copy ¡msg1 ¡msg2 ¡ Condi-onal ¡proper'es ¡ ¡ ¡ ¡ ¡(data ¡msg1 ¡= ¡data1 ¡|@ ¡"source") ¡ ¡ ¡ ¡ ¡ ¡.&. ¡ ¡ ¡ ¡ ¡ ¡(data ¡msg2 ¡<> ¡data2 ¡|@ ¡"target") ¡

  8. Randomly Gener andomly Generated ed Versions ersions 36% ¡ 16% ¡ 8% ¡ 8% ¡ 8% ¡ 4% ¡ 4% ¡ 4% ¡ 4% ¡ 4% ¡ 4% ¡ FsCheck FsCheck: Gener : Generation tion distribu;on ¡of ¡random ¡data ¡using ¡a ¡custom ¡generator ¡

  9. FsCheck: Gener FsCheck: Generation tion type ¡Generators ¡= ¡ ¡ ¡ ¡static ¡member ¡ Version ¡= ¡ ¡ ¡ ¡ ¡ let ¡unknown ¡= ¡Gen.constant ¡Unknown ¡ ¡ ¡ ¡ ¡ let ¡version ¡= ¡Arb.generate<NonNegativeInt> ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡|> ¡Gen.three ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡|> ¡Gen.map ¡( fun ¡(NonNegativeInt ¡m ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡,NonNegativeInt ¡n ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡,NonNegativeInt ¡r) ¡ -­‑> ¡ fszmq.Version ¡(m,n,r)) ¡ ¡ ¡ ¡ ¡[ ¡( 1 ,unknown); ¡( 2 ,version) ¡] ¡ ¡ ¡ ¡ ¡|> ¡Gen.frequency ¡ ¡ ¡ ¡ ¡|> ¡Arb.fromGen ¡ ¡

  10. module ¡Z85Encoder ¡= ¡ ¡ ¡ let ¡``encode,decode ¡are ¡duals`` ¡(data:byte[]) ¡= ¡ FsCheck: Gener FsCheck: Generation tion ¡ ¡ ¡ ¡data|> ¡Z85.encode ¡|> ¡Z85.decode ¡= ¡data ¡ Expressing ¡implicit ¡business ¡rules ¡

  11. module ¡Z85Encoder ¡= ¡ ¡ ¡ let ¡``encode,decode ¡are ¡duals`` ¡(Mod4Bytes ¡data) ¡= ¡ FsCheck: Gener FsCheck: Generation tion ¡ ¡ ¡ ¡data|> ¡Z85.encode ¡|> ¡Z85.decode ¡= ¡data ¡ Expressing ¡implicit ¡business ¡rules ¡ “Z85 ¡… ¡takes ¡a ¡binary ¡frame ¡and ¡encodes ¡it ¡ as ¡a ¡printable ¡ASCII ¡string, ¡or ¡takes ¡an ¡ASCII ¡ encoded ¡string ¡and ¡decodes ¡it ¡into ¡a ¡binary ¡ frame. ¡ The ¡ binary ¡frame ¡SHALL ¡have ¡a ¡length ¡that ¡is ¡ type ¡ Mod4Bytes ¡= ¡Mod4Bytes ¡ of ¡ byte[] ¡ divisible ¡by ¡4 ¡with ¡no ¡remainder . ¡The ¡ string ¡ ¡ frame ¡SHALL ¡have ¡a ¡length ¡that ¡is ¡ divisible ¡by ¡ // ¡... ¡elsewhere ¡... ¡ 5 ¡with ¡no ¡remainder .” ¡ ¡ ¡ static ¡member ¡ Mod4Bytes ¡= ¡ ¡ ¡ let ¡g ¡= ¡Arb.generate<byte[]> ¡ from ¡Z85 ¡RFC ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡|> ¡Gen.suchThat ¡( fun ¡b ¡ -­‑> ¡ b ¡<> ¡null ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡&& ¡b.Length ¡% ¡4 ¡= ¡0) ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡|> ¡Gen.map ¡Mod4Bytes ¡ ¡ ¡ let ¡s ¡(Mod4Bytes ¡bytes) ¡= ¡bytes ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡|> ¡Arb.shrink ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡ ¡|> ¡Seq.map ¡Mod4Bytes ¡ ¡ ¡Arb.fromGenShrink ¡(g,s) ¡

  12. Obser Observed Arr ed Array Siz y Sizes (in B es (in Byt ytes) es) 30% ¡ Tiny ¡(0 ¡.. ¡4 ¡bytes) ¡ 25% ¡ Small ¡(8 ¡.. ¡20 ¡bytes) ¡ Medium ¡(24 ¡.. ¡60 ¡bytes) ¡ 20% ¡ Large ¡(64 ¡.. ¡∞ ¡bytes) ¡ 15% ¡ 10% ¡ 5% ¡ 0% ¡ 0 ¡ 4 ¡ 8 ¡ 12 ¡ 16 ¡ 20 ¡ 24 ¡ 28 ¡ 32 ¡ 36 ¡ 40 ¡ 44 ¡ 48 ¡ 52 ¡ 60 ¡ 64 ¡ 68 ¡ 72 ¡ 76 ¡ FsCheck: Obser FsCheck : Observations tions distribu;on ¡of ¡randomly ¡generated ¡test ¡inputs ¡

  13. FsCheck: Obser FsCheck: Observations tions let ¡``encode,decode ¡are ¡duals`` ¡(Mod4Binary ¡value) ¡= ¡ ¡ ¡ ¡(value ¡|> ¡Z85.encode ¡|> ¡Z85.decode ¡= ¡value) ¡ ¡ ¡ ¡|> ¡Prop.trivial ¡(Array.isEmpty ¡value) ¡ ¡ let ¡``encode,decode ¡are ¡duals`` ¡(Mod4Binary ¡value) ¡= ¡ ¡ ¡ ¡(value ¡|> ¡Z85.encode ¡|> ¡Z85.decode ¡= ¡value) ¡ ¡ ¡ ¡|> ¡Prop.classify ¡(large ¡ ¡value) ¡"large ¡(64 ¡.. ¡∞)” ¡ ¡ ¡|> ¡Prop.classify ¡(medium ¡value) ¡"medium ¡(24 ¡.. ¡60)” ¡ ¡ ¡|> ¡Prop.classify ¡(small ¡ ¡value) ¡"small ¡(8 ¡.. ¡20)” ¡ ¡ ¡|> ¡Prop.classify ¡(tiny ¡ ¡ ¡value) ¡"tiny ¡(0 ¡.. ¡4)" ¡

  14. FsCheck: Obser FsCheck: Observations tions let ¡``encode,decode ¡are ¡duals`` ¡(Mod4Binary ¡value) ¡= ¡ ¡ ¡ ¡(value ¡|> ¡Z85.encode ¡|> ¡Z85.decode ¡= ¡value) ¡ ¡ ¡ ¡|> ¡Prop.collect ¡(Array.length ¡value) ¡ ¡ let ¡``encode,decode ¡are ¡duals`` ¡(Mod4Binary ¡value) ¡= ¡ ¡ ¡ ¡(value ¡|> ¡Z85.encode ¡|> ¡Z85.decode ¡= ¡value) ¡ ¡ ¡ ¡|> ¡Prop.trivial ¡ ¡ ¡(Array.isEmpty ¡value) ¡ ¡ ¡|> ¡Prop.classify ¡ ¡(large ¡ ¡value) ¡“large ¡(64 ¡.. ¡∞)” ¡ ¡ ¡|> ¡Prop.classify ¡ ¡(medium ¡value) ¡“medium ¡(24 ¡.. ¡60)” ¡ ¡ ¡|> ¡Prop.classify ¡ ¡(small ¡ ¡value) ¡“small ¡(8 ¡.. ¡20)” ¡ ¡ ¡|> ¡Prop.classify ¡ ¡(tiny ¡ ¡ ¡value) ¡“tiny ¡(0 ¡.. ¡4)” ¡ ¡ ¡|> ¡Prop.collect ¡ ¡ ¡(Array.length ¡value) ¡

Download Presentation
Download Policy: The content available on the website is offered to you 'AS IS' for your personal information and use only. It cannot be commercialized, licensed, or distributed on other websites without prior consent from the author. To download a presentation, simply click this link. If you encounter any difficulties during the download process, it's possible that the publisher has removed the file from their server.

Recommend


More recommend