Building DAML Applications with Scala Bindings

Reading Time: 3 minutes

“Blockchain by itself isn’t transformational, however it is foundational. As a foundational innovation, Blockchain’s value can only be fully realized when the business process is transformed to take advantage of its capabilities, leading to ROI for existing business models and the ability to create value through new ones.”

 Said by  ― Tom Golway, Planning and Managing ATM Networks

So, what is a Blockchain ?

Blockchain is a peer-to-peer ledger system that allows peers to transact between them without any centralized authority. The peer-to-peer network is completely decentralized. To make it decentralized, each peer carries a copy of the ledger. The ledger can be a complete copy or a minimal copy required for it to stay connected and functional to the network.

What is DAML ?

Digital Asset modelling Language is an open source programming language used to write distributed DAML Application quickly, concisely and correctly. It is functional and was designed for distributed business workflow. It helps a developer to focus more on programming business processes by cutting down the amount of time the developer would spend on dealing with encryption and block chain.For more detail on DAML visit here : DAML Introduction

What are Scala Bindings ?

Before starting Scala Bindings let’s understand about Ledger API.

The Ledger API is a set of services exposed through gRPC, which uses Protocol Buffers as its own interface definition language. It allows developers to create applications around the DAML ledger in other programming languages. You can access  Ledger API via the HTTP JSON API, Java bindings, Scala bindings or gRPC. In all cases, the Ledger API exposes the same services:

  • Submitting commands to the ledger. 
  • Reading from the ledger.
  • Utility services like package service, ledger identity service.
  • Testing Service by using  time service and  reset service.

Scala bindings is a client implementation of the Ledger API. Where Ledger API is a Key Player which interacts with Ledger through grpc calls. The Scala bindings library lets you write applications that connect to the Digital Asset distributed ledger using the Scala programming language. For this it uses two main components :

  • Scala codegen 
  • Akka Stream-based API

Functionality provided by Scala Codegen and Akka Stream-based API 

Scala Codegen is used to generate Scala classes from DAML models. DAML Models hold templates of Contracts. The generated Scala code provides a type safe way of creating contracts (CreateCommand) and exercising contract choices (ExerciseCommand). While Akka Stream-based API used to send commands to the ledger and receive transactions back.

DAML Application Architecture

Getting Started

To use the Scala bindings, set up the following dependencies in your project. If you are using  sbt build tool then add it in build.sbt file.

lazy val codeGenDependencies = Seq(
“com.daml.scala” %% “bindings” % daSdkVersion

lazy val applicationDependencies = Seq(
“com.daml.scala” %% “bindings-akka” % daSdkVersion,
)

Generating Scala code of DAML

  1. Install the latest SDK version from here.
  2. Clone a demo example from Github DAML-Demo:
    • Move to the DAML-Demo folder .
  3. Build a DAR file from a DAML model by using daml build command in the terminal.
  4. Run daml codegen scala  in terminal for generating Scala code of Contact template. After running this command a folder is created with scala-codegen name.

Create a contract and send a CreateCommand

To create a Scala class representing an Contact contract you need to import the following things as you can see in our IouMain file:

import com.digitalasset.ledger.client.binding.{Primitive => P}
import com.knoldus.{Iou => M}

And then give definition to the Contact Contract User:

private val firstParty = P.Party("Alice")

and the following code to create an instance of the M.Contact class:

val iou = M.Contact(                                                                                           
  owner = firstParty,
  telephone = "12345"
  )

To send a CreateCommand (keep in mind the following code snippet is part of the Scala for comprehension expression):

createCmd = iou.create                                                                                _ <- clientUtil.submitCommand(firstParty, issuerWorkflowId, createCmd)
_ = logger.info(s"$firstParty created Contact: $iou")
_ = logger.info(s"$firstParty sent create command: $createCmd")

And to fetch the transaction and decode it into the required type of Contract we use:

tx0 <- clientUtil.nextTransaction(firstParty, offset0)(amat)                                              _ = logger.info(s"$firstParty received transaction: $tx0")
iouContract <- toFuture(decodeCreated[M.Contact](tx0))                                                    _ = logger.info(s"$firstParty received contract: $iouContract")

To exercise UpdateTelephone choice on the Contact contract using followings command :

exerciseCmd = iouContract.contractId.exerciseUpdateTelephone(actor = firstParty, newTelephone = "00000")        

Finally archive Contract so Contract became inactive use following archive command :

archivedIouContractId <- toFuture(decodeArchived[M.Contact](tx1)): Future[P.ContractId[M.Contact]] 

Run Application

To run application use following command in other Terminal:

sbt “application/runMain com.knoldus.IouMain localhost 6865”

References

Knoldus-blog-footer-image