corda / net.corda.core.crypto / CompositeKey

CompositeKey

class CompositeKey : PublicKey

A tree data structure that enables the representation of composite public keys, which are used to represent the signing requirements for multi-signature scenarios such as RAFT notary services. A composite key is a list of leaf keys and their contributing weight, and each leaf can be a conventional single key or a composite key. Keys contribute their weight to the total if they are matched by the signature.

For complex scenarios, such as "Both Alice and Bob need to sign to consume a state S", we can represent the requirement by creating a tree with a root CompositeKey, and Alice and Bob as children. The root node would specify weights for each of its children and a threshold – the minimum total weight required (e.g. the minimum number of child signatures required) to satisfy the tree signature requirement.

Using these constructs we can express e.g. 1 of N (OR) or N of N (AND) signature requirements. By nesting we can create multi-level requirements such as "either the CEO or 3 of 5 of his assistants need to sign".

Types

Builder

class Builder

A helper class for building a CompositeKey.

NodeAndWeight

data class NodeAndWeight : Comparable<NodeAndWeight>

Holds node - weight pairs for a CompositeKey. Ordered first by weight, then by node's hashCode. Each node should be assigned with a positive weight to avoid certain types of weight underflow attacks.

Properties

children

val children: List<NodeAndWeight>

Τhe order of the children may not be the same to what was provided in the builder.

leafKeys

val leafKeys: Set<PublicKey>

Set of all leaf keys of that CompositeKey.

threshold

val threshold: Int

specifies the minimum total weight required (in the simple case – the minimum number of child signatures required) to satisfy the sub-tree rooted at this node.

Functions

checkValidity

fun checkValidity(): Unit

This method will detect graph cycles in the full composite key structure to protect against infinite loops when traversing the graph and key duplicates in the each layer. It also checks if the threshold and weight constraint requirements are met, while it tests for aggregated-weight integer overflow. In practice, this method should be always invoked on the root CompositeKey, as it inherently validates the child nodes (all the way till the leaves).

equals

fun equals(other: Any?): Boolean

getAlgorithm

fun getAlgorithm(): String

getEncoded

fun getEncoded(): ByteArray

getFormat

fun getFormat(): <ERROR CLASS>

hashCode

fun hashCode(): Int

isFulfilledBy

fun isFulfilledBy(key: PublicKey): <ERROR CLASS>

Takes single PublicKey and checks if CompositeKey requirements hold for that key.

fun isFulfilledBy(keysToCheck: Iterable<PublicKey>): Boolean

Function checks if the public keys corresponding to the signatures are matched against the leaves of the composite key tree in question, and the total combined weight of all children is calculated for every intermediary node. If all thresholds are satisfied, the composite key requirement is considered to be met.

toString

fun toString(): String

Companion Object Properties

KEY_ALGORITHM

const val KEY_ALGORITHM: String

Companion Object Functions

getInstance

fun getInstance(encoded: ByteArray): <ERROR CLASS>

Build a composite key from a DER encoded form.

fun getInstance(asn1: <ERROR CLASS>): PublicKey

Extension Properties

keys

val PublicKey.keys: Set<PublicKey>

Return a Set of the contained leaf keys if this is a CompositeKey. Otherwise, return a Set with a single element (this PublicKey). Note that leaf keys cannot be of type CompositeKey.

Extension Functions

containsAny

fun PublicKey.containsAny(otherKeys: Iterable<PublicKey>): Boolean

Checks whether any of the given keys matches a leaf on the CompositeKey tree or a single PublicKey.

contextLogger

fun Any.contextLogger(): <ERROR CLASS>

When called from a companion object, returns the logger for the enclosing class.

isFulfilledBy

fun PublicKey.isFulfilledBy(otherKey: PublicKey): Boolean

Return true if otherKey fulfils the requirements of this PublicKey.

fun PublicKey.isFulfilledBy(otherKeys: Iterable<PublicKey>): Boolean

Return true if otherKeys fulfil the requirements of this PublicKey.

isValid

fun PublicKey.isValid(content: ByteArray, signature: DigitalSignature): Boolean

Utility to simplify the act of verifying a signature. In comparison to verify if the key and signature do not match it returns false rather than throwing an exception. Normally you should use the function which throws, as it avoids the risk of failing to test the result, but this is for uses such as java.security.Signature.verify implementations.

toBase58String

fun PublicKey.toBase58String(): String

Return the Base58 representation of the serialised public key.

toSHA256Bytes

fun PublicKey.toSHA256Bytes(): ByteArray

Return the bytes of the SHA-256 output for this public key.

toStringShort

fun PublicKey.toStringShort(): String

Render a public key to its hash (in Base58) of its serialised form using the DL prefix.

verify

fun PublicKey.verify(content: ByteArray, signature: DigitalSignature): Boolean

Utility to simplify the act of verifying a signature.

fun PublicKey.verify(signatureData: ByteArray, clearData: ByteArray): Boolean

Helper function to verify a signature.