Skip to content

Repository for building a fungible app with Linera step-by-step.

Notifications You must be signed in to change notification settings

linera-io/fungible-app-tutorial

 
 

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

15 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Usage

Setting Up

The WebAssembly binaries for the bytecode can be built and published using steps from the book, summarized below.

Before getting started, make sure that the binary tools linera* corresponding to your version of linera-sdk are in your PATH. For scripting purposes, we also assume that the BASH function linera_spawn_and_read_wallet_variables is defined.

Assuming the Linera source code v0.10.1 in ../linera-protocol, this can be achieved as follows:

export PATH="$PWD/../linera-protocol/target/debug:$PATH"
source /dev/stdin <<<"$(linera net helper 2>/dev/null)"

You may also use cargo install [email protected] and append the output of linera net helper to your ~/.bash_profile.

Now, we are ready to set up a local network with an initial wallet owning several initial chains. In a new BASH shell, enter:

linera_spawn_and_read_wallet_variables linera net up --testing-prng-seed 37

A new test network is now running and the environment variables LINERA_WALLET and LINERA_STORAGE are now be defined for the duration of the shell session. We used the test-only CLI option --testing-prng-seed to make keys deterministic and simplify our presentation.

Now, compile the fungible application WebAssembly binaries, and publish them as an application bytecode:

cargo build --release

BYTECODE_ID=$(linera publish-bytecode \
    target/wasm32-unknown-unknown/release/fungible_{contract,service}.wasm)

Here, we stored the new bytecode ID in a variable BYTECODE_ID to be reused it later.

Creating a Token

In order to use the published bytecode to create a token application, the initial state must be specified. This initial state is where the tokens are minted. After the token is created, no additional tokens can be minted and added to the application. The initial state is a JSON string that specifies the accounts that start with tokens.

In order to select the accounts to have initial tokens, the command below can be used to list the chains created for the test in the default wallet:

linera wallet show

A table will be shown with the chains registered in the wallet and their meta-data. The default chain should be highlighted in green. Each chain has an Owner field, and that is what is used for the account.

Let's define some variables corresponding to these values. (Note that owner addresses would not be predictable without --testing-prng-seed above.)

CHAIN_1=e476187f6ddfeb9d588c7b45d3df334d5501d6499b3f9ad5595cae86cce16a65  # default chain for the wallet
OWNER_1=7136460f0c87ae46f966f898d494c4b40c4ae8c527f4d1c0b1fa0f7cff91d20f  # owner of chain 1
CHAIN_2=256e1dbc00482ddd619c293cc0df94d366afe7980022bb22d99e33036fd465dd  # another chain in the wallet
OWNER_2=598d18f67709fe76ed6a36b75a7c9889012d30b896800dfd027ee10e1afd49a3  # owner of chain 2

The example below creates a token application on the default chain CHAIN_1 and gives the owner 100 tokens:

APP_ID=$(linera create-application $BYTECODE_ID \
    --json-argument "\"100.\""
)

This will store the application ID in a new variable APP_ID.

Using the Token Application

Before using the token, a source and target address should be selected. The source address should ideally be on the default chain (used to create the token) and one of the accounts chosen for the initial state, because it will already have some initial tokens to send.

First, a node service for the current wallet has to be started:

PORT=8080
linera service --port $PORT &

Using GraphiQL

  • Navigate to http://localhost:8080/chains/$CHAIN_1/applications/$APP_ID.
  • To get the current balance of user $OWNER_1, run the query:
    query{
        accounts {
            entry(
                key: "7136460f0c87ae46f966f898d494c4b40c4ae8c527f4d1c0b1fa0f7cff91d20f"
            ) {
                value
            }
        }
    }
  • To get the current balance of user $OWNER_2, run the query:
    query{
        accounts {
            entry(
                key: "598d18f67709fe76ed6a36b75a7c9889012d30b896800dfd027ee10e1afd49a3"
            ) {
                value
            }
        }
    }
  • To transfer 50 tokens from $OWNER_1 to $OWNER_2
    mutation {
        transfer(
            owner: "7136460f0c87ae46f966f898d494c4b40c4ae8c527f4d1c0b1fa0f7cff91d20f",
            amount: "50.",
            targetAccount: {
                chainId: "e476187f6ddfeb9d588c7b45d3df334d5501d6499b3f9ad5595cae86cce16a65",
                owner: "598d18f67709fe76ed6a36b75a7c9889012d30b896800dfd027ee10e1afd49a3"
            }
        )
    }
  • To get the new balance of user $OWNER_1, run the query:
    query{
        accounts {
            entry(
                key: "7136460f0c87ae46f966f898d494c4b40c4ae8c527f4d1c0b1fa0f7cff91d20f"
            ) {
                value
            }
        }
    }
  • To get the new balance of user $OWNER_2, run the query:
    query{
        accounts {
            entry(
                key: "598d18f67709fe76ed6a36b75a7c9889012d30b896800dfd027ee10e1afd49a3"
            ) {
                value
            }
        }
    }

Using web frontend

Installing and starting the web server:

cd web-frontend
npm install --no-save

# Start the server but not open the web page right away.
BROWSER=none npm start &

Web UIs for specific accounts can be opened by navigating URLs of the form http://localhost:3000/$CHAIN?app=$APP_ID&owner=$OWNER&port=$PORT where

  • the path is the ID of the chain where the account is located.
  • the argument app is the token application ID obtained when creating the token.
  • owner is the address of the chosen user account (owner must be have permissions to create blocks in the given chain).
  • port is the port of the wallet service (the wallet must know the secret key of owner).

In this example, two web pages for OWNER_1 and OWNER_2 can be opened by navigating these URLs:

echo "http://localhost:3000/$CHAIN_1?app=$APP_ID&owner=$OWNER_1&port=$PORT"
echo "http://localhost:3000/$CHAIN_1?app=$APP_ID&owner=$OWNER_2&port=$PORT"

OWNER_2 doesn't have the applications loaded initially. Using the first page to transfer tokens from OWNER_1 to OWNER_2 at CHAIN_2 will instantly update the UI of the second page.

About

Repository for building a fungible app with Linera step-by-step.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages

  • Rust 57.4%
  • JavaScript 35.1%
  • CSS 4.9%
  • HTML 2.6%