From 1b44081880159cf1c9042c983d12fd9a5fa2e030 Mon Sep 17 00:00:00 2001 From: Mike Hearn Date: Thu, 12 Nov 2015 23:36:46 +0100 Subject: [PATCH] Minor: tweak the cash/amount API --- src/contracts/Cash.kt | 11 +++++++---- src/contracts/ComedyPaper.kt | 6 +----- src/core/ContractsDSL.kt | 5 +++-- tests/contracts/ComedyPaperTests.kt | 2 +- 4 files changed, 12 insertions(+), 12 deletions(-) diff --git a/src/contracts/Cash.kt b/src/contracts/Cash.kt index 999f5c1aa6..9117fcc071 100644 --- a/src/contracts/Cash.kt +++ b/src/contracts/Cash.kt @@ -2,6 +2,7 @@ package contracts import core.* import java.security.PublicKey +import java.util.* ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // @@ -91,7 +92,7 @@ object Cash : Contract { val outputs = cashOutputs.filter { it.deposit == deposit } outputsLeft -= outputs.size - val inputAmount = inputs.map { it.amount }.sum() + val inputAmount = inputs.map { it.amount }.sumOrThrow() val outputAmount = outputs.map { it.amount }.sumOrZero(currency) val issuerCommand = args.select(institution = deposit.institution).singleOrNull() @@ -164,7 +165,7 @@ object Cash : Contract { val states = gathered.groupBy { it.deposit }.map { val (deposit, coins) = it - val totalAmount = coins.map { it.amount }.sum() + val totalAmount = coins.map { it.amount }.sumOrThrow() State(deposit, totalAmount, to) } @@ -187,5 +188,7 @@ object Cash : Contract { } // Small DSL extension. -fun Iterable.sumCashBy(owner: PublicKey) = filterIsInstance().filter { it.owner == owner }.map { it.amount }.sum() -fun Iterable.sumCash() = filterIsInstance().map { it.amount }.sum() +fun Iterable.sumCashBy(owner: PublicKey) = filterIsInstance().filter { it.owner == owner }.map { it.amount }.sumOrThrow() +fun Iterable.sumCash() = filterIsInstance().map { it.amount }.sumOrThrow() +fun Iterable.sumCashOrNull() = filterIsInstance().map { it.amount }.sumOrNull() +fun Iterable.sumCashOrZero(currency: Currency) = filterIsInstance().map { it.amount }.sumOrZero(currency) diff --git a/src/contracts/ComedyPaper.kt b/src/contracts/ComedyPaper.kt index dc2dfd6082..bb385395c6 100644 --- a/src/contracts/ComedyPaper.kt +++ b/src/contracts/ComedyPaper.kt @@ -61,11 +61,7 @@ object ComedyPaper : Contract { } is Commands.Redeem -> requireThat { - val received = try { - outStates.sumCash() - } catch (e: UnsupportedOperationException) { - throw IllegalStateException("invalid cash outputs") - } + val received = outStates.sumCashOrNull() ?: throw IllegalStateException("no cash being redeemed") // Do we need to check the signature of the issuer here too? "the paper must have matured" by (input.maturityDate < time) "the received amount equals the face value" by (received == input.faceValue) diff --git a/src/core/ContractsDSL.kt b/src/core/ContractsDSL.kt index 8794887ffc..d452d0a208 100644 --- a/src/core/ContractsDSL.kt +++ b/src/core/ContractsDSL.kt @@ -110,8 +110,9 @@ data class Amount(val pennies: Int, val currency: Currency) : Comparable } // Note: this will throw an exception if the iterable is empty. -fun Iterable.sum() = reduce { left, right -> left + right } -fun Iterable.sumOrZero(currency: Currency) = if (iterator().hasNext()) sum() else Amount(0, currency) +fun Iterable.sumOrNull() = if (!iterator().hasNext()) null else sumOrThrow() +fun Iterable.sumOrThrow() = reduce { left, right -> left + right } +fun Iterable.sumOrZero(currency: Currency) = if (iterator().hasNext()) sumOrThrow() else Amount(0, currency) // TODO: Think about how positive-only vs positive-or-negative amounts can be represented in the type system. // endregion diff --git a/tests/contracts/ComedyPaperTests.kt b/tests/contracts/ComedyPaperTests.kt index 40c03dc9d7..00fb615d8a 100644 --- a/tests/contracts/ComedyPaperTests.kt +++ b/tests/contracts/ComedyPaperTests.kt @@ -41,7 +41,7 @@ class ComedyPaperTests { arg(DUMMY_PUBKEY_2, MINI_CORP_KEY) { ComedyPaper.Commands.Redeem() } // No cash output, can't redeem like that! - this.rejects("invalid cash outputs") + this.rejects("no cash being redeemed") input { CASH_3 } output { CASH_2 }