Replace PublicKey with PublicKeyTree in Party. A single entity can now be identified by more than one key.

This commit is contained in:
Andrius Dagys
2016-11-11 18:14:50 +00:00
parent d7defd3157
commit c33c55eb20
84 changed files with 532 additions and 510 deletions

View File

@ -2,10 +2,9 @@ package net.corda.contracts
import net.corda.core.contracts.*
import net.corda.core.crypto.Party
import net.corda.core.crypto.PublicKeyTree
import net.corda.core.crypto.SecureHash
import net.corda.core.crypto.toStringShort
import net.corda.core.transactions.TransactionBuilder
import java.security.PublicKey
import java.time.LocalDate
import java.time.ZoneOffset
import java.util.*
@ -44,24 +43,24 @@ class AccountReceivable : Contract {
data class State(
// technical variables
override val owner: PublicKey,
override val owner: PublicKeyTree,
val status: StatusEnum,
val props: AccountReceivableProperties
) : OwnableState {
override val contract = ACCOUNTRECEIVABLE_PROGRAM_ID
override val participants: List<PublicKey>
override val participants: List<PublicKeyTree>
get() = listOf(owner)
override fun toString() = "AR owned by ${owner.toStringShort()})"
override fun toString() = "AR owned by $owner)"
fun checkInvoice(invoice: Invoice.State): Boolean {
val arProps = Helper.invoicePropsToARProps(invoice.props, props.discountRate)
return props == arProps
}
override fun withNewOwner(newOwner: PublicKey) = Pair(Commands.Issue(), copy(owner = newOwner, status = StatusEnum.Issued))
override fun withNewOwner(newOwner: PublicKeyTree) = Pair(Commands.Issue(), copy(owner = newOwner, status = StatusEnum.Issued))
}

View File

@ -2,10 +2,10 @@ package net.corda.contracts
import net.corda.core.contracts.*
import net.corda.core.crypto.Party
import net.corda.core.crypto.PublicKeyTree
import net.corda.core.crypto.SecureHash
import net.corda.core.days
import net.corda.core.transactions.TransactionBuilder
import java.security.PublicKey
import java.time.Instant
import java.time.LocalDate
@ -46,15 +46,15 @@ class BillOfLadingAgreement : Contract {
data class State(
// technical variables
override val owner: PublicKey,
override val owner: PublicKeyTree,
val beneficiary: Party,
val props: BillOfLadingProperties
) : OwnableState {
override val participants: List<PublicKey>
override val participants: List<PublicKeyTree>
get() = listOf(owner)
override fun withNewOwner(newOwner: PublicKey): Pair<CommandData, OwnableState> {
override fun withNewOwner(newOwner: PublicKeyTree): Pair<CommandData, OwnableState> {
return Pair(Commands.TransferPossession(), copy(owner = newOwner))
}
@ -112,7 +112,7 @@ class BillOfLadingAgreement : Contract {
/**
* Returns a transaction that issues a Bill of Lading Agreement
*/
fun generateIssue(owner: PublicKey, beneficiary: Party, props: BillOfLadingProperties, notary: Party): TransactionBuilder {
fun generateIssue(owner: PublicKeyTree, beneficiary: Party, props: BillOfLadingProperties, notary: Party): TransactionBuilder {
val state = State(owner, beneficiary, props)
val builder = TransactionType.General.Builder(notary = notary)
builder.setTime(Instant.now(), 1.days)
@ -122,17 +122,17 @@ class BillOfLadingAgreement : Contract {
/**
* Updates the given partial transaction with an input/output/command to reassign ownership of the paper.
*/
fun generateTransferAndEndorse(tx: TransactionBuilder, BoL: StateAndRef<State>, newOwner: PublicKey, newBeneficiary: Party) {
fun generateTransferAndEndorse(tx: TransactionBuilder, BoL: StateAndRef<State>, newOwner: PublicKeyTree, newBeneficiary: Party) {
tx.addInputState(BoL)
tx.addOutputState(BoL.state.data.copy(owner = newOwner, beneficiary = newBeneficiary))
val signers: List<PublicKey> = listOf(BoL.state.data.owner, BoL.state.data.beneficiary.owningKey)
val signers: List<PublicKeyTree> = listOf(BoL.state.data.owner, BoL.state.data.beneficiary.owningKey)
tx.addCommand(Commands.TransferAndEndorseBL(), signers)
}
/**
* Updates the given partial transaction with an input/output/command to reassign ownership of the paper.
*/
fun generateTransferPossession(tx: TransactionBuilder, BoL: StateAndRef<State>, newOwner: PublicKey) {
fun generateTransferPossession(tx: TransactionBuilder, BoL: StateAndRef<State>, newOwner: PublicKeyTree) {
tx.addInputState(BoL)
tx.addOutputState(BoL.state.data.copy(owner = newOwner))
// tx.addOutputState(BoL.state.data.copy().withNewOwner(newOwner))

View File

@ -3,6 +3,7 @@ package net.corda.contracts
import com.fasterxml.jackson.annotation.JsonIgnoreProperties
import net.corda.core.contracts.*
import net.corda.core.crypto.Party
import net.corda.core.crypto.PublicKeyTree
import net.corda.core.crypto.SecureHash
import net.corda.core.transactions.TransactionBuilder
import java.security.PublicKey
@ -71,7 +72,7 @@ class Invoice : Contract {
override val contract = INVOICE_PROGRAM_ID
override val participants: List<PublicKey>
override val participants: List<PublicKeyTree>
get() = listOf(owner.owningKey)
// returns true when the actual business properties of the
@ -86,7 +87,7 @@ class Invoice : Contract {
val amount: Amount<Issued<Currency>> get() = props.amount
override fun isRelevant(ourKeys: Set<PublicKey>): Boolean {
return owner.owningKey in ourKeys || buyer.owningKey in ourKeys
return owner.owningKey.containsAny(ourKeys) || buyer.owningKey.containsAny(ourKeys)
}
}

View File

@ -1,11 +1,11 @@
package net.corda.contracts
import net.corda.core.contracts.*
import net.corda.core.crypto.NullPublicKey
import net.corda.core.crypto.NullPublicKeyTree
import net.corda.core.crypto.Party
import net.corda.core.crypto.PublicKeyTree
import net.corda.core.crypto.SecureHash
import net.corda.core.transactions.TransactionBuilder
import java.security.PublicKey
import java.time.LocalDate
import java.time.Period
import java.util.*
@ -108,14 +108,14 @@ class LCApplication : Contract {
}
data class State(
val owner: PublicKey,
val owner: PublicKeyTree,
val status: Status,
val props: LCApplicationProperties
) : ContractState {
override val contract = LC_APPLICATION_PROGRAM_ID
override val participants: List<PublicKey>
override val participants: List<PublicKeyTree>
get() = listOf(owner)
// returns true when the actual business properties of the
@ -125,7 +125,7 @@ class LCApplication : Contract {
}
// iterate over the goods list and sum up the price for each
fun withoutOwner() = copy(owner = NullPublicKey)
fun withoutOwner() = copy(owner = NullPublicKeyTree)
}
fun generateApply(props: LCApplicationProperties, notary: Party, purchaseOrder: Attachment): TransactionBuilder {

View File

@ -3,10 +3,10 @@ package net.corda.contracts
import net.corda.contracts.asset.sumCashBy
import net.corda.core.contracts.*
import net.corda.core.crypto.Party
import net.corda.core.crypto.PublicKeyTree
import net.corda.core.crypto.SecureHash
import net.corda.core.days
import net.corda.core.transactions.TransactionBuilder
import java.security.PublicKey
import java.time.Instant
import java.time.LocalDate
import java.time.Period
@ -58,7 +58,7 @@ class LOC : Contract {
) : ContractState {
override val contract = LOC_PROGRAM_ID
override val participants: List<PublicKey>
override val participants: List<PublicKeyTree>
get() = listOf()
}

View File

@ -2,10 +2,10 @@ package net.corda.contracts.universal
import net.corda.core.contracts.*
import net.corda.core.crypto.Party
import net.corda.core.crypto.PublicKeyTree
import net.corda.core.crypto.SecureHash
import net.corda.core.transactions.TransactionBuilder
import java.math.BigDecimal
import java.security.PublicKey
import java.time.Instant
/**
@ -18,7 +18,7 @@ val UNIVERSAL_PROGRAM_ID = UniversalContract()
class UniversalContract : Contract {
data class State(override val participants: List<PublicKey>,
data class State(override val participants: List<PublicKeyTree>,
val details: Arrangement) : ContractState {
override val contract = UNIVERSAL_PROGRAM_ID
}
@ -316,7 +316,7 @@ class UniversalContract : Contract {
override val legalContractReference: SecureHash
get() = throw UnsupportedOperationException()
fun generateIssue(tx: TransactionBuilder, arrangement: Arrangement, at: PartyAndReference, notary: PublicKey) {
fun generateIssue(tx: TransactionBuilder, arrangement: Arrangement, at: PartyAndReference, notary: PublicKeyTree) {
check(tx.inputStates().isEmpty())
tx.addOutputState(State(listOf(notary), arrangement))
tx.addCommand(Commands.Issue(), at.party.owningKey)

View File

@ -2,15 +2,11 @@ package net.corda.contracts.universal
import com.google.common.collect.ImmutableSet
import com.google.common.collect.Sets
import net.corda.core.contracts.Amount
import net.corda.core.contracts.Frequency
import net.corda.core.crypto.Party
import com.sun.org.apache.xpath.internal.operations.Bool
import java.math.BigDecimal
import java.security.PublicKey
import net.corda.core.crypto.PublicKeyTree
import java.time.Instant
import java.time.LocalDate
import java.util.*
/**
* Created by sofusmortensen on 23/05/16.
@ -20,44 +16,44 @@ fun Instant.toLocalDate(): LocalDate = LocalDate.ofEpochDay(this.epochSecond / 6
fun LocalDate.toInstant(): Instant = Instant.ofEpochSecond(this.toEpochDay() * 60 * 60 * 24)
private fun liablePartiesVisitor(arrangement: Arrangement): ImmutableSet<PublicKey> =
private fun liablePartiesVisitor(arrangement: Arrangement): ImmutableSet<PublicKeyTree> =
when (arrangement) {
is Zero -> ImmutableSet.of<PublicKey>()
is Zero -> ImmutableSet.of<PublicKeyTree>()
is Transfer -> ImmutableSet.of(arrangement.from.owningKey)
is And ->
arrangement.arrangements.fold(ImmutableSet.builder<PublicKey>(), { builder, k -> builder.addAll(liablePartiesVisitor(k)) }).build()
arrangement.arrangements.fold(ImmutableSet.builder<PublicKeyTree>(), { builder, k -> builder.addAll(liablePartiesVisitor(k)) }).build()
is Actions ->
arrangement.actions.fold(ImmutableSet.builder<PublicKey>(), { builder, k -> builder.addAll(liablePartiesVisitor(k)) }).build()
arrangement.actions.fold(ImmutableSet.builder<PublicKeyTree>(), { builder, k -> builder.addAll(liablePartiesVisitor(k)) }).build()
is RollOut -> liablePartiesVisitor(arrangement.template)
is Continuation -> ImmutableSet.of<PublicKey>()
is Continuation -> ImmutableSet.of<PublicKeyTree>()
else -> throw IllegalArgumentException("liableParties " + arrangement)
}
private fun liablePartiesVisitor(action: Action): ImmutableSet<PublicKey> =
private fun liablePartiesVisitor(action: Action): ImmutableSet<PublicKeyTree> =
if (action.actors.size != 1)
liablePartiesVisitor(action.arrangement)
else
Sets.difference(liablePartiesVisitor(action.arrangement), ImmutableSet.of(action.actors.single())).immutableCopy()
/** returns list of potentially liable parties for a given contract */
fun liableParties(contract: Arrangement): Set<PublicKey> = liablePartiesVisitor(contract)
fun liableParties(contract: Arrangement): Set<PublicKeyTree> = liablePartiesVisitor(contract)
private fun involvedPartiesVisitor(action: Action): Set<PublicKey> =
private fun involvedPartiesVisitor(action: Action): Set<PublicKeyTree> =
Sets.union(involvedPartiesVisitor(action.arrangement), action.actors.map { it.owningKey }.toSet()).immutableCopy()
private fun involvedPartiesVisitor(arrangement: Arrangement): ImmutableSet<PublicKey> =
private fun involvedPartiesVisitor(arrangement: Arrangement): ImmutableSet<PublicKeyTree> =
when (arrangement) {
is Zero -> ImmutableSet.of<PublicKey>()
is Zero -> ImmutableSet.of<PublicKeyTree>()
is Transfer -> ImmutableSet.of(arrangement.from.owningKey)
is And ->
arrangement.arrangements.fold(ImmutableSet.builder<PublicKey>(), { builder, k -> builder.addAll(involvedPartiesVisitor(k)) }).build()
arrangement.arrangements.fold(ImmutableSet.builder<PublicKeyTree>(), { builder, k -> builder.addAll(involvedPartiesVisitor(k)) }).build()
is Actions ->
arrangement.actions.fold(ImmutableSet.builder<PublicKey>(), { builder, k -> builder.addAll(involvedPartiesVisitor(k)) }).build()
arrangement.actions.fold(ImmutableSet.builder<PublicKeyTree>(), { builder, k -> builder.addAll(involvedPartiesVisitor(k)) }).build()
else -> throw IllegalArgumentException()
}
/** returns list of involved parties for a given contract */
fun involvedParties(arrangement: Arrangement): Set<PublicKey> = involvedPartiesVisitor(arrangement)
fun involvedParties(arrangement: Arrangement): Set<PublicKeyTree> = involvedPartiesVisitor(arrangement)
fun replaceParty(action: Action, from: Party, to: Party): Action =
if (action.actors.contains(from)) {