#near #token #owner #events #smart-contracts #slot #macro

near-sdk-contract-tools

为 NEAR 协议上开发智能合约提供有用的函数和宏

9 个稳定版本 (3 个主要版本)

3.0.2 2024 年 5 月 14 日
3.0.1 2024 年 5 月 9 日
2.1.0 2023 年 10 月 30 日
1.1.1 2023 年 11 月 6 日
0.7.2 2022 年 12 月 16 日

#1128 in 神奇豆

Download history 5/week @ 2024-04-10 30/week @ 2024-04-17 21/week @ 2024-04-24 8/week @ 2024-05-01 381/week @ 2024-05-08 84/week @ 2024-05-15 58/week @ 2024-05-22 32/week @ 2024-05-29 27/week @ 2024-06-05 37/week @ 2024-06-12 16/week @ 2024-06-19 8/week @ 2024-06-26 35/week @ 2024-07-03 9/week @ 2024-07-10 9/week @ 2024-07-17 9/week @ 2024-07-24

68 每月下载次数

GPL-3.0 OR Apache-2.0

260KB
5K SLoC

near-sdk-contract-tools

NFT

use near_sdk::near;
use near_sdk_contract_tools::nft::*;

#[derive(Default, NonFungibleToken)]
#[near(contract_state)]
pub struct MyNftContract {}

#[near]
impl MyNftContract {
    #[init]
    pub fn new() -> Self {
        let mut contract = Self {};

        contract.set_contract_metadata(&ContractMetadata::new("My NFT", "MNFT", None));

        contract
    }
}

FT

use near_sdk::near;
use near_sdk_contract_tools::ft::*;

#[derive(Default, FungibleToken)]
#[near(contract_state)]
pub struct MyFtContract {}

#[near]
impl MyFtContract {
    #[init]
    pub fn new() -> Self {
        let mut contract = Self {};

        contract.set_metadata(&ContractMetadata::new("My Fungible Token", "MYFT", 24));

        contract
    }
}

这是什么?

此包是 NEAR 智能合约开发中常见工具和模式的集合

  • 存储费用管理。
  • 托管模式和 derive 宏。
  • 所有者模式和 derive 宏。
  • 暂停模式和 derive 宏。
  • 基于角色的访问控制。
  • NEP 标准的 derive 宏

不要与包含标准化 NEP 官方实现的 near-contract-standards 混淆。这个 crate 旨在与 near-contract-standards 相辅相成。

你可以将这个常用工具和模式的集合(主要是以 derive 宏 的形式)视为 NEAR 的某种 OpenZeppelin

小贴士:使用合约向导为您下一个项目生成起始代码。

安装

cargo add near-sdk-contract-tools

示例

另请参阅:[完整的集成测试](https://github.com/near/near-sdk-contract-tools/blob/71ba97b77e4c226fdf24f1b516e5a1349068db80/tests/macros/mod.rs)。

所有者

use near_sdk::{near, AccountId, PanicOnDefault};
use near_sdk_contract_tools::{owner::Owner, Owner};

#[derive(Owner, PanicOnDefault)]
#[near(contract_state)]
struct Contract {
    // ...
}

#[near]
impl Contract {
    #[init]
    pub fn new(owner_id: AccountId) -> Self {
        let mut contract = Self {
            // ...
        };

        Owner::init(&mut contract, &owner_id);

        contract
    }

    pub fn owner_only(&self) {
        Self::require_owner();

        // ...
    }
}

Owner派生宏向区块链公开以下方法

fn own_get_owner(&self) -> Option<AccountId>;
fn own_get_proposed_owner(&self) -> Option<AccountId>;
fn own_renounce_owner(&mut self);
fn own_propose_owner(&mut self, account_id: Option<AccountId>);
fn own_accept_owner(&mut self);

事件

#[event]宏可以应用于结构体或枚举。

use near_sdk_contract_tools::{event, standard::nep297::Event};

#[event(standard = "nft", version = "1.0.0")]
pub struct MintEvent {
    pub owner_id: String,
    pub token_id: String,
}

let e = MintEvent {
    owner_id: "account".to_string(),
    token_id: "token_1".to_string(),
};

// Emits the event to the blockchain
e.emit();

可互换代币

要创建与NEP-141NEP-145NEP-148标准兼容的合约,该合约会发出符合标准的事件(NEP-297)。

use near_sdk::near;
use near_sdk_contract_tools::ft::*;

#[derive(Default, FungibleToken)]
#[near(contract_state)]
struct MyFt {}

#[near]
impl MyFt {
    #[init]
    pub fn new() -> Self {
        let mut contract = Self {};

        contract.set_metadata(&ContractMetadata::new("My Fungible Token", "MYFT", 24));

        contract
    }
}

每个标准也有独立的宏。

非可互换代币

使用NonFungibleToken派生宏实现NEP-145NEP-171NEP-177NEP-178NEP-181,并带有NEP-297事件。

use near_sdk::{near, PanicOnDefault};
use near_sdk_contract_tools::nft::*;

#[derive(NonFungibleToken, PanicOnDefault)]
#[near(contract_state)]
pub struct MyNft {}

宏组合

有时可能希望在一个合约中将多个宏的功能结合起来。所有宏都编写得可以在独立模式下工作,因此这应该基本上没有问题。但是,有时可能希望宏能够相互组合使用。例如,为了使可互换代币可暂停,可以使用可互换代币挂钩要求在执行代币转账之前先暂停合约

use near_sdk_contract_tools::{
    ft::*,
    pause::{*, hooks::Pausable},
    Pause,
};
use near_sdk::{near, PanicOnDefault};

#[derive(FungibleToken, Pause, PanicOnDefault)]
#[fungible_token(all_hooks = "Pausable")]
#[near(contract_state)]
struct Contract {}

自定义Crates

如果您是库开发者,已经修改了一个near-sdk-contract-tools宏使用的crate(例如serdenear-sdk),或者正在以不同的名称使用crate,可以在宏中指定crate名称,如下所示

#[event(
    // ...
    crate = "near_sdk_contract_tools",
    macros = "near_sdk_contract_tools_macros",
    serde = "serde",
)]
// ...

#[derive(Owner)]
#[owner(
    // ...
    near_sdk = "near_sdk",
)]

其他提示

内部方法与外部方法

内部方法无法通过区块链调用。外部方法是公共的,可以被其他合约调用。

拉取模式

提出所有权(而不是直接转移)通常是一个好习惯,因为它可以防止您意外地将所有权转移到没有访问权的账户,从而损坏合约。

展开

cargo expand将生成一个包含所有宏已处理的大Rust文件

cargo install cargo-expand
cargo expand > expanded.rs

槽位

请参阅[源/slot.rs](https://github.com/near/near-sdk-contract-tools/blob/71ba97b77e4c226fdf24f1b516e5a1349068db80/src/slot.rs)。槽位是存储键的薄包装。

assert_one_yocto()

near_sdk::assert_one_yocto()是一个需要完整访问密钥(通过要求存入最小的NEAR单位之一yoctonear)的函数。

如果用户将他们的NEAR账户连接到dapp,dapp仍然无法调用调用assert_one_yocto()的函数,因为函数调用访问密钥不允许转账原生代币。这些函数将需要一个完整访问密钥的签名,通常涉及用户钱包中的确认屏幕。

贡献

设置

运行 git config core.hooksPath hooks/ 以设置提交钩子。

构建和测试

如果尚未安装,请安装 cargo-make

cargo install cargo-make cargo-nextest

运行测试

cargo nextest run
cargo test --doc
cd workspaces-tests
cargo make nextest

审计

本库的 1.0.0 版本已经由 Kudelski Security(2023 年 5 月)进行审计。

作者


(以前被称为 near-contract-tools。)

依赖项

约 5MB
约 102K SLoC