Comment rédiger un contrat intelligent pour ICO en 5 minutes



Bonjour à tous! Dans cet article, je vais vous expliquer comment lancer un contrat de collecte d'argent intelligent pour votre ICO sur Ethereum en 5 minutes et plusieurs commandes dans le terminal. Cet essai vous fera potentiellement économiser des dizaines de milliers de dollars américains, car n'importe quel programmeur - et pas un programmeur aussi - pourra lancer un contrat intelligent audité et sécurisé (au lieu de payer 15 000 $ - 75 000 $ pour le développement). En bref, vous pouvez envoyer de l'argent à ce contrat intelligent et recevoir des jetons ERC20 pour cela. On peut dire que cet article est un recueil de toute l'expérience que j'ai acquise en lançant une ICO pour mon projet.

Sur Internet, ceux-ci sont déjà remplis d'articles sur les contrats intelligents, mais dès que vous commencez à en rédiger un, vous découvrez que les informations sont répétées partout, et il n'y a tout simplement pas de tutoriels sur la façon de tromper votre ERC20, ou ils sont déjà obsolètes. Soit dit en passant, pour que cet article reste pertinent, je vais essayer d'indiquer les endroits potentiels où il peut devenir obsolète (et comment y remédier). C'est parti!

Solidité


C'est le nom de la langue principale que l'équipe du kéfir a développée pour lancer des contrats intelligents. Si vous êtes programmeur, passez simplement en revue la documentation du langage - c'est indécemment simple. Soit dit en passant, ils ont rendu les choses simples, de sorte qu'il était plus difficile de se tromper en écrivant un contrat intelligent. Donc, absolument tout programmeur, au moins au niveau junior, pourra le comprendre. Il ne sert à rien de payer d'énormes sommes d'argent aux développeurs qui connaissent la solidité - il sera beaucoup moins cher de former un développeur existant.

Contrats intelligents


... et tout ce que vous devez savoir à leur sujet. Ignorez cette section si vous n'êtes pas programmeur. Un contrat intelligent est un morceau de code. En principe, il s'agit d'une classe de solidité (OOP, oui), qui a deux types de fonctions: à changement d'état et non à changement d'état. Eh bien, pour exécuter des fonctions dans un contrat intelligent simplement en lui envoyant du kéfir, vous devez marquer comme payable cette fonction.

State est un entrepôt de données, blockchain, EPT. Les contrats peuvent changer la blockchain (état, stockage) - mais pour changer la blockchain, vous devez payer le kéfir aux mineurs. La façon dont ils partageront le kéfir ne sera pas analysée dans le cadre de cet article. Le paiement aux mineurs pour l'exécution d'un code à changement d'état s'appelle Gas. Si quelqu'un de l'extérieur jette du kéfir à l'adresse d'un contrat intelligent avec un appel à une fonction marquée payable mais non marquée Constant , View ou Pure , le montant nécessaire de kéfir pour le paiement aux mineurs sera déduit du montant envoyé. Généralement, dans les jetons ERC20, ce sont des fonctions qui distribuent l'expéditeur de jeton pour le kéfir ou transfèrent des jetons d'un détenteur de jeton à un autre.

Et si vous marquez une fonction dans le contrat avec les mots Constant ou View (ils signifient la même chose, ils ne vous permettent que de lire l'état) ou Pure (la même chose, vous ne lisez même pas l'état), alors vous n'aurez même pas besoin de dépenser du kéfir pour cette fonction! Je dirai même plus que ces fonctions n'ont pas besoin d'être appelées par des transactions - après tout, n'importe quel client de yaourt peut théoriquement l'exécuter à la maison - et personne n'a plus besoin de le savoir (après tout, rien n'est écrit dans la blockchain).

Et il y a deux choses importantes dans la solidité: l'héritage multiple et les modificateurs de fonction. Vous devez également les connaître.

Le premier - juste des contrats peuvent être hérités simultanément de plusieurs classes telles que TimedCrowdsale , CappedCrowdsale , MintedCrowdsale , Ownable - en même temps, les fonctions des constructeurs sont également lancées l'une après l'autre - mais je l'expliquerai plus tard à titre d'exemple.

La seconde est la possibilité de créer des fonctions qui seront ensuite insérées dans d'autres fonctions. C'est comme une simple encapsulation, juste un peu plus flexible - c'est littéralement un modèle de fonction. Lorsque vous créez un modificateur, vous écrivez le caractère spécial _ où vous voulez dire le code d'une fonction utilisant ce modificateur. Autrement dit, les modificateurs ne sont pas uniquement des fonctionnalités encapsulées qui renvoient une valeur; il s'agit d'un modèle de fonction lorsque le code d'un modificateur est littéralement inséré dans une fonction utilisant ce modificateur.

Passons à la pratique.

Environnement de cuisson


Si vous ne savez pas ce qu'est un terminal, lisez cet article ici . Si vous êtes sous Windows, définissez-vous un terminal via WLS. Si vous connaissez déjà le terminal, continuons. Aussi, mettez-vous immédiatement Node.js - il sera nécessaire pour les prochaines étapes. Il est préférable d'installer LTS, mais, en fait, cela ne fait aucune différence laquelle des versions modernes du nœud installer.

La première chose que nous installons et démarrons immédiatement le processus de synchronisation des blocs est geth . En bref, il s'agit d'un utilitaire écrit en Go qui nous permettra d'exécuter le nœud éther sur l'ordinateur local et de nous connecter aux réseaux de test et réels. Vous pouvez installer via des programmes d'installation , mais je vous recommande vivement de vous geth immédiatement dans Terminal, comme décrit ici . Vous pouvez vérifier si vos normes geth sont geth exécutant la commande dans le terminal:

 geth version 

Si vous avez craché la version geth - tout est ajouré, continuez le tutoriel. Sinon - mauvais, correct; il semble que vous devrez faire des ébats avec le terminal et votre système d'exploitation - mais ce n'est pas la première fois que vous le comprenez. Comment installer geth, exécutez la commande dans le terminal:

 geth --testnet console 

Cela lancera le processus de synchronisation de votre nœud avec le serveur de test, dont les blocs peuvent être consultés ici . Vous pouvez vérifier si vous vous êtes synchronisé avec le réseau dans la console geth en geth :

 eth.blockNumber #  0 —     eth.syncing #     false,     

Le processus de synchronisation m'a pris de 1 à 4 heures - quand comment. De plus, en plus de la synchronisation des blocs, vous devrez également attendre la synchronisation des états - elle est souvent plus longue que la synchronisation des blocs. Vous pouvez également utiliser les geth avec l'indicateur --light - puis la synchronisation dure de quelques secondes à une minute et vous pouvez toujours déployer des contrats.

D'accord, nous avons installé le premier utilitaire - mettez le suivant. Nous devons mettre un analogue de geth , seulement une simulation de chaîne de blocs très locale - testrpc . Oui, nous avons 3 blockchains :

  • testrpc - simulation de blockchain locale; rapide, mais faux et stocké uniquement sur votre machine
  • geth --testnet est déjà une véritable blockchain, mais vous ne perdrez pas d'argent où vous pouvez obtenir du kéfir et tester gratuitement toutes geth --testnet
  • geth - mainnet, main, blockchain réel, kéfir réel; le tout de façon adulte, les erreurs ici sont les pertes de kéfir réel

En conséquence, nous allons démarrer le contrat de test avec testrpc , puis l'installer dans geth --testnet , puis le télécharger directement dans geth .

Nous testrpc en exécutant la commande suivante:

 npm install -g ethereumjs-testrpc 

Eh bien, ou il monte immédiatement avec une truffe, car maintenant testrpc sous l'aile de truffe et s'appelle ganache-cli . Bien que le diable le sache, tout fonctionnait testrpc avec vanilla testrpc . Et si ça marche, ne le touchez pas, comme on m'a enseigné à l'académie intergalactique. Vous pouvez également l'exécuter pour vérifier l'installation en enregistrant la truffle dans la console, mais la blockchain de test est déjà synchronisée avec nous - ne le dérange pas.

Eh bien, compris les chaînes de blocs? Il y a maintenant des nœuds et le test est même synchronisé? Nous mettons un utilitaire pratique pour travailler avec des contrats intelligents sur le kéfir - truffle , avec la commande suivante:

 npm install -g truffle truffle version #  ,  ,   

Truffle est un outil qui vous permet de conserver des contrats intelligents dans différents fichiers, d'importer d'autres fichiers et de compiler également votre code de contrat intelligent en un seul bytecode (illisible par une personne), il trouve automatiquement un geth cours d'exécution local (test et réel ) ou testrpc , déployez votre contrat intelligent sur ce réseau. En outre, la vérification des erreurs dans votre code de contrat intelligent et les transactions récemment terminées aident également au débogage . Masthead, en bref.

À ce stade, vous devriez avoir installé: testrpc , geth , truffle - si l'un de ces éléments est manquant ou si la version ne crache pas sur la console sur demande, corrigez cela; sinon vous ne réussirez pas.

De plus, j'ai lancé un simple script bash qui va tout installer pour vous. Appelé comme ceci:

 source <(curl -s https://raw.githubusercontent.com/backmeupplz/eth-installer/master/install.sh) 

- mais je ne l'ai encore jamais testé, donc je ne suis pas sûr de ses performances. Cependant, je serai heureux de tirer des demandes.

Contrat Figash


Tout a déjà été inventé et écrit pour vous - c'est bien. Un petit bruant sera tout de même - mais je vais essayer de le minimiser. Nous utiliserons des contrats ERC20 prêts à l'emploi d'OpenZeppelin - c'est maintenant la norme de l'industrie, ils ont passé l'audit, et en effet ils utilisent tous leur code. Merci beaucoup pour votre contribution à l'open source.

Faites un cd dans un dossier sûr, puis écrivez:

 mkdir contract && cd contract 

Dans ce dossier, nous allons travailler. Créez un talon ici pour notre contrat intelligent:

 truffle init 

Trébucher, clairement. Nous avons maintenant deux dossiers très importants dans lesquels nous allons grimper: les contracts et les migrations . Le premier est le code de nos contrats, le second est le code de la truffe pour savoir quoi faire lors du déploiement de contrats sur la blockchain.

Ensuite, nous devons prendre le code de contrat intelligent actuel de npm et, en fait, démarrer le projet lui-même:

 npm init -y #     ( -y) npm install -E openzeppelin-solidity #       ( -E) 

Eh bien, le code des contrats intelligents d'OpenZeppelin est dans notre poche dans le dossier node_modules/openzeppelin-solidity/contracts . Maintenant, nous allons dans le dossier principal des contracts , supprimons tous les fichiers et ajoutez les fichiers MyToken.sol et MyCrowdsale.sol - naturellement, vous MyCrowdsale.sol vos contrats différemment. Le premier sera un contrat pour notre Token ERC20, et le second sera un contrat de notre ICO, qui acceptera le kéfir et distribuera MyToken gens. Cet article peut être obsolète, mais vous pouvez toujours voir comment OpenZeppelin vous suggère de créer des contrats dans leur référentiel . Voici à quoi MyToken.sol :

 pragma solidity ^0.4.23; // Imports import "../node_modules/openzeppelin-solidity/contracts/token/ERC20/MintableToken.sol"; // Main token smart contract contract MyToken is MintableToken { string public constant name = "My Token"; string public constant symbol = "MTKN"; uint8 public constant decimals = 18; } 

Bien - vous avez un contrat intelligent de votre propre jeton (changez simplement les noms dans les constantes)! Vous pouvez voir quel MintableToken héritage il y a de MintableToken - mais tout est aussi simple que possible là-bas. Il s'agit d'un jeton qui peut être émis (de l'anglais «Mint» - à mint), et seul le propriétaire a le droit de le délivrer, car le MintableToken est également hérité de Ownable . De plus, MintableToken hérite également des classes de jetons ERC20 écrites par OpenZeppelin, dans lesquelles l'interface ERC20 est implémentée:

 contract ERC20Basic { function totalSupply() public view returns (uint256); function balanceOf(address who) public view returns (uint256); function transfer(address to, uint256 value) public returns (bool); event Transfer(address indexed from, address indexed to, uint256 value); } 

Oui, vous avez ici toute l'interface ERC20. Est-ce difficile? Je ne pense pas. Il vous donne la possibilité de voir combien de jetons ont été émis, de vérifier le solde de l'adresse et de transférer des jetons vers une autre adresse en crachant un événement de transfert pour les clients de kéfir léger sur le réseau. Et tout cela, vous obtenez gratuitement dans votre MyToken.sol grâce au travail d'OpenZeppelin - ils sont super.

Et maintenant passons à la partie principale de notre ICO - nous devons accepter le kéfir et distribuer MyToken ! Voici à quoi ressemblera votre MyCrowdsale.sol :

 pragma solidity ^0.4.23; // Imports import "../node_modules/openzeppelin-solidity/contracts/crowdsale/emission/MintedCrowdsale.sol"; import "../node_modules/openzeppelin-solidity/contracts/crowdsale/distribution/RefundableCrowdsale.sol"; import "../node_modules/openzeppelin-solidity/contracts/crowdsale/validation/CappedCrowdsale.sol"; import "../node_modules/openzeppelin-solidity/contracts/token/ERC20/MintableToken.sol"; contract MyCrowdsale is CappedCrowdsale, RefundableCrowdsale, MintedCrowdsale { constructor( uint256 _openingTime, uint256 _closingTime, uint256 _rate, address _wallet, uint256 _cap, MintableToken _token, uint256 _goal ) public Crowdsale(_rate, _wallet, _token) CappedCrowdsale(_cap) TimedCrowdsale(_openingTime, _closingTime) RefundableCrowdsale(_goal) { //   ,  ,    // ,     require(_goal <= _cap); } } 

Tant bien que mal, qu'est-ce qui nous prend? Quoi, les garçons, les contrats intelligents? Notre vente publique de jetons hérite de trois des propriétés les plus populaires: elle a un capuchon rigide, qui ne peut plus être collecté; capuchon souple, ne recueillant pas quels esters sont retournés; heure de début et de fin de la vente de jetons. En fait, que faut-il d'autre pour le bonheur?

Les programmeurs, notez comment les constructeurs de plusieurs classes d'héritage sont organisés dans une rangée et obtenez des arguments du constructeur principal de MyCrowdsale . De plus, nous vérifions que la touche fixe est plus haute que la touche programmable - Ales Gut! Ne vous MyCrowdsale pas non MyCrowdsale paramètres MyCrowdsale constructeur MyCrowdsale - nous les passerons au stade du déploiement du contrat dans la truffe.

C'est tout - vous avez des contrats prêts à l'emploi de votre propre jeton ERC20 et même un contrat intelligent ICO, qui est configuré selon votre désir et distribue vos jetons pour le kéfir. En outre, il est pris en charge par tous les portefeuilles ERC20 - une erreur! Passons aux tests manuels et au déploiement.

Migrations


Comme je l'ai dit plus tôt, nous allons tester séquentiellement sur trois réseaux de blockchain, mais le processus de test avec des stylos sera toujours le même. Commençons par testrpc , puis passons à geth --testnet et continuons à geth . Sou phares, nous venons d'écrire le code, essayons de le compiler. Dans le dossier du projet, écrivez:

 truffle compile 

Si tout est compilé sans problème, vous verrez le build , qui contiendra le krakozyab pour la truffe afin qu'il puisse intégrer le bytecode de vos contrats intelligents dans la blockchain. Avant de déployer des contrats intelligents, nous devons dire à la truffe quoi faire. Le déploiement truffier des contrats intelligents s'appelle la migration - eh bien, restons-en à cette terminologie. Accédez à migrations/1_initial_migration.js et modifiez-le de la manière suivante:

 const token = artifacts.require("../contracts/MyToken.sol"); const crowdsale = artifacts.require("../contracts/MyCrowdsale.sol"); module.exports = function(deployer, network, accounts) { const openingTime = 1514764800; // 15  2018 const closingTime = 1561939200; // 1  2019 const rate = new web3.BigNumber(1); // 1   1  const wallet = '0x281055afc982d96fab65b3a49cac8b878184cb16'; // - const cap = 200 * 1000000; //  const goal = 100 * 1000000; //  return deployer .then(() => { return deployer.deploy(token); }) .then(() => { return deployer.deploy( crowdsale, openingTime, closingTime, rate, wallet, cap, token.address, goal ); }) .then(() => { // Crowdsale    var tokenContract = web3.eth.contract(token.abi).at(token.address); web3.eth.defaultAccount = web3.eth.accounts[0]; tokenContract.transferOwnership(crowdsale.address); }); }; 

Il s'agit du même fichier qui sera utilisé par la truffe pour déployer les contrats. Alors qu'est-ce qu'on fait ici? Tout d'abord, nous avons demandé la compilation de MyToken et MyCrowdsale . Ensuite, nous définissons les constantes avec tous les arguments de notre ICO - définissons les heures de début et de fin; combien de jetons les gens recevront pour 1 vey de kéfir (0.000000000000000001 eth = 1 wei; la définition des decimals indique combien de commandes wei sont nécessaires pour obtenir 1 de vos tokens nouvellement fabriqués); portefeuille, où viendra le kéfir obtenu de la vente; capuchon dur et capuchon souple. Veuillez noter que openingTime doit toujours être après l'heure du bloc actuel dans la blockchain - sinon votre contrat intelligent ne sera pas bloqué en raison de la vérification de la condition dans TimedCrowdsale . J'ai marché sur ce rake, et les transactions échouées ne peuvent pas être débitées du tout. Modifiez ces constantes comme vous le souhaitez.

La prochaine étape est précisément le déploiement de contrats intelligents. Rien d'intéressant ici: nous avons un objet deployer qui déploie des artefacts de contrat intelligent et y passe des arguments. Notez que MyToken est MyToken premier, puis seulement MyCrowdsale - et l'adresse du premier est passée dans le second comme argument.

Ensuite, la chose la plus intéressante est ce qu'ils n'écrivent ni dans la documentation ni dans les livres. Lorsque vous créez un MyToken partir d'un portefeuille, ce portefeuille devient le propriétaire de MyToken dans la superclasse Ownable - la même chose se produit avec MyCrowdsale . Si vous creusez profondément dans le MintableToken , vous pouvez voir que seul le Owner peut frapper des pièces! Et qui est le propriétaire de MyToken ? C'est vrai: l'adresse qui l'a bouleversé. Et qui enverra les demandes de frappe de pièces? Correct: contrat intelligent MyCrowdsale . Permettez-moi de vous rappeler que l'adresse qui a créé MyToken et MyCrowdsale sont deux adresses différentes.

Par conséquent, nous ajoutons la troisième étape de déploiement non orthodoxe, où l'adresse qui a défié les contrats ( web3.eth.accounts[0] ) appelle la fonction transferOwnership sur le contrat MyToken que MyCrowdsale possède MyToken et puisse frapper des pièces. Et MyCrowdsale est toujours la propriété de web3.eth.accounts[0] - donc tout est groupé.

Remarque sur web3.eth.accounts[0] : lors du déploiement d'un contrat intelligent, assurez-vous que geth ou testrpc ont le bon portefeuille dans web3.eth.accounts[0] - ne perdez pas la clé privée, bien que cela ne vous nuise en aucune façon, mais du coup le propriétaire devra faire quelque chose plus tard, mais la clé n'est plus là?
Dans testrpc , en règle générale, les comptes sont créés immédiatement au démarrage et ils sont immédiatement déverrouillés; cependant, sur un test et une véritable blockchain aérienne, cela vaut la peine de créer un compte via personal.newAccount() - puis réapprovisionnez cette adresse via Faucet sur la blockchain de test ou le vrai kéfir sur la vraie blockchain. Ne perdez pas votre mot de passe et vos clés privées.
En outre, vous pouvez ajouter un portefeuille existant à vos comptes en appelant web3.personal.importRawKey('pvt_key', 'password') , mais pour cela, vous devez appeler geth avec le paramètre supplémentaire --rpcapi="db,eth,net,web3,personal,web3" . Je pense que vous comprendrez.

Test et déploiement


Oui, les contrats sont prêts, les migrations sont écrites, il ne reste plus qu'à déployer et vérifier. geth (test et réel) et testrpc gérés de la même manière via la truffle console - je décrirai donc la méthode de vérification pour testrpc et vous dirai simplement comment activer geth après. Et donc, nous lançons la blockchain locale de test du kéfir:

 testrpc 

Hum ... c'est tout. Vous simulez la blockchain de kéfir localement.

Et afin de déployer sur la blockchain de test ether, au lieu de cette commande, vous obtiendrez geth --testnet --rpc . Et pour déployer sur la vraie chaîne de blocs d'éther, vous geth --rpc simplement geth --rpc . Le drapeau --rpc nécessaire pour que la truffe puisse se connecter. Les étapes de déploiement et de test suivantes sont plus ou moins les mêmes pour les trois types de blockchain. La seule chose est qu'après avoir exécuté le test ou la vraie blockchain via geth , il commencera à synchroniser les blocs - et cela peut prendre jusqu'à 4-5 heures sur une bonne connexion Internet. Une remarque à ce sujet figurait au tout début de l'article. Avant de déployer des contrats intelligents, je recommande d'attendre la synchronisation complète. De plus, la blockchain pèse entre 60 et 100 gigaoctets, alors préparez l'espace disque pour cela.
Assurez-vous également que web3.eth.accounts[0] déverrouillé. Vous pouvez généralement enregistrer testrpc dans la console, qui s'ouvre immédiatement, ou dans une fenêtre de terminal distincte dans la console, qui s'ouvre via la geth console : eth.unlockAccount(eth.accounts[0], ", ", 24*3600) - cela débloquera votre compte, ce qui devrait créer un contrat intelligent

Maintenant, ouvrez une nouvelle fenêtre Terminal ( testrpc ne testrpc pas testrpc - cela devrait fonctionner) et écrivez-la dans le dossier du projet:

 truffle migrate --reset 

Cette commande magique compilera un contrat intelligent (c'est-à-dire que vous n'avez pas besoin d'écrire une truffle compile chaque fois) et la déploiera sur le micro-serveur blockchain trouvé localement ouvert. Il convient de noter que si testrpc fait instantanément, le test et les vraies chaînes de blocs incluront la transaction dans les prochains blocs beaucoup plus longtemps. Après cela, vous devriez cracher quelque chose comme ça dans la console:

 Using network 'development'. Running migration: 1_initial_migration.js Running step... Replacing MyToken... ... 0x86a7090b0a279f8befc95b38fa8bee6918df30928dda0a3c48416454e2082b65 MyToken: 0x2dc35f255e56f06bd2935f5a49a0033548d85477 Replacing MyCrowdsale... ... 0xf0aab5d550f363478ac426dc2aff570302a576282c6c2c4e91205a7a3dea5d72 MyCrowdsale: 0xaac611907f12d5ebe89648d6459c1c81eca78151 ... 0x459303aa0b79be2dc2c8041dd48493f2d0e109fac19588f50c0ac664f34c7e30 Saving artifacts... 

Je pense que vous avez déjà réalisé que la console vous a donné les adresses des contrats intelligents MyToken et MyCrowdsale . C’est tout! Le contrat intelligent est intégré dans la blockchain dont vous avez ouvert le micro-serveur. Il ne reste plus qu'à vérifier que les jetons sont réellement distribués aux utilisateurs qui envoient du kéfir au contrat intelligent MyCrowdsale . Nous écrivons ce qui suit dans le terminal pour entrer dans la console de truffe:

 truffle console 

Nous écrivons ce qui suit dans la truffe maintenant (pas de commentaire seulement):

 //   - t="0x2dc35f255e56f06bd2935f5a49a0033548d85477" //     MyToken ="0xaac611907f12d5ebe89648d6459c1c81eca78151" //     MyCrowdsale //   - token=MyToken.at(t) crowdsale=MyCrowdsale.at(c) //       account=web3.eth.accounts[0] // ,      token.balanceOf(account) //   0 //    - web3.eth.sendTransaction({from: account, to:c, value: web3.toWei(0.1, 'ether'), gas: 900000}) 

Dans le cas de, testrpcvous pouvez à nouveau vérifier immédiatement le solde de notre portefeuille, mais dans le cas du test et de la vraie blockchain, vous devez attendre que notre transaction soit incluse dans le bloc - généralement lorsque cela se produit, la truffe vous donne le numéro de transaction. Tu as attendu? Vérifiez à nouveau notre solde dans MyToken:

 // ,      token.balanceOf(account) //     

C'est tout!Testez d'abord votre contrat testrpc, puis geth --testnet, puis déployez-le geth. Vous avez donc lancé votre propre ICO! Et vous n'avez pas eu à dépenser des dizaines de kilobaks pour l'audit et le lancement. Gâcher ce que les gars d'OpenZeppelin nous ont fourni est en fait très difficile. Et lorsque vous l'utilisez truffle- c'est ainsi que le développement solidaire se transforme généralement en conte de fées. Eh bien, sauf dans les cas où les transactions sont inversées lors de l'exécution d'un contrat intelligent - débutez leur enfer. Mais le débogage des contrats intelligents mérite vraiment un article séparé.

Conclusion


Merci beaucoup d'avoir lu jusqu'à la fin de cet article! Si j'ai réussi à vous faire gagner du temps ou de l'argent, ou si vous avez appris quelque chose de nouveau grâce à cet article, j'en serai très heureux. Je serais également très reconnaissant si vous partagez cet article avec vos amis ou connaissances qui souhaitent mener une ICO - économisez 75 000 $ pour les sous-programmeurs qui aspirent de l'argent du marché de la cryptographie comme les parasites, copiant-collant les mêmes 25 lignes de code .

Bonne chance pour développer des contrats intelligents! Vous avez encore des questions? Je vous le demande dans les commentaires - je serai ravi de tout répondre et d’essayer de résoudre les problèmes.

Bonus


Mais que se passe-t-il si vous souhaitez changer la logique selon laquelle le prix d'achat des jetons est considéré? Bien sûr, vous pouvez le changer correctement rateou utiliser l'une des classes de contrats d'OpenZeppelin, mais que se passe-t-il si vous voulez quelque chose d'encore plus perverti? Dans un contrat intelligent, vous pouvez remplacer la fonction getTokenAmountcomme suit:

 function _getTokenAmount(uint256 _weiAmount) internal view returns (uint256) { if (block.timestamp < 1533081600) { // August 1st, 2018 rate = rate * 4; } else if (block.timestamp < 1546300800) { // January 1st, 2019 rate = rate * 2; } return _weiAmount.mul(rate); } 

En général, cela peut rendre le prix du jeton dépendant du moment de l'achat - plus loin dans la forêt, plus les jetons sont chers. N'ayez pas peur d'expérimenter et de réécrire certaines des fonctionnalités des contrats intelligents - c'est amusant!

Source: https://habr.com/ru/post/fr414493/


All Articles