Skip to main content

Token Standards

WeilChain provides standards for creating fungible and non-fungible tokens. The following documentation explains the core principles behind these token types, their components, common functions, and usage.

When we talk about a token, we may be talking about the set of all such tokens or a subset of units of it. For example, we can say that "Bitcoin is a cryptocurrency" or we can say that "Alice's transferred 3 Bitcoins to Bob". To avoid confusion, here we differentiate the two cases by calling the firs t a token class and the latter simply tokens.

What are Fungible and Non-Fungible Tokens?

Fungible Tokens

Fungible tokens are classes of interchangeable assets, with identical value and properties. Each unit of some fungible token class is identical to another, meaning holders can exchange one unit for another without any loss in value or change in functionality. Examples include cryptocurrencies and utility tokens, like Bitcoin, where each coin unit holds the same value and properties.

Non-Fungible Tokens (NFTs)

Non-fungible tokens are classes of unique assets and are not necessarily interchangeable on a 1:1 basis. Each non-fungible token represents a distinct item with unique properties and identifiers, making it ideal for representing digital art, collectibles, and other individual assets. Each token's uniqueness is tracked via an ID.

Structure of Tokens

Fungible Token Overview

In a WeilChain, a fungible token class is defined by an Applet that instantiates the FungibleToken type, defined in the Fungible Token standard and available in the Contract SDK.

A FungibleToken instance is defined by:

  • Token Name: a descriptive name of the token;
  • Token Symbol: a short code, e.g., WRC, that represents the token;
  • Decimals: the number of decimals the token can be subdivided into; and,
  • Total Supply: the number of tokens already minted;

Within the same class, all tokens are identical in type and value and therefore need not be tracked individually, as long as their numbers are tracked. Internally, FungibleToken uses the Ledger to keep balances for every account.

Balances are changed by transferring tokens from a source account to a destination account. Transfers can be performed by the owner of the source account or by an authorized agent.

The following functions are used to query balances and allowances (transfer authorizations), to modify allowances, and to trigger transfers:

  • balanceOf(address): provides the balance of tokens for a specified address;
  • transfer(address, uint256): Transfers a specified number of tokens to a given address.
  • approve(address, uint256): Authorizes a spender to withdraw a specified amount from the caller's account.
  • allowance(address, address): Returns the remaining number of tokens that a spender is allowed to withdraw from an account.
  • transferFrom(address, address, uint256): Allows a spender to transfer tokens from one address to another within the approved limit.

When defining a new fungible token class, these methods, exported by the FungibleToken must be implemented and re-exported, without changing their signatures. Most of the time this consists in simply delegating the call to the FungibleToken instance. This ensures that the new tokens can be transferred, approved, and queried with consistency across all contracts, making it easier to integrate the tokens with wallets, exchanges, and dApps.

Method mint, on the other hand, probably shouldn't be re-exported, as minting should be well controlled and accompanied by further logic. This can be accomplished using new methods.

Non-Fungible Token Overview

In a WeilChain, a non-fungible token class is defined by an Applet that instantiates the NonFungibleToken type, defined in the Non-Fungible Token standard and available in the Contract SDK.

A NonFungibleToken instance is defined solely by its name.

The creation of tokens in a class, or minting, may be performed all at once, during the class instantiation (e.g. a non-modifiable collection of monkey drawings) or at a later moment (e.g., to represent real world assets that get "digitized").

Each NFT is defined by:

  • Token Name: (string) a short name for this NFT;
  • Token Title: (string) a title for the asset which this NFT represents;
  • Token Description: (string) additional data associated with each token (e.g., a human readable description of the NFT or a resource locator to where a a description lies, off-chain);
  • Token Payload: (string) the actual contents of the NFT or a resource locator to where the contents lie.

Since every token is unique inside the class, they are tracked individually. This is done by NonFungibleToken using the Ledger.

Tokens are created using method

mint(token {name:string, title:string, description:string, payload:string}, tokenId: string)

Minted tokens are transferred individually from a source account to a destination account. Transfers may be performed by the owner of the source account or by an authorized agent.

The following functions are used to query balances and allowances (transfer authorizations), to modify allowances, and to trigger transfers:

  • balanceOf(address: string): provides the number of NFTs owned by a given address.
  • ownerOf(tokenId: string): returns the owner of a specified token Id.
  • details(tokenId: string): returns the name, title, description and payload of the specified token Id.
  • transfer(toAdd: string, tokenId: string): transfers the specified token to the specified address, if owned by the caller;
  • approve(spender: string, tokenId: string): approves address spender to transfer token tokenId on behalf of the owner caller;
  • transferFrom(fromAddr: string, toAddr: string, tokenId: string): transfers ownership of token tokenId from one address fromAddr to address toAddr, checking for ownership and authorization;
  • setApproveForAll(spender: string, approval: bool): approves or revokes the approval for the address spender to transfer all tokens of caller/owner.
  • get_approved(tokenId: string): lists the addresses that may "spend" token tokenId
  • isApprovedForAll(owner: string, spender: String): checks if address owner has given address spender an approve for all.

When defining a new non-fungible token class, these methods, exported by NonFungibleToken must be implemented and re-exported, without changing their signatures. Most of the time this consists in simply delegating the call to the FungibleToken instance. This ensures that the new tokens can be transferred, approved, and queried with consistency across all contracts, making it easier to integrate the tokens with wallets, exchanges, and dApps.

Method mint, on the other hand, probably shouldn't be re-exported, as minting should be well controlled and accompanied by further logic. This can be accomplished using new methods.

Usage of Fungible and Non-Fungible tokens

  • Fungible Token Use Cases

    • Stablecoins: Pegged tokens that hold value against an external asset, often used in payments or value preservation.
    • Utility Tokens: Used within a specific platform, granting holders access to services, products, or rewards.
    • Governance Tokens: Enable token holders to vote on decisions within a decentralized ecosystem.
    • Incentives and Rewards: tokens can be used as rewards within games or platforms, adding economic incentives.
  • Non-Fungible Token Use Cases

    • Digital Art and Collectibles: Each NFT can represent a unique piece of art or collectible, allowing creators to sell unique digital assets.
    • Gaming Assets: In-game items like weapons, characters, or plots of land are often represented as NFTs, allowing users to trade, sell, or use them across compatible games.
    • Real Estate and Property Ownership: WRC721 tokens can represent real estate deeds, property ownership, and other tangible assets.
    • Identity and Certification: NFTs can represent digital certificates, licenses, or achievements, proving ownership and authenticity of various credentials.

Summary

WeilChains offer standards and base implementations to create, manage, and integrate fungible and non-fungible tokens into Web3.0 applications. These tokens open possibilities for innovative applications across finance, gaming, art, and real-world asset representation, enabling secure and efficient digital asset management.