Skip to content

Commit 4dc738d

Browse files
Add functions to UTxO interface. (#2067)
Uses `UTxO.foldMap`, `UTxO.map` and `UTxO.txOutputs` that will be the interface from cardano-api-10.17. Also adds `UTxO.null`. `UTxO.size`, `UTxO.totalValue` and `UTxO.lovelaceValue` that will be upstreamed.
1 parent 78ff0b5 commit 4dc738d

File tree

34 files changed

+109
-97
lines changed

34 files changed

+109
-97
lines changed

hydra-cardano-api/src/Cardano/Api/UTxO.hs

Lines changed: 25 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,11 +10,11 @@ module Cardano.Api.UTxO where
1010

1111
import Cardano.Api hiding (UTxO, toLedgerUTxO)
1212
import Cardano.Api qualified
13+
import Cardano.Api.Ledger (Coin)
1314
import Cardano.Api.Shelley (ReferenceScript (..))
1415
import Cardano.Ledger.Babbage ()
1516
import Data.Bifunctor (second)
1617
import Data.Coerce (coerce)
17-
import Data.Foldable qualified as F
1818
import Data.List qualified as List
1919
import Data.Map (Map)
2020
import Data.Map qualified as Map
@@ -36,8 +36,6 @@ newtype UTxO' out = UTxO
3636
deriving newtype
3737
( Eq
3838
, Show
39-
, Functor
40-
, Foldable
4139
, Semigroup
4240
, Monoid
4341
, ToJSON
@@ -88,12 +86,33 @@ difference a b = UTxO $ Map.difference (toMap a) (toMap b)
8886
-- | Check if the first 'UTxO' contains all **outputs** of the second 'UTxO'.
8987
-- First argument is the 'UTxO' to search in, second argument is the 'UTxO'
9088
-- to search for.
91-
containsOutputs :: Eq out => UTxO' out -> UTxO' out -> Bool
89+
containsOutputs :: UTxO -> UTxO -> Bool
9290
containsOutputs utxoForSearching utxo =
93-
let allOutputs = F.toList utxoForSearching
94-
expectedOutputs = F.toList utxo
91+
let allOutputs = txOutputs utxoForSearching
92+
expectedOutputs = txOutputs utxo
9593
in all (`elem` allOutputs) expectedOutputs
9694

95+
map :: (TxOut CtxUTxO Era -> TxOut CtxUTxO Era) -> UTxO -> UTxO
96+
map f = UTxO . Map.map f . toMap
97+
98+
foldMap :: Monoid m => (TxOut CtxUTxO Era -> m) -> UTxO -> m
99+
foldMap fn = Prelude.foldMap fn . toMap
100+
101+
txOutputs :: UTxO -> [TxOut CtxUTxO Era]
102+
txOutputs = Map.elems . toMap
103+
104+
null :: UTxO -> Bool
105+
null = Map.null . toMap
106+
107+
size :: UTxO -> Int
108+
size = Map.size . toMap
109+
110+
totalValue :: UTxO -> Value
111+
totalValue = Cardano.Api.UTxO.foldMap (\(TxOut _ (txOutValueToValue -> v) _ _) -> v)
112+
113+
totalLovelace :: UTxO -> Coin
114+
totalLovelace = selectLovelace . totalValue
115+
97116
-- * Type Conversions
98117

99118
-- | Transforms a UTxO containing tx outs from any era into Babbage era.

hydra-cluster/src/Hydra/Cluster/Faucet.hs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -87,7 +87,7 @@ findFaucetUTxO networkId backend lovelace = do
8787
(faucetVk, _) <- keysFor Faucet
8888
faucetUTxO <- Backend.queryUTxO backend [buildAddress faucetVk networkId]
8989
let foundUTxO = UTxO.filter (\o -> (selectLovelace . txOutValue) o >= lovelace) faucetUTxO
90-
when (null foundUTxO) $
90+
when (UTxO.null foundUTxO) $
9191
throwIO $
9292
FaucetHasNotEnoughFunds{faucetUTxO}
9393
pure foundUTxO
@@ -178,7 +178,7 @@ returnFundsToFaucet' tracer backend senderSk = do
178178
let senderVk = getVerificationKey senderSk
179179
utxo <- Backend.queryUTxOFor backend QueryTip senderVk
180180
returnAmount <-
181-
if null utxo
181+
if UTxO.null utxo
182182
then pure 0
183183
else retryOnExceptions tracer $ do
184184
let utxoValue = balance @Tx utxo

hydra-cluster/src/Hydra/Cluster/Scenarios.hs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -744,7 +744,7 @@ singlePartyUsesWithdrawZeroTrick tracer workDir backend hydraScriptsTxId =
744744
recomputeIntegrityHash pparams [PlutusV3] $
745745
toLedgerTx tx
746746
& bodyTxL . collateralInputsTxBodyL .~ Set.map toLedgerTxIn (UTxO.inputSet utxoToCommit)
747-
& bodyTxL . totalCollateralTxBodyL .~ SJust (foldMap (selectLovelace . txOutValue) utxoToCommit)
747+
& bodyTxL . totalCollateralTxBodyL .~ SJust (UTxO.totalLovelace utxoToCommit)
748748
& bodyTxL . withdrawalsTxBodyL .~ Withdrawals (Map.singleton rewardAccount 0)
749749
& witsTxL . rdmrsTxWitsL .~ Redeemers (Map.singleton (ConwayRewarding $ AsIx 0) (redeemer, exUnits))
750750
& witsTxL . scriptTxWitsL .~ Map.singleton scriptHash script

hydra-cluster/src/Hydra/Generator.hs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -134,7 +134,7 @@ generateDemoUTxODataset ::
134134
generateDemoUTxODataset network nodeSocket faucetSk nClients nTxs = do
135135
-- Query available funds
136136
faucetUTxO <- queryUTxOFor network nodeSocket QueryTip faucetVk
137-
let (Coin fundsAvailable) = foldMap (selectLovelace . txOutValue) faucetUTxO
137+
let (Coin fundsAvailable) = UTxO.totalLovelace faucetUTxO
138138
-- Generate client datasets
139139
allPaymentKeys <- generate $ replicateM nClients genSigningKey
140140
clientFunds <- generate $ genClientFunds allPaymentKeys fundsAvailable

hydra-cluster/test/Test/DirectChainSpec.hs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -157,7 +157,7 @@ spec = around (showLogsOnFailure "DirectChainSpec") $ do
157157
-- Expect that Alice got her committed value back to her
158158
-- external address
159159
utxo <- Backend.queryUTxO backend [aliceExternalAddress]
160-
let aliceValues = txOutValue <$> toList utxo
160+
let aliceValues = txOutValue <$> UTxO.txOutputs utxo
161161
aliceValues `shouldContain` [lovelaceToValue aliceCommitment]
162162

163163
it "cannot abort a non-participating head" $ \tracer ->

hydra-cluster/test/Test/GeneratorSpec.hs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ module Test.GeneratorSpec where
55
import Hydra.Prelude
66
import Test.Hydra.Prelude
77

8+
import Cardano.Api.UTxO qualified as UTxO
89
import Data.Text (unpack)
910
import Hydra.Cardano.Api (LedgerEra, UTxO, prettyPrintJSON, utxoFromTx)
1011
import Hydra.Chain.ChainState (ChainSlot (ChainSlot))
@@ -45,7 +46,7 @@ prop_keepsUTxOConstant =
4546
\Dataset{fundingTransaction, clientDatasets = [ClientDataset{txSequence}]} ->
4647
let initialUTxO = utxoFromTx fundingTransaction
4748
finalUTxO = foldl' (apply defaultGlobals ledgerEnv) initialUTxO txSequence
48-
in length finalUTxO == length initialUTxO
49+
in length (UTxO.txOutputs finalUTxO) == length (UTxO.txOutputs initialUTxO)
4950
& counterexample ("transactions: " <> prettyJSONString txSequence)
5051
& counterexample ("utxo: " <> prettyJSONString initialUTxO)
5152
& counterexample ("funding tx: " <> prettyJSONString fundingTransaction)

hydra-cluster/test/Test/Hydra/Cluster/FaucetSpec.hs

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,10 @@ module Test.Hydra.Cluster.FaucetSpec where
55
import Hydra.Prelude
66
import Test.Hydra.Prelude
77

8+
import Cardano.Api.UTxO qualified as UTxO
89
import CardanoNode (withCardanoNodeDevnet)
910
import Control.Concurrent.Async (replicateConcurrently)
10-
import Hydra.Cardano.Api (Coin (..), selectLovelace, txOutValue)
11+
import Hydra.Cardano.Api (Coin (..), selectLovelace)
1112
import Hydra.Chain.Backend qualified as Backend
1213
import Hydra.Chain.CardanoClient (QueryPoint (..))
1314
import Hydra.Chain.Direct (DirectBackend (..))
@@ -36,7 +37,7 @@ spec =
3637
vk <- generate genVerificationKey
3738
seedFromFaucet backend vk 1_000_000 tracer
3839
-- 10 unique outputs
39-
length (fold utxos) `shouldBe` 10
40+
UTxO.size (fold utxos) `shouldBe` 10
4041

4142
describe "returnFundsToFaucet" $ do
4243
it "does nothing if nothing to return" $ \(tracer, backend) -> do
@@ -53,13 +54,13 @@ spec =
5354
returnFundsToFaucet tracer backend actor
5455
remaining <- Backend.queryUTxOFor backend QueryTip vk
5556
finalFaucetFunds <- Backend.queryUTxOFor backend QueryTip faucetVk
56-
foldMap txOutValue remaining `shouldBe` mempty
57+
UTxO.totalValue remaining `shouldBe` mempty
5758

5859
-- check the faucet has one utxo extra in the end
59-
length finalFaucetFunds `shouldBe` length initialFaucetFunds + 1
60+
UTxO.size finalFaucetFunds `shouldBe` UTxO.size initialFaucetFunds + 1
6061

61-
let initialFaucetValue = selectLovelace (foldMap txOutValue initialFaucetFunds)
62-
let finalFaucetValue = selectLovelace (foldMap txOutValue finalFaucetFunds)
62+
let initialFaucetValue = selectLovelace (UTxO.totalValue initialFaucetFunds)
63+
let finalFaucetValue = selectLovelace (UTxO.totalValue finalFaucetFunds)
6364
let difference = initialFaucetValue - finalFaucetValue
6465
-- difference between starting faucet amount and final one should
6566
-- just be the amount of paid fees
@@ -77,4 +78,4 @@ spec =
7778
-- it squashed the UTxO
7879
utxoAfter <- Backend.queryUTxOFor backend QueryTip vk
7980

80-
length utxoAfter `shouldBe` 1
81+
UTxO.size utxoAfter `shouldBe` 1

hydra-node/bench/tx-cost/TxCost.hs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -102,7 +102,7 @@ computeCommitCost = do
102102
Right tx ->
103103
case checkSizeAndEvaluate tx (utxo <> knownUtxo) of
104104
Just (txSize, memUnit, cpuUnit, minFee) ->
105-
pure $ Just (NumUTxO $ length utxo, txSize, memUnit, cpuUnit, minFee)
105+
pure $ Just (NumUTxO $ UTxO.size utxo, txSize, memUnit, cpuUnit, minFee)
106106
Nothing ->
107107
pure Nothing
108108

@@ -309,4 +309,4 @@ serializedSize :: UTxO -> Natural
309309
serializedSize =
310310
fromIntegral
311311
. lengthOfByteString
312-
. foldMap (serialiseData . toBuiltinData . fromJust . toPlutusTxOut)
312+
. UTxO.foldMap (serialiseData . toBuiltinData . fromJust . toPlutusTxOut)

hydra-node/src/Hydra/Chain/Blockfrost/Client.hs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -547,6 +547,6 @@ awaitUTxO networkId addresses txid i = do
547547
Left _e -> liftIO (threadDelay 1) >> go (n - 1)
548548
Right utxo' ->
549549
let wantedUTxO = UTxO.fromList $ List.filter (\(TxIn txid' _, _) -> txid' == txid) (UTxO.toList utxo')
550-
in if null wantedUTxO
550+
in if UTxO.null wantedUTxO
551551
then liftIO (threadDelay 1) >> go (n - 1)
552552
else pure utxo'

hydra-node/src/Hydra/Chain/CardanoClient.hs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -122,7 +122,7 @@ awaitTransaction networkId socket tx =
122122
ins = keys (UTxO.toMap $ utxoFromTx tx)
123123
go = do
124124
utxo <- queryUTxOByTxIn networkId socket QueryTip ins
125-
if null utxo
125+
if UTxO.null utxo
126126
then go
127127
else pure utxo
128128

0 commit comments

Comments
 (0)