mirror of
https://github.com/corda/corda.git
synced 2025-06-15 13:48:14 +00:00
Introducing StartableByRPC and SchedulableFlow annotations, needed by flows started via RPC and schedulable flows respectively.
CordaPluginRegistry.requiredFlows is no longer needed as a result.
This commit is contained in:
@ -7,6 +7,7 @@ import net.corda.core.utilities.DUMMY_BANK_A
|
||||
import net.corda.core.utilities.DUMMY_BANK_B
|
||||
import net.corda.core.utilities.DUMMY_NOTARY
|
||||
import net.corda.node.driver.driver
|
||||
import net.corda.node.services.startFlowPermission
|
||||
import net.corda.node.services.transactions.SimpleNotaryService
|
||||
import net.corda.nodeapi.User
|
||||
import org.junit.Test
|
||||
@ -17,11 +18,11 @@ class AttachmentDemoTest {
|
||||
@Test fun `attachment demo using a 10MB zip file`() {
|
||||
val numOfExpectedBytes = 10_000_000
|
||||
driver(dsl = {
|
||||
val demoUser = listOf(User("demo", "demo", setOf("StartFlow.net.corda.flows.FinalityFlow")))
|
||||
val demoUser = listOf(User("demo", "demo", setOf(startFlowPermission<AttachmentDemoFlow>())))
|
||||
val (nodeA, nodeB) = Futures.allAsList(
|
||||
startNode(DUMMY_BANK_A.name, rpcUsers = demoUser),
|
||||
startNode(DUMMY_BANK_B.name, rpcUsers = demoUser),
|
||||
startNode(DUMMY_NOTARY.name, setOf(ServiceInfo(SimpleNotaryService.Companion.type)))
|
||||
startNode(DUMMY_NOTARY.name, setOf(ServiceInfo(SimpleNotaryService.type)))
|
||||
).getOrThrow()
|
||||
|
||||
val senderThread = CompletableFuture.supplyAsync {
|
||||
|
@ -1,5 +1,6 @@
|
||||
package net.corda.attachmentdemo
|
||||
|
||||
import co.paralleluniverse.fibers.Suspendable
|
||||
import com.google.common.net.HostAndPort
|
||||
import joptsimple.OptionParser
|
||||
import net.corda.client.rpc.CordaRPCClient
|
||||
@ -9,14 +10,14 @@ import net.corda.core.contracts.TransactionForContract
|
||||
import net.corda.core.contracts.TransactionType
|
||||
import net.corda.core.identity.Party
|
||||
import net.corda.core.crypto.SecureHash
|
||||
import net.corda.core.flows.FlowLogic
|
||||
import net.corda.core.flows.StartableByRPC
|
||||
import net.corda.core.getOrThrow
|
||||
import net.corda.core.messaging.CordaRPCOps
|
||||
import net.corda.core.messaging.startTrackedFlow
|
||||
import net.corda.core.sizedInputStreamAndHash
|
||||
import net.corda.core.utilities.DUMMY_BANK_B
|
||||
import net.corda.core.utilities.DUMMY_NOTARY
|
||||
import net.corda.core.utilities.DUMMY_NOTARY_KEY
|
||||
import net.corda.core.utilities.Emoji
|
||||
import net.corda.core.transactions.SignedTransaction
|
||||
import net.corda.core.utilities.*
|
||||
import net.corda.flows.FinalityFlow
|
||||
import net.corda.node.driver.poll
|
||||
import java.io.InputStream
|
||||
@ -83,26 +84,40 @@ fun sender(rpc: CordaRPCOps, inputStream: InputStream, hash: SecureHash.SHA256)
|
||||
val id = rpc.uploadAttachment(it)
|
||||
require(hash == id) { "Id was '$id' instead of '$hash'" }
|
||||
}
|
||||
require(rpc.attachmentExists(hash))
|
||||
}
|
||||
|
||||
// Create a trivial transaction with an output that describes the attachment, and the attachment itself
|
||||
val ptx = TransactionType.General.Builder(notary = DUMMY_NOTARY)
|
||||
require(rpc.attachmentExists(hash))
|
||||
ptx.addOutputState(AttachmentContract.State(hash))
|
||||
ptx.addAttachment(hash)
|
||||
|
||||
// Sign with the notary key
|
||||
ptx.signWith(DUMMY_NOTARY_KEY)
|
||||
|
||||
// Send the transaction to the other recipient
|
||||
val stx = ptx.toSignedTransaction()
|
||||
println("Sending ${stx.id}")
|
||||
val flowHandle = rpc.startTrackedFlow(::FinalityFlow, stx, setOf(otherSide))
|
||||
val flowHandle = rpc.startTrackedFlow(::AttachmentDemoFlow, otherSide, hash)
|
||||
flowHandle.progress.subscribe(::println)
|
||||
flowHandle.returnValue.getOrThrow()
|
||||
val stx = flowHandle.returnValue.getOrThrow()
|
||||
println("Sent ${stx.id}")
|
||||
}
|
||||
|
||||
@StartableByRPC
|
||||
class AttachmentDemoFlow(val otherSide: Party, val hash: SecureHash.SHA256) : FlowLogic<SignedTransaction>() {
|
||||
|
||||
object SIGNING : ProgressTracker.Step("Signing transaction")
|
||||
|
||||
override val progressTracker: ProgressTracker = ProgressTracker(SIGNING)
|
||||
|
||||
@Suspendable
|
||||
override fun call(): SignedTransaction {
|
||||
// Create a trivial transaction with an output that describes the attachment, and the attachment itself
|
||||
val ptx = TransactionType.General.Builder(notary = DUMMY_NOTARY)
|
||||
ptx.addOutputState(AttachmentContract.State(hash))
|
||||
ptx.addAttachment(hash)
|
||||
|
||||
progressTracker.currentStep = SIGNING
|
||||
// Sign with the notary key
|
||||
ptx.signWith(DUMMY_NOTARY_KEY)
|
||||
|
||||
// Send the transaction to the other recipient
|
||||
val stx = ptx.toSignedTransaction()
|
||||
|
||||
return subFlow(FinalityFlow(stx, setOf(otherSide))).single()
|
||||
}
|
||||
}
|
||||
|
||||
fun recipient(rpc: CordaRPCOps) {
|
||||
println("Waiting to receive transaction ...")
|
||||
val stx = rpc.verifiedTransactions().second.toBlocking().first()
|
||||
|
@ -1,12 +0,0 @@
|
||||
package net.corda.attachmentdemo.plugin
|
||||
|
||||
import net.corda.core.node.CordaPluginRegistry
|
||||
import net.corda.core.transactions.SignedTransaction
|
||||
import net.corda.flows.FinalityFlow
|
||||
|
||||
class AttachmentDemoPlugin : CordaPluginRegistry() {
|
||||
// A list of Flows that are required for this cordapp
|
||||
override val requiredFlows: Map<String, Set<String>> = mapOf(
|
||||
FinalityFlow::class.java.name to setOf(SignedTransaction::class.java.name, setOf(Unit).javaClass.name, setOf(Unit).javaClass.name)
|
||||
)
|
||||
}
|
@ -1,2 +0,0 @@
|
||||
# Register a ServiceLoader service extending from net.corda.core.node.CordaPluginRegistry
|
||||
net.corda.attachmentdemo.plugin.AttachmentDemoPlugin
|
Reference in New Issue
Block a user