* Support repeated destroys to safely destroy large assets * require freezing accounts before destroying * support only deleting asset as final stage when there's no assets left * pre: introduce the RemoveKeyLimit config parameter * debug_ensure empty account in the right if block * update to having separate max values for accounts and approvals * add tests and use RemoveKeyLimit constant * add useful comments to the extrinsics, and calculate returned weight * add benchmarking for start_destroy and finish destroy * push failing benchmark logic * add benchmark tests for new functions * update weights via local benchmarks * remove extra weight file * Update frame/assets/src/lib.rs Co-authored-by: joe petrowski <25483142+joepetrowski@users.noreply.github.com> * Update frame/assets/src/types.rs Co-authored-by: joe petrowski <25483142+joepetrowski@users.noreply.github.com> * Update frame/assets/src/lib.rs Co-authored-by: joe petrowski <25483142+joepetrowski@users.noreply.github.com> * effect some changes from codereview * use NotFrozen error * remove origin checks, as anyone can complete destruction after owner has begun the process; Add live check for other extrinsics * fix comments about Origin behaviour * add AssetStatus docs * modularize logic to allow calling logic in on_idle and on_initialize hooks * introduce simple migration for assets details * reintroduce logging in the migrations * move deposit_Event out of the mutate block * Update frame/assets/src/functions.rs Co-authored-by: Muharem Ismailov <ismailov.m.h@gmail.com> * Update frame/assets/src/migration.rs Co-authored-by: Muharem Ismailov <ismailov.m.h@gmail.com> * move AssetNotLive checkout out of the mutate blocks * rename RemoveKeysLimit to RemoveItemsLimit * update docs * fix event name in benchmark * fix cargo fmt. * fix lint in benchmarking * Empty commit to trigger CI * Update frame/assets/src/lib.rs Co-authored-by: Oliver Tale-Yazdi <oliver.tale-yazdi@parity.io> * Update frame/assets/src/lib.rs Co-authored-by: Oliver Tale-Yazdi <oliver.tale-yazdi@parity.io> * Update frame/assets/src/functions.rs Co-authored-by: Oliver Tale-Yazdi <oliver.tale-yazdi@parity.io> * Update frame/assets/src/functions.rs Co-authored-by: Oliver Tale-Yazdi <oliver.tale-yazdi@parity.io> * Update frame/assets/src/functions.rs Co-authored-by: Oliver Tale-Yazdi <oliver.tale-yazdi@parity.io> * Update frame/assets/src/lib.rs Co-authored-by: Oliver Tale-Yazdi <oliver.tale-yazdi@parity.io> * Update frame/assets/src/functions.rs Co-authored-by: Oliver Tale-Yazdi <oliver.tale-yazdi@parity.io> * effect change suggested during code review * move limit to a single location * Update frame/assets/src/functions.rs Co-authored-by: joe petrowski <25483142+joepetrowski@users.noreply.github.com> * rename events * fix weight typo, using rocksdb instead of T::DbWeight. Pending generating weights * switch to using dead_account.len() * rename event in the benchmarks * empty to retrigger CI * trigger CI to check cumulus dependency * trigger CI for dependent cumulus * Update frame/assets/src/migration.rs Co-authored-by: Oliver Tale-Yazdi <oliver.tale-yazdi@parity.io> * move is-frozen to the assetStatus enum (#12547) * add pre and post migration hooks * update do_transfer logic to add new assert for more correct error messages * trigger CI * switch checking AssetStatus from checking Destroying state to checking live state * fix error type in tests from Frozen to AssetNotLive * trigger CI * change ensure check for fn reducible_balance() * change the error type to Error:<T,I>::IncorrectStatus to be clearer * Trigger CI Co-authored-by: joe petrowski <25483142+joepetrowski@users.noreply.github.com> Co-authored-by: parity-processbot <> Co-authored-by: Muharem Ismailov <ismailov.m.h@gmail.com> Co-authored-by: Oliver Tale-Yazdi <oliver.tale-yazdi@parity.io>
Assets Module
A simple, secure module for dealing with fungible assets.
Overview
The Assets module provides functionality for asset management of fungible asset classes with a fixed supply, including:
- Asset Issuance
- Asset Transfer
- Asset Destruction
To use it in your runtime, you need to implement the assets assets::Config.
The supported dispatchable functions are documented in the assets::Call enum.
Terminology
- Asset issuance: The creation of a new asset, whose total supply will belong to the account that issues the asset.
- Asset transfer: The action of transferring assets from one account to another.
- Asset destruction: The process of an account removing its entire holding of an asset.
- Fungible asset: An asset whose units are interchangeable.
- Non-fungible asset: An asset for which each unit has unique characteristics.
Goals
The assets system in Substrate is designed to make the following possible:
- Issue a unique asset to its creator's account.
- Move assets between accounts.
- Remove an account's balance of an asset when requested by that account's owner and update the asset's total supply.
Interface
Dispatchable Functions
issue- Issues the total supply of a new fungible asset to the account of the caller of the function.transfer- Transfers anamountof units of fungible assetidfrom the balance of the function caller's account (origin) to atargetaccount.destroy- Destroys the entire holding of a fungible assetidassociated with the account that called the function.
Please refer to the Call enum and its associated variants for documentation on each function.
Public Functions
balance- Get the assetidbalance ofwho.total_supply- Get the total supply of an assetid.
Please refer to the Pallet struct for details on publicly available functions.
Usage
The following example shows how to use the Assets module in your runtime by exposing public functions to:
- Issue a new fungible asset for a token distribution event (airdrop).
- Query the fungible asset holding balance of an account.
- Query the total supply of a fungible asset that has been issued.
Prerequisites
Import the Assets module and types and derive your runtime's configuration traits from the Assets module trait.
Simple Code Snippet
use pallet_assets as assets;
use sp_runtime::ArithmeticError;
#[frame_support::pallet]
pub mod pallet {
use super::*;
use frame_support::pallet_prelude::*;
use frame_system::pallet_prelude::*;
#[pallet::pallet]
pub struct Pallet<T>(_);
#[pallet::config]
pub trait Config: frame_system::Config + assets::Config {}
#[pallet::call]
impl<T: Config> Pallet<T> {
pub fn issue_token_airdrop(origin: OriginFor<T>) -> DispatchResult {
let sender = ensure_signed(origin)?;
const ACCOUNT_ALICE: u64 = 1;
const ACCOUNT_BOB: u64 = 2;
const COUNT_AIRDROP_RECIPIENTS: u64 = 2;
const TOKENS_FIXED_SUPPLY: u64 = 100;
ensure!(!COUNT_AIRDROP_RECIPIENTS.is_zero(), ArithmeticError::DivisionByZero);
let asset_id = Self::next_asset_id();
<NextAssetId<T>>::mutate(|asset_id| *asset_id += 1);
<Balances<T>>::insert((asset_id, &ACCOUNT_ALICE), TOKENS_FIXED_SUPPLY / COUNT_AIRDROP_RECIPIENTS);
<Balances<T>>::insert((asset_id, &ACCOUNT_BOB), TOKENS_FIXED_SUPPLY / COUNT_AIRDROP_RECIPIENTS);
<TotalSupply<T>>::insert(asset_id, TOKENS_FIXED_SUPPLY);
Self::deposit_event(Event::Issued(asset_id, sender, TOKENS_FIXED_SUPPLY));
Ok(())
}
}
}
Assumptions
Below are assumptions that must be held when using this module. If any of them are violated, the behavior of this module is undefined.
- The total count of assets should be less than
Config::AssetId::max_value().
Related Modules
License: Apache-2.0