The Corda flow cookbook: Chapter 1

Corda Jul 19 2021 By: David Awad
Comments

0 Comments

Views

140 Views

The Corda Flow Cookbook
David Awad
David Awad Developer
Share This Post:
Copied

You can use our “Flow Cookbook” to do lots of exciting things – from identifying other nodes to gathering signatures. 

This series will introduce you to some key recipes in the cookbook. You’ll learn how they work and what you can use them for.  

You’ll learn how to:

  •  Use the service hub to get references to services from the Corda network
  • Request a specific counterparty identity
  • Share arbitrary data, and 
  • Unwrap data using a Lambada function.

The first recipe is relatively straightforward—it lets you request a notary reference from the network. This uses the Corda service hub to get references to services from the Corda network. 

    
CordaX500Name notaryName = new CordaX500Name("Notary Service", "London", "GB");
Party specificNotary = Objects.requireNonNull(getServiceHub().getNetworkMapCache().getNotary(notaryName));
// Alternatively, we can pick an arbitrary notary from the notary
// list. However, it is always preferable to specify the notary
// explicitly, as the notary list might change when new notaries are
// introduced, or old ones decommissioned.
Party firstNotary = getServiceHub().getNetworkMapCache().getNotaryIdentities().get(0);
    

You can also use the service hub to request a specific counterparty identity to use within your flow. Here’s the recipe:

    
CordaX500Name notaryName = new CordaX500Name("Notary Service", "London", "GB");
Party specificNotary = Objects.requireNonNull(getServiceHub().getNetworkMapCache().getNotary(notaryName));
// CordaX500Name counterPartyName = new CordaX500Name("NodeA", "London", "GB");
Party namedCounterparty = getServiceHub().getIdentityService().wellKnownPartyFromX500Name(counterPartyName);
Party keyedCounterparty = getServiceHub().getIdentityService().partyFromKey(dummyPubKey);
    

Once you can find a notary and identify a specific party, you can  share arbitrary data with them:

    
FlowSession counterpartySession = initiateFlow(counterparty);

// We can send arbitrary data to a counterparty.
// If this is the first ``send``, the counterparty will either:
// 1. Ignore the message if they are not registered to respond
//    to messages from this flow.
// 2. Start the flow they have registered to respond to this flow,
//    and run the flow until the first call to ``receive``, at
//    which point they process the message.
// In other words, we are assuming that the counterparty is
// registered to respond to this flow, and has a corresponding
// ``receive`` call.
counterpartySession.send(new Object());

// We can wait to receive arbitrary data of a specific type from a
// counterparty. Again, this implies a corresponding ``send`` call
// in the counterparty's flow. A few scenarios:
// - We never receive a message back. In the current design, the
//   flow is paused until the node's owner kills the flow.
// - Instead of sending a message back, the counterparty throws a
//   ``FlowException``. This exception is propagated back to us,
//   and we can use the error message to establish what happened.
// - We receive a message back, but it's of the wrong type. In
//   this case, a ``FlowException`` is thrown.
// - We receive back a message of the correct type. All is good.
//
// Upon calling ``receive()`` (or ``sendAndReceive()``), the
// ``FlowLogic`` is suspended until it receives a response.
//
// We receive the data wrapped in an ``UntrustworthyData``
// instance. This is a reminder that the data we receive may not
// be what it appears to be! We must unwrap the
// ``UntrustworthyData`` using a lambda.
UntrustworthyData packet1 = counterpartySession.receive(Integer.class);
Integer integer = packet1.unwrap(data -> {
    // Perform checking on the object received.
    // T O D O: Check the received object.
    // Return the object.
    return data;
});
    

You could also do this by unwrapping the data when you receive it with a lambda function:


UntrustworthyData packet2 = counterpartySession.sendAndReceive(Boolean.class, "You can send and receive any class!");
Boolean bool = packet2.unwrap(data -> {
    // Perform checking on the object received.
    // T O D O: Check the received object.
    // Return the object.
    return data;
});
    

These recipes will give you a good foothold for writing basic flows.

David Awad
David Awad David Awad is a Developer Evangelist at R3, an enterprise blockchain software firm working with a global ecosystem of more than 350 participants across multiple industries from both the private and public sectors to develop on Corda, its open-source blockchain platform, and Corda Enterprise, a commercial version of Corda for enterprise usage. Follow David on Twitter here.

Leave a Reply

Subscribe to our newsletter to stay up to date on the latest developer news, tools, and articles.