Writing Your First Plutus Smart Contract

img

4) Writing Your First Wallet Function

Now that we have written an empty smart contract we need to be able to interact with it. We will be writing our first wallet function in this section which will allow the wallet to keep track of the smart contract’s state.

First thing’s first, we will define the address of our ValidatorScript.

1
2
smartContractAddress :: Address'
smartContractAddress = scriptAddress myFirstValidator

Take note that the type of an address is Address'. To acquire the address we use the function scriptAddress which takes a ValidatorScript as input. Thus we feed it our ValidatorScript myFirstValidator. In Haskell inputs to functions are provided with spaces between them. From now on whenever we need the smart contract’s address we simply call smartContractAddress.

Before we proceed with using the wallet we must import the functionality to interact with it.

1
2
import Wallet
import Playground.Contract

Now with the smart contract’s address in hand and the wallet functionality imported, we are able to write our first wallet function.

1
2
watchSmartContract :: MockWallet ()
watchSmartContract = startWatching smartContractAddress

In the Plutus Plaground, any functionality that uses a wallet has the type MockWallet (). In this case we call the function startWatching which takes an Address' as input and returns a type of MockWallet (). Any wallet that calls this function in it’s Action Sequence will track the changes in state of the smart contract and be able to respond to them.

However we still haven’t provided the ability for the Plutus Playground to know that we have created a function which can be used as an Action. This is done with a little bit more Template Haskell “magic”.

1
$(mkFunction 'watchSmartContract)

This creates a new function in the Plutus Playground UI under each wallet labelled watchSmartContract. You can now click on said function and it will be added to the Action Sequence list. From now on whenever you test any other Actions, make sure to always call watchSmartContract for each wallet you intend to use first. Our code this far is the following:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
module MyFirstPlutusSmartContract where

import qualified Language.PlutusTx as PlutusTx
import Ledger
import Wallet
import Playground.Contract

myFirstValidator :: ValidatorScript
myFirstValidator = ValidatorScript (fromCompiledCode $$(PlutusTx.compile
[|| \(a :: ()) (b :: ()) (c :: ()) -> () ||]))

smartContractAddress :: Address'
smartContractAddress = scriptAddress myFirstValidator

watchSmartContract :: MockWallet ()
watchSmartContract = startWatching smartContractAddress

$(mkFunction 'watchSmartContract)

Make sure to write it out and compile it yourself to verify that it works. Furthermore try using watchSmartContract in the Action Sequence. It won’t do anything by itself, but getting use to the Plutus Playground UI is important.