Skip to content

Commit

Permalink
add noDuplicateTxIn
Browse files Browse the repository at this point in the history
  • Loading branch information
fluency03 committed Apr 27, 2018
1 parent 5b8474b commit 1014558
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 2 deletions.
4 changes: 4 additions & 0 deletions src/main/scala/com/fluency03/blockchain/core/Block.scala
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@ import com.fluency03.blockchain.core.Transaction.createCoinbaseTx
import org.json4s.native.JsonMethods.{compact, render}
import org.json4s.{Extraction, JValue}

import scala.collection.mutable

/**
* Block on the chain.
* @param header Header of current Block
Expand Down Expand Up @@ -37,6 +39,8 @@ case class Block(header: BlockHeader, transactions: Seq[Transaction], hash: Stri

def hasValidHeaderHash: Boolean = hash == header.hash

def allTransactionsValid(uTxOs: mutable.Map[Outpoint, TxOut]): Boolean = transactions.forall(tx => tx.isValid(uTxOs))

def toJson: JValue = Extraction.decompose(this)

override def toString: String = compact(render(toJson))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -134,12 +134,17 @@ object Transaction {
.map(t => t.txOuts.zipWithIndex.map {
case (txOut, index) => Outpoint(t.id, index) -> txOut
}.toMap)
.reduce { _ ++ _ }
.foldLeft(Map.empty[Outpoint, TxOut])(_ ++ _)

def getConsumedUTxOs(transactions: Seq[Transaction]): Map[Outpoint, TxOut] =
transactions.map(_.txIns)
.reduce { _ ++ _ }
.foldLeft(Seq.empty[TxIn])(_ ++ _)
.map(txIn => Outpoint(txIn.previousOut.id, txIn.previousOut.index) -> TxOut("", 0))
.toMap

def noDuplicateTxIn(transactions: Seq[Transaction]): Boolean = {
val allRefs = transactions.map(_.txIns.map(_.previousOut)).foldLeft(Seq.empty[Outpoint])(_ ++ _)
allRefs.distinct.length == allRefs.length
}

}
33 changes: 33 additions & 0 deletions src/test/scala/com/fluency03/blockchain/core/TransactionTest.scala
Original file line number Diff line number Diff line change
Expand Up @@ -207,4 +207,37 @@ class TransactionTest extends FlatSpec with Matchers {
signedTx2.isValid(uTxOs) shouldEqual true
}

"noDuplicateTxIn" should "detect whether Seq of Transactions contians duplicate TxIns." in {
noDuplicateTxIn(Seq.empty[Transaction]) shouldEqual true
val tx1: Transaction = Transaction(
Seq(TxIn(Outpoint("a", 0), ""),
TxIn(Outpoint("b", 1), "")),
Seq(TxOut("o", 40)),
genesisTimestamp
)
noDuplicateTxIn(Seq(tx1)) shouldEqual true
val tx2: Transaction = Transaction(
Seq(TxIn(Outpoint("c", 0), ""),
TxIn(Outpoint("d", 1), "")),
Seq(TxOut("o", 40)),
genesisTimestamp
)
noDuplicateTxIn(Seq(tx1, tx2)) shouldEqual true
val tx3: Transaction = Transaction(
Seq(TxIn(Outpoint("e", 0), ""),
TxIn(Outpoint("a", 1), "")),
Seq(TxOut("o", 40)),
genesisTimestamp
)
noDuplicateTxIn(Seq(tx1, tx2, tx3)) shouldEqual true
val tx4: Transaction = Transaction(
Seq(TxIn(Outpoint("a", 0), ""),
TxIn(Outpoint("f", 1), "")),
Seq(TxOut("o", 40)),
genesisTimestamp
)
noDuplicateTxIn(Seq(tx1, tx2, tx3, tx4)) shouldEqual false
}


}

0 comments on commit 1014558

Please sign in to comment.