Infos blockchain, cryptos & NFT en français pour les Sysadmins GNU/Linux francophones et autres crypto enthousiastes. SysAdmInCrypto

Infos blockchain, cryptos & NFT en français pour les Sysadmins GNU/Linux francophones et autres crypto enthousiastes.

31 March 2021

Chats Lunaires: Le Périple, deuxième partie

un Chat Lunaire Lors de notre précédante exploration, nous avions vu comment était généré un Chat Lunaire. A présent voyons comment fonctionne un wrapper, qui annonce emballer notre chat, le normaliser en NFT ERC721… Alors que la réalité est toute autre ! Il veut le cryogéniser et le cloner ! Voyez plus bas, la suite va vous étonner !

Le NFT ERC721

Avant d’entrer un peu plus dans les détails du wrapper, attardons-nous sur ce qu’est un ERC721, puisqu’il va créer un token de type ERC721 à partir d’un MoonCat.
Traduisons l’introduction de cette norme : “Le standard suivant permet l’implémentation d’une API standard au sein des smart contracts. Ce standard fournit des fonctionnalités de base pour traquer et transférer des NFT.
Cette norme permet donc de définir des des NFT standardisés, simplifiant les échanges sur les places de marché telles que Opensea et Rarible, à travers la définition de méthodes et attributs génériques. Si l’objet est conforme, il est également visible dans le wallet depuis etherscan :

Mais revenons à notre wrapper, dont la tâche sera de “dresser” les Chats Lunaires selon la norme ERC721, tout en en conservant leurs attributs. Je mets le verbe “dresser” entre guillemets, car tout amateur de Chat qui se respecte est bien conscient qu’un Chat ne se laissera jamais “dresser”. Surtout s’il est issu d’un smart contract sauvage…

Le wrapper

Avant de commencer, rappelons-nous la procédure de JR_Kunz pour wrapper les MoonCats évoqué dans notre premier billet. Traduction libre :

  1. Activer dans le contrat sur la page etherscan de MoonCatsRescue 12. makeAdoptionOffer, avec comme paramètre le catId et l’adresse du contrat du wrapper,
  2. Activer la fonction wrap() du wrapper le catId

Étudions à présent un extrait de code de Smart Contract MoonCatsWrapped à partir de la ligne 1800, soit la ligne 1 de notre extrait.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
contract MoonCatsWrapped is ERC721 {

    using Counters for Counters.Counter;
    Counters.Counter private _tokenIdTracker;

    MoonCatsRescue public _moonCats = MoonCatsRescue(0x60cd862c9C687A9dE49aecdC3A99b74A4fc54aB6);

    mapping(bytes5 => uint) public _catIDToTokenID; // dictionnaire (hash) convertissant catID vers ID ERC721
    mapping(uint => bytes5) public  _tokenIDToCatID; // dictionnaire de ID ERC721 vers catID
    string private _baseTokenURI;
    address public _owner = 0xD2927a91570146218eD700566DF516d67C5ECFAB;


    event Wrapped(bytes5 indexed catId, uint tokenID);
    event Unwrapped(bytes5 indexed catId, uint tokenID);

    constructor() ERC721("Wrapped MoonCatsRescue", "WMCR") {}

    function setBaseURI(string memory _newBaseURI) public {
        require(_msgSender() == _owner);
        _baseTokenURI = _newBaseURI;
    }

    function renounceOwnership() public {
        require(_msgSender() == _owner);
        _owner = address(0x0);
    }


    function _baseURI() public view virtual returns (string memory) {
        return _baseTokenURI;
    }


    function wrap(bytes5 catId) public {
        MoonCatsRescue.AdoptionOffer memory offer = _moonCats.adoptionOffers(catId);
        require(offer.seller == _msgSender()); //seul le propriétaire peut emballer son Chat
        _moonCats.acceptAdoptionOffer(catId);


        //Vérifie si le chat n'est pas déjà emballé
        uint tokenID = _catIDToTokenID[catId];
        uint tokenIDToAssign = tokenID;

        if (tokenID == 0) {
            tokenIDToAssign = _tokenIdTracker.current();
            _tokenIdTracker.increment();
            _catIDToTokenID[catId] = tokenIDToAssign;
            _tokenIDToCatID[tokenIDToAssign] = catId;
        }
        _mint(_msgSender(), tokenIDToAssign);
        emit Wrapped(catId, tokenIDToAssign);

    }

    function unwrap(uint256 tokenID) public {
        bytes5 catId = _tokenIDToCatID[tokenID];
        address owner = ownerOf(tokenID);
        require(owner == _msgSender()); //seul le propriétaire peut déballer son chat
        _moonCats.giveCat(catId, owner);
        _burn(tokenID); // on brûle le chat ERC721 🔥😿🔥
        emit Unwrapped(catId, tokenID); // on dégèle le Chat initial ❄️
    }

}

wrap()

Exemple de transaction. L’onglet (Logs) permet de voir les paramètres utilisés, en particulier l’initiateur de la transaction, le catID et le tokenID correspondant qui lui assigné.

Dans le wallet du contrat de wrap, nous pouvons observer les Chats cryogénisés (càd gelés dans le compte du contrat jusqu’à l’appel d’un unwrap())

unwrap()

Exemple de transaction. Pour retrouver l’appel à unwrap et connaître les paramètres TokenID et catID, voir en bas de page de l’onglet Logs(5).

Remonter l’historique d’un Chat

A partir d’un wallet possédant un Chat (par exemple sur Rarible) ou Opensea, nous pouvons remonter l’historique, à l’aide d’etherscan. Nous pouvons également récupérer son TokenID et interroger le contrat ; fonctions 5 et 11 par exemple.

Ici le 7519. Si à partir du TokenID nous pouvons obtenir le catId, nous pouvons aussi aller glaner des informations sur le contrat mooncatrescue (attention à la présentation des valeurs ; le TokenID est un uint256, donc un entier non signé, alors que le catId, un bytes5, doit être préfixé de 0x)

Aller plus loin (en anglais)

Categories: NFT - mooncats - etherscan - smartcontracts