Blockchain : quel PoC construire ?

Vos yeux ont peur et vos mains vous démangent !

Dans des articles précédents, nous avons traité des technologies sur lesquelles sont construites les blockchains (Que devrions-nous construire une blockchain ?) et les cas qui peuvent être mis en œuvre avec leur aide (Pourquoi devrions-nous monter un dossier ?). Il est temps de travailler de vos mains ! Pour mettre en œuvre les pilotes et les PoC (Proof of Concept), je préfère utiliser les cloud, car... ils sont accessibles depuis n'importe où dans le monde et, souvent, il n'est pas nécessaire de perdre du temps dans une installation fastidieuse de l'environnement, car Il existe des configurations prédéfinies. Alors, créons quelque chose de simple, par exemple un réseau de transfert de pièces entre participants et appelons-le modestement Bitcoin. Pour cela nous utiliserons le cloud IBM et la blockchain universelle Hyperledger Fabric. Tout d’abord, voyons pourquoi Hyperledger Fabric est appelé une blockchain universelle ?

Blockchain : quel PoC construire ?

Hyperledger Fabric - une blockchain universelle

D’une manière générale, un système d’information universel c’est :

  • Un ensemble de serveurs et un cœur logiciel qui exécute la logique métier ;
  • Interfaces d'interaction avec le système ;
  • Outils d'enregistrement, d'authentification et d'autorisation des appareils/personnes ;
  • Base de données stockant les données opérationnelles et archivées :

Blockchain : quel PoC construire ?

La version officielle de ce qu'est Hyperledger Fabric peut être lue sur En ligne, et en bref, Hyperledger Fabric est une plateforme open source qui vous permet de créer des blockchains privées et d'exécuter des contrats intelligents arbitraires écrits dans les langages de programmation JS et Go. Examinons en détail l'architecture d'Hyperledger Fabric et assurons-nous qu'il s'agit d'un système universel qui n'a que des spécificités pour le stockage et l'enregistrement des données. La spécificité est que les données, comme dans toutes les blockchains, sont stockées dans des blocs qui ne sont placés sur la blockchain que si les participants parviennent à un consensus et qu'après l'enregistrement, les données ne peuvent pas être discrètement corrigées ou supprimées.

Architecture de structure Hyperledger

Le diagramme montre l'architecture Hyperledger Fabric :

Blockchain : quel PoC construire ?

Organisations — les organisations contiennent des pairs, c'est-à-dire la blockchain existe grâce au soutien des organisations. Différentes organisations peuvent faire partie du même canal.

Développement — une structure logique qui unit les pairs en groupes, c'est-à-dire la blockchain est spécifiée. Hyperledger Fabric peut traiter simultanément plusieurs blockchains avec une logique métier différente.

Fournisseur de services aux membres (MSP) est une CA (Certificate Authority) pour la délivrance d'identité et l'attribution de rôles. Pour créer un nœud, vous devez interagir avec le MSP.

Nœuds homologues — vérifier les transactions, stocker la blockchain, exécuter des contrats intelligents et interagir avec les applications. Les pairs ont une identité (certificat numérique), délivrée par le MSP. Contrairement au réseau Bitcoin ou Etherium, où tous les nœuds ont des droits égaux, dans Hyperledger Fabric, les nœuds jouent des rôles différents :

  • Peut-être avec les pairs pair approuvant (EP) et exécuter des contrats intelligents.
  • Pair engagé (CP) - enregistrez uniquement les données dans la blockchain et mettez à jour «l'état mondial».
  • Pair d'ancrage (AP) - si plusieurs organisations participent à la blockchain, des pairs d'ancrage sont utilisés pour la communication entre elles. Chaque organisation doit avoir un ou plusieurs pairs d’ancrage. Grâce à AP, n'importe quel homologue d'une organisation peut obtenir des informations sur tous les homologues d'autres organisations. Utilisé pour synchroniser les informations entre les points d'accès protocole de potins.
  • Pair leader — si une organisation a plusieurs pairs, alors seul le leader du pair recevra des blocs du service de commande et les donnera au reste des pairs. Le leader peut être soit spécifié de manière statique, soit sélectionné de manière dynamique par ses pairs de l'organisation. Le protocole Gossip est également utilisé pour synchroniser les informations sur les dirigeants.

Outils — des entités qui ont de la valeur et sont stockées sur la blockchain. Plus précisément, il s'agit de données clé-valeur au format JSON. Ce sont ces données qui sont enregistrées dans la Blockchain. Ils ont un historique, qui est stocké dans la blockchain, et un état actuel, qui est stocké dans la base de données « World state ». Les structures de données sont remplies arbitrairement en fonction des tâches métier. Il n'y a pas de champs obligatoires, la seule recommandation est que les actifs doivent avoir un propriétaire et avoir de la valeur.

Ledger — se compose de la Blockchain et de la base de données d'état Word, qui stocke l'état actuel des actifs. L'état mondial utilise LevelDB ou CouchDB.

Contrat intelligent — à l'aide de contrats intelligents, la logique métier du système est implémentée. Dans Hyperledger Fabric, les contrats intelligents sont appelés chaincode. À l'aide du code chaîne, les actifs et les transactions sur ceux-ci sont spécifiés. En termes techniques, les contrats intelligents sont des modules logiciels implémentés dans les langages de programmation JS ou Go.

Politique d'approbation — pour chaque code chaîne, vous pouvez définir une politique sur le nombre de confirmations d'une transaction à attendre et de qui. Si la politique n'est pas définie, la valeur par défaut est : « la transaction doit être confirmée par n'importe quel membre de n'importe quelle organisation du canal. » Exemples de politiques :

  • La transaction doit être approuvée par tout administrateur de l'organisation ;
  • Doit être confirmé par tout membre ou client de l'organisation;
  • Doit être confirmé par toute organisation homologue.

Service de commande - regroupe les transactions en blocs et les envoie aux pairs du canal. Garantit la livraison des messages à tous les pairs du réseau. Utilisé pour les systèmes industriels Courtier de messages Kafka, pour le développement et les tests Solo Dome.

Flux d'appels

Blockchain : quel PoC construire ?

  • L'application communique avec Hyperledger Fabric à l'aide de Go, Node.js ou Java SDK ;
  • Le client crée une transaction d'émission et l'envoie aux pairs qui l'approuvent ;
  • Le pair vérifie la signature du client, termine la transaction et renvoie la signature d'approbation au client. Chaincode est exécuté uniquement sur le pair approuvant et le résultat de son exécution est envoyé à tous les pairs. Cet algorithme de travail est appelé consensus PBFT (Practical Byzantine Fault Tolerant). Diffère de BFT classique le fait que le message est envoyé et que la confirmation n'est pas attendue de tous les participants, mais seulement d'un certain ensemble ;
  • Après que le client a reçu le nombre de réponses correspondant à la politique d'avenant, il envoie la transaction au service Commande ;
  • Le service Ordering génère un bloc et l’envoie à tous les pairs qui s’engagent. Le service de commande garantit l'enregistrement séquentiel des blocs, ce qui élimine ce que l'on appelle la fourchette du grand livre (voir rubrique "Fourches");
  • Les pairs reçoivent un bloc, vérifient à nouveau la politique d'approbation, écrivent le bloc dans la blockchain et modifient l'état dans la base de données « État mondial ».

Ceux. Il en résulte une répartition des rôles entre les nœuds. Cela garantit que la blockchain est évolutive et sécurisée :

  • Les contrats intelligents (chaincode) effectuent l’approbation des pairs. Cela garantit la confidentialité des contrats intelligents, car il n'est pas stocké par tous les participants, mais uniquement par les pairs qui l'approuvent.
  • La commande devrait fonctionner rapidement. Ceci est assuré par le fait que Ordering forme uniquement un bloc et l’envoie à un ensemble fixe de pairs leaders.
  • Les pairs engagés stockent uniquement la blockchain - il peut y en avoir beaucoup et ils ne nécessitent pas beaucoup de puissance ni de fonctionnement instantané.

Plus de détails sur les solutions architecturales d'Hyperledger Fabric et pourquoi il fonctionne de cette façon et non autrement peuvent être trouvés ici : Origines de l'architecture ou ici: Hyperledger Fabric : un système d'exploitation distribué pour les blockchains autorisées.

Ainsi, Hyperledger Fabric est un système véritablement universel avec lequel vous pouvez :

  • Implémenter une logique métier arbitraire à l'aide du mécanisme de contrat intelligent ;
  • Enregistrer et recevoir les données de la base de données blockchain au format JSON ;
  • Accordez et vérifiez l'accès à l'API à l'aide de l'autorité de certification.

Maintenant que nous comprenons un peu les spécificités d'Hyperledger Fabric, faisons enfin quelque chose d'utile !

Déployer la blockchain

Formulation du problème

La tâche est de mettre en œuvre le réseau Citcoin avec les fonctions suivantes : créer un compte, obtenir un solde, recharger votre compte, transférer des pièces d'un compte à un autre. Dessinons un modèle objet, que nous implémenterons ensuite dans un contrat intelligent. Ainsi, nous aurons des comptes identifiés par des noms et contenant un solde et une liste de comptes. Les comptes et une liste de comptes sont, en termes d'actifs Hyperledger Fabric. En conséquence, ils ont une histoire et un état actuel. Je vais essayer de dessiner ceci clairement :

Blockchain : quel PoC construire ?

Les chiffres les plus élevés correspondent à l'état actuel, qui est stocké dans la base de données « État mondial ». En dessous se trouvent des chiffres montrant l’historique stocké dans la blockchain. L'état actuel des actifs est modifié par les transactions. L'actif ne change que dans son ensemble, donc à la suite de la transaction, un nouvel objet est créé et la valeur actuelle de l'actif entre dans l'historique.

IBM-Cloud

Nous créons un compte dans Nuage IBM. Pour utiliser la plateforme blockchain, elle doit être mise à niveau vers Pay-As-You-Go. Ce processus n'est peut-être pas rapide, car... IBM demande des informations supplémentaires et les vérifie manuellement. Sur une note positive, je peux dire qu'IBM propose de bons supports de formation qui vous permettent de déployer Hyperledger Fabric dans leur cloud. J'ai aimé la série d'articles et d'exemples suivante :

Voici des captures d'écran de la plateforme IBM Blockchain. Il ne s'agit pas d'une instruction sur la façon de créer une blockchain, mais simplement d'une démonstration de l'ampleur de la tâche. Ainsi, pour nos besoins, nous créons une seule organisation :

Blockchain : quel PoC construire ?

Nous y créons des nœuds : Orderer CA, Org1 CA, Orderer Peer :

Blockchain : quel PoC construire ?

Nous créons des utilisateurs :

Blockchain : quel PoC construire ?

Créez une chaîne et appelez-la citcoin :

Blockchain : quel PoC construire ?

Essentiellement, Channel est une blockchain, il commence donc par le bloc zéro (bloc Genesis) :

Blockchain : quel PoC construire ?

Rédaction d'un contrat intelligent

/*
 * Citcoin smart-contract v1.5 for Hyperledger Fabric
 * (c) Alexey Sushkov, 2019
 */
 
'use strict';
 
const { Contract } = require('fabric-contract-api');
const maxAccounts = 5;
 
class CitcoinEvents extends Contract {
 
    async instantiate(ctx) {
        console.info('instantiate');
        let emptyList = [];
        await ctx.stub.putState('accounts', Buffer.from(JSON.stringify(emptyList)));
    }
    // Get all accounts
    async GetAccounts(ctx) {
        // Get account list:
        let accounts = '{}'
        let accountsData = await ctx.stub.getState('accounts');
        if (accountsData) {
            accounts = JSON.parse(accountsData.toString());
        } else {
            throw new Error('accounts not found');
        }
        return accountsData.toString()
    }
     // add a account object to the blockchain state identifited by their name
    async AddAccount(ctx, name, balance) {
        // this is account data:
        let account = {
            name: name,
            balance: Number(balance),       
            type: 'account',
        };
        // create account:
        await ctx.stub.putState(name, Buffer.from(JSON.stringify(account)));
 
        // Add account to list:
        let accountsData = await ctx.stub.getState('accounts');
        if (accountsData) {
            let accounts = JSON.parse(accountsData.toString());
            if (accounts.length < maxAccounts)
            {
                accounts.push(name);
                await ctx.stub.putState('accounts', Buffer.from(JSON.stringify(accounts)));
            } else {
                throw new Error('Max accounts number reached');
            }
        } else {
            throw new Error('accounts not found');
        }
        // return  object
        return JSON.stringify(account);
    }
    // Sends money from Account to Account
    async SendFrom(ctx, fromAccount, toAccount, value) {
        // get Account from
        let fromData = await ctx.stub.getState(fromAccount);
        let from;
        if (fromData) {
            from = JSON.parse(fromData.toString());
            if (from.type !== 'account') {
                throw new Error('wrong from type');
            }   
        } else {
            throw new Error('Accout from not found');
        }
        // get Account to
        let toData = await ctx.stub.getState(toAccount);
        let to;
        if (toData) {
            to = JSON.parse(toData.toString());
            if (to.type !== 'account') {
                throw new Error('wrong to type');
            }  
        } else {
            throw new Error('Accout to not found');
        }
 
        // update the balances
        if ((from.balance - Number(value)) >= 0 ) {
            from.balance -= Number(value);
            to.balance += Number(value);
        } else {
            throw new Error('From Account: not enought balance');          
        }
 
        await ctx.stub.putState(from.name, Buffer.from(JSON.stringify(from)));
        await ctx.stub.putState(to.name, Buffer.from(JSON.stringify(to)));
                 
        // define and set Event
        let Event = {
            type: "SendFrom",
            from: from.name,
            to: to.name,
            balanceFrom: from.balance,
            balanceTo: to.balance,
            value: value
        };
        await ctx.stub.setEvent('SendFrom', Buffer.from(JSON.stringify(Event)));
 
        // return to object
        return JSON.stringify(from);
    }
 
    // get the state from key
    async GetState(ctx, key) {
        let data = await ctx.stub.getState(key);
        let jsonData = JSON.parse(data.toString());
        return JSON.stringify(jsonData);
    }
    // GetBalance   
    async GetBalance(ctx, accountName) {
        let data = await ctx.stub.getState(accountName);
        let jsonData = JSON.parse(data.toString());
        return JSON.stringify(jsonData);
    }
     
    // Refill own balance
    async RefillBalance(ctx, toAccount, value) {
        // get Account to
        let toData = await ctx.stub.getState(toAccount);
        let to;
        if (toData) {
            to = JSON.parse(toData.toString());
            if (to.type !== 'account') {
                throw new Error('wrong to type');
            }  
        } else {
            throw new Error('Accout to not found');
        }
 
        // update the balance
        to.balance += Number(value);
        await ctx.stub.putState(to.name, Buffer.from(JSON.stringify(to)));
                 
        // define and set Event
        let Event = {
            type: "RefillBalance",
            to: to.name,
            balanceTo: to.balance,
            value: value
        };
        await ctx.stub.setEvent('RefillBalance', Buffer.from(JSON.stringify(Event)));
 
        // return to object
        return JSON.stringify(from);
    }
}
module.exports = CitcoinEvents;

Intuitivement, tout devrait être clair ici :

  • Il existe plusieurs fonctions (AddAccount, GetAccounts, SendFrom, GetBalance, RefillBalance) que le programme de démonstration appellera à l'aide de l'API Hyperledger Fabric.
  • Les fonctions SendFrom et RefillBalance génèrent des événements que le programme de démonstration recevra.
  • La fonction d'instanciation est appelée une fois lorsqu'un contrat intelligent est instancié. En fait, il n’est pas appelé une seule fois, mais à chaque fois que la version du contrat intelligent change. Par conséquent, initialiser une liste avec un tableau vide est une mauvaise idée, car Désormais, lorsque nous modifierons la version du contrat intelligent, nous perdrons la liste actuelle. Mais ça va, j'apprends juste).
  • Les comptes et une liste de comptes sont des structures de données JSON. JS est utilisé pour la manipulation des données.
  • Vous pouvez obtenir la valeur actuelle d'un actif à l'aide de l'appel de fonction getState et la mettre à jour à l'aide de putState.
  • Lors de la création d'un compte, la fonction AddAccount est appelée, dans laquelle une comparaison est effectuée pour le nombre maximum de comptes dans la blockchain (maxAccounts = 5). Et ici il y a un montant (avez-vous remarqué ?), qui entraîne une augmentation sans fin du nombre de comptes. De telles erreurs doivent être évitées)

Ensuite, nous chargeons le contrat intelligent dans le canal et l'instancions :

Blockchain : quel PoC construire ?

Regardons la transaction pour l'installation de Smart Contract :

Blockchain : quel PoC construire ?

Examinons les détails de notre chaîne :

Blockchain : quel PoC construire ?

En conséquence, nous obtenons le schéma suivant d'un réseau blockchain dans le cloud IBM. Le diagramme montre également un programme de démonstration exécuté dans le cloud Amazon sur un serveur virtuel (plus d'informations à ce sujet dans la section suivante) :

Blockchain : quel PoC construire ?

Création d'une interface graphique pour les appels d'API Hyperledger Fabric

Hyperledger Fabric dispose d'une API qui peut être utilisée pour :

  • Créer une chaîne ;
  • Connexions peer-to-channel ;
  • Installation et instanciation de contrats intelligents dans le canal ;
  • Appel de transactions ;
  • Demandez des informations sur la blockchain.

Développement d'applications

Dans notre programme de démonstration, nous utiliserons l'API uniquement pour appeler des transactions et demander des informations, car Nous avons déjà terminé les étapes restantes en utilisant la plateforme blockchain IBM. Nous écrivons une interface graphique en utilisant une pile technologique standard : Express.js + Vue.js + Node.js. Vous pouvez rédiger un article séparé sur la façon de commencer à créer des applications Web modernes. Ici, je laisserai un lien vers la série de conférences que j'ai le plus appréciée : Application Web Full Stack utilisant Vue.js et Express.js. Le résultat est une application client-serveur avec une interface graphique familière dans le style Material Design de Google. L'API REST entre client et serveur se compose de plusieurs appels :

  • HyperledgerDemo/v1/init - initialise la blockchain ;
  • HyperledgerDemo/v1/accounts/list — obtenez une liste de tous les comptes ;
  • HyperledgerDemo/v1/account?name=Bob&balance=100 — créer un compte Bob ;
  • HyperledgerDemo/v1/info?account=Bob — obtenez des informations sur le compte Bob ;
  • HyperledgerDemo/v1/transaction?from=Bob&to=Alice&volume=2 — transférez deux pièces de Bob à Alice ;
  • HyperledgerDemo/v1/disconnect - ferme la connexion à la blockchain.

Description de l'API avec des exemples inclus dans Site du facteur - un programme bien connu pour tester l'API HTTP.

Application de démonstration dans le cloud Amazon

J'ai téléchargé l'application sur Amazon parce que... IBM n'a toujours pas pu mettre à jour mon compte et me permettre de créer des serveurs virtuels. Comment ajouter une cerise au domaine : www.citcoin.info. Je vais laisser le serveur allumé pendant un moment, puis l'éteindre, parce que... les centimes à louer dégoulinent et les pièces citcoin ne sont pas encore cotées en bourse) J'inclus des captures d'écran de la démo dans l'article afin que la logique du travail soit claire. L'application de démonstration peut :

  • Initialisez la blockchain ;
  • Créez un compte (mais vous ne pouvez désormais pas créer un nouveau compte, car le nombre maximum de comptes spécifié dans le contrat intelligent a été atteint dans la blockchain) ;
  • Recevez une liste de comptes ;
  • Transférez des pièces de monnaie citcoin entre Alice, Bob et Alex ;
  • Recevoir des événements (mais il n'y a désormais aucun moyen d'afficher les événements, donc pour plus de simplicité, l'interface indique que les événements ne sont pas pris en charge) ;
  • Enregistrez les actions.

Nous initialisons d’abord la blockchain :

Blockchain : quel PoC construire ?

Ensuite, nous créons notre compte, ne perdons pas de temps avec le solde :

Blockchain : quel PoC construire ?

Nous obtenons une liste de tous les comptes disponibles :

Blockchain : quel PoC construire ?

Nous sélectionnons l'expéditeur et le destinataire et obtenons leurs soldes. Si l'expéditeur et le destinataire sont identiques, alors son compte sera réapprovisionné :

Blockchain : quel PoC construire ?

Dans le journal, nous surveillons l'exécution des transactions :

Blockchain : quel PoC construire ?

En fait, c'est tout avec le programme de démonstration. Ci-dessous vous pouvez voir notre transaction dans la blockchain :

Blockchain : quel PoC construire ?

Et la liste générale des transactions :

Blockchain : quel PoC construire ?

Avec cela, nous avons achevé avec succès la mise en œuvre du PoC pour créer le réseau Citcoin. Que faut-il faire d'autre pour que Citcoin devienne un réseau à part entière de transfert de pièces ? Très peu:

  • Au stade de la création du compte, mettez en œuvre la génération d'une clé privée/publique. La clé privée doit être stockée chez l'utilisateur du compte, la clé publique doit être stockée dans la blockchain.
  • Effectuez un transfert de pièces dans lequel une clé publique, plutôt qu'un nom, est utilisée pour identifier l'utilisateur.
  • Chiffrez les transactions allant de l'utilisateur au serveur avec sa clé privée.

Conclusion

Nous avons mis en place le réseau Citcoin avec les fonctions suivantes : ajouter un compte, obtenir un solde, recharger votre compte, transférer des pièces d'un compte à un autre. Alors, combien nous a-t-il coûté de construire un PoC ?

  • Vous devez étudier la blockchain en général et Hyperledger Fabric en particulier ;
  • Apprenez à utiliser les cloud IBM ou Amazon ;
  • Apprendre le langage de programmation JS et certains frameworks web ;
  • Si certaines données doivent être stockées non pas dans la blockchain, mais dans une base de données distincte, apprenez à les intégrer, par exemple, avec PostgreSQL ;
  • Et enfin et surtout : vous ne pouvez pas vivre dans le monde moderne sans connaître Linux !)

Bien sûr, ce n’est pas sorcier, mais il va falloir travailler dur !

Исходники sur GitHub

Sources mises en ligne GitHub. Brève description du référentiel :
Catalogue «serveur» — Serveur Node.js
Catalogue «client» — Client Node.js
Catalogue «blockchain"(les valeurs des paramètres et les clés, bien entendu, ne fonctionnent pas et ne sont données qu'à titre d'exemple) :

  • contrat – code source du contrat intelligent
  • wallet - clés utilisateur pour utiliser l'API Hyperledger Fabric.
  • *.cds - versions compilées de contrats intelligents
  • Fichiers *.json - exemples de fichiers de configuration pour l'utilisation de l'API Hyperledger Fabric

Ce n'est que le début !

Source: habr.com

Ajouter un commentaire