Skip to content

Commit

Permalink
Merge PR cosmos#3826: Port IsAllGT from safe-coins PR
Browse files Browse the repository at this point in the history
  • Loading branch information
jackzampolin authored Mar 8, 2019
2 parents 714168f + 862cc43 commit f37ab4a
Show file tree
Hide file tree
Showing 2 changed files with 38 additions and 10 deletions.
37 changes: 34 additions & 3 deletions types/coin.go
Original file line number Diff line number Diff line change
Expand Up @@ -269,6 +269,23 @@ func (coins Coins) safeAdd(coinsB Coins) Coins {
}
}

// ContainsDenomsOf returns true if coinsB' denom set
// is subset of the receiver's denoms.
func (coins Coins) ContainsDenomsOf(coinsB Coins) bool {
// more denoms in B than in receiver
if len(coinsB) > len(coins) {
return false
}

for _, coinB := range coinsB {
if coins.AmountOf(coinB.Denom).IsZero() {
return false
}
}

return true
}

// Sub subtracts a set of coins from another.
//
// e.g.
Expand Down Expand Up @@ -297,12 +314,26 @@ func (coins Coins) SafeSub(coinsB Coins) (Coins, bool) {
// IsAllGT returns true if for every denom in coins, the denom is present at a
// greater amount in coinsB.
func (coins Coins) IsAllGT(coinsB Coins) bool {
diff, _ := coins.SafeSub(coinsB)
if len(diff) == 0 {
if len(coins) == 0 {
return false
}

return diff.IsAllPositive()
if len(coinsB) == 0 {
return true
}

if !coins.ContainsDenomsOf(coinsB) {
return false
}

for _, coinB := range coinsB {
amountA, amountB := coins.AmountOf(coinB.Denom), coinB.Amount
if !amountA.GT(amountB) {
return false
}
}

return true
}

// IsAllGTE returns true iff for every denom in coins, the denom is present at
Expand Down
11 changes: 4 additions & 7 deletions types/coin_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -276,10 +276,7 @@ func TestCoins(t *testing.T) {
mixedCase3 := Coins{
{"gAs", NewInt(1)},
}
empty := Coins{
{"gold", NewInt(0)},
}
null := Coins{}
empty := NewCoins()
badSort1 := Coins{
{"tree", NewInt(1)},
{"gas", NewInt(1)},
Expand Down Expand Up @@ -312,7 +309,7 @@ func TestCoins(t *testing.T) {
assert.False(t, mixedCase2.IsValid(), "First Coins denoms contain upper case characters")
assert.False(t, mixedCase3.IsValid(), "Single denom in Coins contains upper case characters")
assert.True(t, good.IsAllPositive(), "Expected coins to be positive: %v", good)
assert.False(t, null.IsAllPositive(), "Expected coins to not be positive: %v", null)
assert.False(t, empty.IsAllPositive(), "Expected coins to not be positive: %v", empty)
assert.True(t, good.IsAllGTE(empty), "Expected %v to be >= %v", good, empty)
assert.False(t, good.IsAllLT(empty), "Expected %v to be < %v", good, empty)
assert.True(t, empty.IsAllLT(good), "Expected %v to be < %v", empty, good)
Expand All @@ -331,7 +328,7 @@ func TestCoinsGT(t *testing.T) {
assert.True(t, Coins{{testDenom1, one}}.IsAllGT(Coins{}))
assert.False(t, Coins{{testDenom1, one}}.IsAllGT(Coins{{testDenom1, one}}))
assert.False(t, Coins{{testDenom1, one}}.IsAllGT(Coins{{testDenom2, one}}))
assert.True(t, Coins{{testDenom1, one}, {testDenom2, one}}.IsAllGT(Coins{{testDenom2, one}}))
assert.True(t, Coins{{testDenom1, one}, {testDenom2, two}}.IsAllGT(Coins{{testDenom2, one}}))
assert.False(t, Coins{{testDenom1, one}, {testDenom2, one}}.IsAllGT(Coins{{testDenom2, two}}))
}

Expand All @@ -358,7 +355,7 @@ func TestCoinsLT(t *testing.T) {
assert.False(t, Coins{{testDenom1, one}, {testDenom2, one}}.IsAllLT(Coins{{testDenom2, one}}))
assert.False(t, Coins{{testDenom1, one}, {testDenom2, one}}.IsAllLT(Coins{{testDenom2, two}}))
assert.False(t, Coins{{testDenom1, one}, {testDenom2, one}}.IsAllLT(Coins{{testDenom1, one}, {testDenom2, one}}))
assert.True(t, Coins{{testDenom1, one}, {testDenom2, one}}.IsAllLT(Coins{{testDenom1, one}, {testDenom2, two}}))
assert.True(t, Coins{{testDenom1, one}, {testDenom2, one}}.IsAllLT(Coins{{testDenom1, two}, {testDenom2, two}}))
assert.True(t, Coins{}.IsAllLT(Coins{{testDenom1, one}}))
}

Expand Down

0 comments on commit f37ab4a

Please sign in to comment.