Skip to content

Commit 626d283

Browse files
committed
Add smoke tests for PerasCertDiffusion
1 parent 411e98d commit 626d283

File tree

3 files changed

+134
-0
lines changed

3 files changed

+134
-0
lines changed

ouroboros-consensus/ouroboros-consensus.cabal

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -607,6 +607,7 @@ test-suite consensus-test
607607
Test.Consensus.MiniProtocol.ChainSync.CSJ
608608
Test.Consensus.MiniProtocol.ChainSync.Client
609609
Test.Consensus.MiniProtocol.LocalStateQuery.Server
610+
Test.Consensus.MiniProtocol.ObjectDiffusion.PerasCert.Smoke
610611
Test.Consensus.MiniProtocol.ObjectDiffusion.Smoke
611612
Test.Consensus.Peras.WeightSnapshot
612613
Test.Consensus.Util.MonadSTM.NormalForm

ouroboros-consensus/test/consensus-test/Main.hs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ import qualified Test.Consensus.MiniProtocol.BlockFetch.Client (tests)
1616
import qualified Test.Consensus.MiniProtocol.ChainSync.CSJ (tests)
1717
import qualified Test.Consensus.MiniProtocol.ChainSync.Client (tests)
1818
import qualified Test.Consensus.MiniProtocol.LocalStateQuery.Server (tests)
19+
import qualified Test.Consensus.MiniProtocol.ObjectDiffusion.PerasCert.Smoke (tests)
1920
import qualified Test.Consensus.MiniProtocol.ObjectDiffusion.Smoke (tests)
2021
import qualified Test.Consensus.Peras.WeightSnapshot (tests)
2122
import qualified Test.Consensus.Util.MonadSTM.NormalForm (tests)
@@ -39,6 +40,7 @@ tests =
3940
, Test.Consensus.MiniProtocol.ChainSync.CSJ.tests
4041
, Test.Consensus.MiniProtocol.ChainSync.Client.tests
4142
, Test.Consensus.MiniProtocol.ObjectDiffusion.Smoke.tests
43+
, Test.Consensus.MiniProtocol.ObjectDiffusion.PerasCert.Smoke.tests
4244
, Test.Consensus.MiniProtocol.LocalStateQuery.Server.tests
4345
, testGroup
4446
"Mempool"
Lines changed: 131 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,131 @@
1+
{-# LANGUAGE FlexibleContexts #-}
2+
{-# LANGUAGE FlexibleInstances #-}
3+
{-# LANGUAGE MultiParamTypeClasses #-}
4+
{-# LANGUAGE NamedFieldPuns #-}
5+
{-# LANGUAGE RankNTypes #-}
6+
{-# LANGUAGE TypeApplications #-}
7+
{-# LANGUAGE UndecidableInstances #-}
8+
{-# OPTIONS_GHC -Wno-orphans #-}
9+
10+
module Test.Consensus.MiniProtocol.ObjectDiffusion.PerasCert.Smoke (tests) where
11+
12+
import Control.Tracer (contramap, nullTracer)
13+
import Data.Functor.Identity (Identity (..))
14+
import qualified Data.List.NonEmpty as NE
15+
import Network.TypedProtocol.Driver.Simple (runPeer, runPipelinedPeer)
16+
import Ouroboros.Consensus.Block.SupportsPeras
17+
import Ouroboros.Consensus.MiniProtocol.ObjectDiffusion.ObjectPool.API
18+
import Ouroboros.Consensus.MiniProtocol.ObjectDiffusion.ObjectPool.PerasCert
19+
import Ouroboros.Consensus.Storage.PerasCertDB.API
20+
( AddPerasCertResult (..)
21+
, PerasCertDB
22+
, PerasCertTicketNo
23+
)
24+
import qualified Ouroboros.Consensus.Storage.PerasCertDB.API as PerasCertDB
25+
import qualified Ouroboros.Consensus.Storage.PerasCertDB.Impl as PerasCertDB
26+
import Ouroboros.Consensus.Util.IOLike
27+
import Ouroboros.Network.Block (Point (..), SlotNo (SlotNo), StandardHash)
28+
import Ouroboros.Network.Point (Block (Block), WithOrigin (..))
29+
import Ouroboros.Network.Protocol.ObjectDiffusion.Codec
30+
import Ouroboros.Network.Protocol.ObjectDiffusion.Inbound
31+
( objectDiffusionInboundPeerPipelined
32+
)
33+
import Ouroboros.Network.Protocol.ObjectDiffusion.Outbound (objectDiffusionOutboundPeer)
34+
import Test.Consensus.MiniProtocol.ObjectDiffusion.Smoke
35+
( ListWithUniqueIds (..)
36+
, ProtocolConstants
37+
, WithId
38+
, getId
39+
, prop_smoke_object_diffusion
40+
)
41+
import Test.QuickCheck
42+
import Test.Tasty
43+
import Test.Tasty.QuickCheck (testProperty)
44+
import Test.Util.TestBlock
45+
46+
tests :: TestTree
47+
tests =
48+
testGroup
49+
"ObjectDiffusion.PerasCert.Smoke"
50+
[ testProperty "PerasCertDiffusion smoke test" prop_smoke
51+
]
52+
53+
instance Arbitrary (Point TestBlock) where
54+
arbitrary =
55+
-- Sometimes pick the genesis point
56+
frequency
57+
[ (1, pure $ Point Origin)
58+
,
59+
( 4
60+
, do
61+
slotNo <- SlotNo <$> arbitrary
62+
hash <- TestHash . NE.fromList . getNonEmpty <$> arbitrary
63+
pure $ Point (At (Block slotNo hash))
64+
)
65+
]
66+
67+
instance Arbitrary (Point blk) => Arbitrary (PerasCert blk) where
68+
arbitrary = do
69+
pcCertRound <- PerasRoundNo <$> arbitrary
70+
pcCertBoostedBlock <- arbitrary
71+
pure $ PerasCert{pcCertRound, pcCertBoostedBlock}
72+
73+
instance WithId (PerasCert blk) PerasRoundNo where
74+
getId = pcCertRound
75+
76+
newCertDB :: (IOLike m, StandardHash blk) => [PerasCert blk] -> m (PerasCertDB m blk)
77+
newCertDB certs = do
78+
db <- PerasCertDB.openDB (PerasCertDB.PerasCertDbArgs @Identity nullTracer)
79+
mapM_
80+
( \cert -> do
81+
let validatedCert =
82+
ValidatedPerasCert
83+
{ vpcCert = cert
84+
, vpcCertBoost = boostPerCert
85+
}
86+
result <- PerasCertDB.addCert db validatedCert
87+
case result of
88+
AddedPerasCertToDB -> pure ()
89+
PerasCertAlreadyInDB -> throwIO (userError "Expected AddedPerasCertToDB, but cert was already in DB")
90+
)
91+
certs
92+
pure db
93+
94+
prop_smoke :: ProtocolConstants -> ListWithUniqueIds (PerasCert TestBlock) PerasRoundNo -> Property
95+
prop_smoke protocolConstants (ListWithUniqueIds certs) =
96+
prop_smoke_object_diffusion protocolConstants certs runOutboundPeer runInboundPeer mkPoolInterfaces
97+
where
98+
runOutboundPeer outbound outboundChannel tracer =
99+
runPeer
100+
((\x -> "Outbound (Client): " ++ show x) `contramap` tracer)
101+
codecObjectDiffusionId
102+
outboundChannel
103+
(objectDiffusionOutboundPeer outbound)
104+
>> pure ()
105+
runInboundPeer inbound inboundChannel tracer =
106+
runPipelinedPeer
107+
((\x -> "Inbound (Server): " ++ show x) `contramap` tracer)
108+
codecObjectDiffusionId
109+
inboundChannel
110+
(objectDiffusionInboundPeerPipelined inbound)
111+
>> pure ()
112+
mkPoolInterfaces ::
113+
forall m.
114+
IOLike m =>
115+
m
116+
( ObjectPoolReader PerasRoundNo (PerasCert TestBlock) PerasCertTicketNo m
117+
, ObjectPoolWriter PerasRoundNo (PerasCert TestBlock) m
118+
, m [PerasCert TestBlock]
119+
)
120+
mkPoolInterfaces = do
121+
outboundPool <- newCertDB certs
122+
inboundPool <- newCertDB []
123+
124+
let outboundPoolReader = makePerasCertPoolReaderFromCertDB outboundPool
125+
inboundPoolWriter = makePerasCertPoolWriterFromCertDB inboundPool
126+
getAllInboundPoolContent = do
127+
snap <- atomically $ PerasCertDB.getCertSnapshot inboundPool
128+
let rawContent = PerasCertDB.getCertsAfter snap (PerasCertDB.zeroPerasCertTicketNo)
129+
pure $ getPerasCert . fst <$> rawContent
130+
131+
return (outboundPoolReader, inboundPoolWriter, getAllInboundPoolContent)

0 commit comments

Comments
 (0)