defuse_token_id/
imt.rs

1pub use defuse_nep245::TokenId;
2
3use std::{fmt, str::FromStr};
4
5use near_sdk::{
6    AccountId, near,
7    serde_with::{DeserializeFromStr, SerializeDisplay},
8};
9
10use crate::{TokenIdType, error::TokenIdError};
11
12// Intent mintable token - can be minted only by intents 'ImtMint'
13#[cfg_attr(any(feature = "arbitrary", test), derive(::arbitrary::Arbitrary))]
14#[derive(Clone, PartialEq, Eq, PartialOrd, Ord, Hash, SerializeDisplay, DeserializeFromStr)]
15#[serde_with(crate = "::near_sdk::serde_with")]
16#[near(serializers = [borsh])]
17pub struct ImtTokenId {
18    pub minter_id: AccountId,
19
20    pub token_id: TokenId,
21}
22
23impl ImtTokenId {
24    pub fn new(minter_id: impl Into<AccountId>, token_id: impl Into<TokenId>) -> Self {
25        Self {
26            minter_id: minter_id.into(),
27            token_id: token_id.into(),
28        }
29    }
30}
31
32impl std::fmt::Debug for ImtTokenId {
33    #[inline]
34    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
35        write!(f, "{}:{}", &self.minter_id, &self.token_id)
36    }
37}
38
39impl std::fmt::Display for ImtTokenId {
40    #[inline]
41    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
42        fmt::Debug::fmt(&self, f)
43    }
44}
45
46impl FromStr for ImtTokenId {
47    type Err = TokenIdError;
48
49    fn from_str(data: &str) -> Result<Self, Self::Err> {
50        let (minter_id, token_id) = data
51            .split_once(':')
52            .ok_or(strum::ParseError::VariantNotFound)?;
53        Ok(Self::new(minter_id.parse::<AccountId>()?, token_id))
54    }
55}
56
57impl From<&ImtTokenId> for TokenIdType {
58    #[inline]
59    fn from(_: &ImtTokenId) -> Self {
60        Self::Imt
61    }
62}
63
64#[cfg(test)]
65mod tests {
66    use super::*;
67
68    use defuse_test_utils::random::make_arbitrary;
69    use rstest::rstest;
70
71    #[rstest]
72    #[trace]
73    fn display_from_str_roundtrip(#[from(make_arbitrary)] token_id: ImtTokenId) {
74        let s = token_id.to_string();
75        let got: ImtTokenId = s.parse().unwrap();
76        assert_eq!(got, token_id);
77    }
78}