Skip to content

Corda RPC

Purpose

A helper layer over the R3 Corda RPC Blockchain API: Corda

Platform 6 supports Corda 4. It comes bundled with the latest java archives required to integrate and interact with Corda.

The latest developer guide can be found here: https://docs.corda.net/docs/corda-os/4.4.html

corda

The Corda RCP API is provided as a native java API and as such is available for use directly from any Platform 6 script.

Note

Using the Corda RPC API will require your scripts import all the net.corda packages used. A great way to hide this and de-clutter your scripts is to use the @import to insert a commonly used set of imports into each of your scripts.

Current API documentation can be found here: https://docs.corda.net/docs/corda-os/4.4/tutorial-clientrpc-api.html

Methods

Binding name: p6.cordarpc


Method: CordaContext build(final String hostPort, final String username, final String password)

Build an instance of a CordaContext object using the supplied node connection parameters.

A CordaContext has the following fields for your convenience:

CordaRPCClient client
CordaRPCConnection connection
CordaRPCOps proxy

The CordaContext implements Closeable so making the closure of the connection more manageable.

The supplied hostPort parameter is parsed by the net.corda.core.utilities.NetworkHostAndPort class to build a usable node address.

Warning

For simplicity I have shown username and password values in the following example scripts. It is not advisable to hard code user credentials in scripts. A better way would be to use values from our configuration service or other external injection mechanism.


Examples

Example One

A simple one line script that will connect to a node, retrieve and log the node diagnostic information and close the connection cleanly

p6.cordarpc.build('localhost:10005', 'user1', 'test').withCloseable { ctx -> p6.log.info(ctx.proxy.nodeDiagnosticInfo().toString()) }

Example Two

A more basic use of the CordaContext to list the nodes registered flows and finally close the context

def cordaCtx = p6.cordarpc.build('localhost:10005', 'user1', 'test')
def lstFlows = cordaCtx.proxy.registeredFlows()
p6.log.info('Registered Flows: ' + lstFlows)
cordaCtx.close()

Example Three

This example uses the nodes and cordapps deployed using the Corda Samples project: https://github.com/corda/samples

After building https://github.com/corda/samples/tree/release-V4/cordapp-example I started four nodes using the runnodes script.

Note

In order to reference the com.example.flow package in your scripts it is essential that a copy of the Example cordapp JAR files are copied into the folder ${P6_DATA}/lib so they are added to the Platform 6 classpath

cordapp-example-workflows-0.1.jar and cordapp-example-contracts-0.1.jar in this tutorial.

Please refer to the Bundled Resources Service This is the recommended way to distribute JAR files with your applications.

This example will connect to node PartyA and initiate an example flow establishing a IOUState with value 99 with PartyB

When the flow is complete the script logs the transaction id associated with this flow initiation:

INFO [GROOVYSCRIPT: io.platform6.scripts.p6core.corda.Main] ExampleFlow initiation complete: SignedTransaction(id=F6F990A117DFAA07D5EDAD22F78AE527888BC31A4D638C293E91EAEA083E7507)
import com.example.flow.ExampleFlow

import net.corda.core.identity.Party
import net.corda.core.identity.CordaX500Name

p6.cordarpc.build('localhost:10005', 'user1', 'test').withCloseable { ctx ->

    def partyBName = new CordaX500Name('PartyB', 'New York', 'US')
    def partyB = ctx.proxy.wellKnownPartyFromX500Name(partyBName)

    def flowHandle = ctx.proxy.startFlowDynamic(ExampleFlow.Initiator.class, 99, partyB)
    p6.log.info('ExampleFlow initiation complete: ' + flowHandle.getReturnValue().get())
}

Warning

The following text is taken from the Corda API documentation but is worth repeating here:

“With regards to the start flow RPCs, there is an extra layer of security whereby the flow to be executed has to be annotated with @StartableByRPC. Flows without this annotation cannot execute using RPC.”

Without the annotation the startFlowDynamic() call will fail!