Examples of a SRC 20 contract in Sway
contract;
use standards::src20::{SetDecimalsEvent, SetNameEvent, SetSymbolEvent, SRC20, TotalSupplyEvent,};
use std::{auth::msg_sender, string::String};
configurable {
/// The total supply of coins for the asset minted by this contract.
TOTAL_SUPPLY: u64 = 100_000_000,
/// The decimals of the asset minted by this contract.
DECIMALS: u8 = 9u8,
/// The name of the asset minted by this contract.
NAME: str[7] = __to_str_array("MyAsset"),
/// The symbol of the asset minted by this contract.
SYMBOL: str[5] = __to_str_array("MYTKN"),
}
impl SRC20 for Contract {
/// Returns the total number of individual assets minted by a contract.
///
/// # Additional Information
///
/// For this single asset contract, this is always one.
///
/// # Returns
///
/// * [u64] - The number of assets that this contract has minted.
///
/// # Examples
///
/// ```sway
/// use src20::SRC20;
///
/// fn foo(contract_id: ContractId) {
/// let src_20_abi = abi(SRC20, contract_id);
/// let assets = src_20_abi.total_assets();
/// assert(assets == 1);
/// }
/// ```
#[storage(read)]
fn total_assets() -> u64 {
1
}
/// Returns the total supply of coins for the asset.
///
/// # Arguments
///
/// * `asset`: [AssetId] - The asset of which to query the total supply, this should be the default `SubId`.
///
/// # Returns
///
/// * [Option<u64>] - The total supply of an `asset`.
///
/// # Examples
///
/// ```sway
/// use src20::SRC20;
/// use std::constants::DEFAULT_SUB_ID;
///
/// fn foo(contract_id: ContractId) {
/// let src_20_abi = abi(SRC20, contract_id);
/// let supply = src_20_abi.total_supply(DEFAULT_SUB_ID);
/// assert(supply.unwrap() != 0);
/// }
/// ```
#[storage(read)]
fn total_supply(asset: AssetId) -> Option<u64> {
if asset == AssetId::default() {
Some(TOTAL_SUPPLY)
} else {
None
}
}
/// Returns the name of the asset.
///
/// # Arguments
///
/// * `asset`: [AssetId] - The asset of which to query the name, this should be the default `SubId`.
///
/// # Returns
///
/// * [Option<String>] - The name of `asset`.
///
/// # Examples
///
/// ```sway
/// use src20::SRC20;
/// use std::constants::DEFAULT_SUB_ID;
///
/// fn foo(contract_id: ContractId) {
/// let src_20_abi = abi(SRC20, contract_id);
/// let name = src_20_abi.name(DEFAULT_SUB_ID);
/// assert(name.is_some());
/// }
/// ```
#[storage(read)]
fn name(asset: AssetId) -> Option<String> {
if asset == AssetId::default() {
Some(String::from_ascii_str(from_str_array(NAME)))
} else {
None
}
}
/// Returns the symbol of the asset.
///
/// # Arguments
///
/// * `asset`: [AssetId] - The asset of which to query the symbol, this should be the default `SubId`.
///
/// # Returns
///
/// * [Option<String>] - The symbol of `asset`.
///
/// # Examples
///
/// ```sway
/// use src20::SRC20;
/// use std::constants::DEFAULT_SUB_ID;
///
/// fn foo(contract_id: ContractId) {
/// let src_20_abi = abi(SRC20, contract_id);
/// let symbol = src_20_abi.symbol(DEFAULT_SUB_ID);
/// assert(symbol.is_some());
/// }
/// ```
#[storage(read)]
fn symbol(asset: AssetId) -> Option<String> {
if asset == AssetId::default() {
Some(String::from_ascii_str(from_str_array(SYMBOL)))
} else {
None
}
}
/// Returns the number of decimals the asset uses.
///
/// # Arguments
///
/// * `asset`: [AssetId] - The asset of which to query the decimals, this should be the default `SubId`.
///
/// # Returns
///
/// * [Option<u8>] - The decimal precision used by `asset`.
///
/// # Examples
///
/// ```sway
/// use src20::SRC20;
/// use std::constants::DEFAULT_SUB_ID;
///
/// fn foo(contract_id: ContractId) {
/// let src_20_abi = abi(SRC20, contract_id);
/// let decimals = src_20_abi.decimals(DEFAULT_SUB_ID);
/// assert(decimals.unwrap() == 9u8);
/// }
/// ```
#[storage(read)]
fn decimals(asset: AssetId) -> Option<u8> {
if asset == AssetId::default() {
Some(DECIMALS)
} else {
None
}
}
}
abi EmitSRC20Events {
fn emit_src20_events();
}
impl EmitSRC20Events for Contract {
fn emit_src20_events() {
// Metadata that is stored as a configurable should only be emitted once.
let asset = AssetId::default();
let sender = msg_sender().unwrap();
log(SetNameEvent {
asset,
name: Some(String::from_ascii_str(from_str_array(NAME))),
sender,
});
log(SetSymbolEvent {
asset,
symbol: Some(String::from_ascii_str(from_str_array(SYMBOL))),
sender,
});
log(SetDecimalsEvent {
asset,
decimals: DECIMALS,
sender,
});
log(TotalSupplyEvent {
asset,
supply: TOTAL_SUPPLY,
sender,
});
}
}