.NET, Solidity, Permissioned Ethereum - So kommt Ihre Anwendung zur Blockchain

7a1b0b24e5251ee7f5407681cca7d142?s=47 Ingo Rammer
September 27, 2018

.NET, Solidity, Permissioned Ethereum - So kommt Ihre Anwendung zur Blockchain

Aufbauend auf den Grundlagen aus der Session "Blockchain für Architekten & Entwickler" zeigt Ihnen Ingo Rammer in diesem Vortrag, wie sie die dort gezeigten Konzepte in der Praxis in einer privaten Blockchain umsetzen können. Sie lernen die technischen Grundlagen der Konfiguration einer Permissioned Blockchain auf Basis von Ethereum kennen, sehen wie Smart Contracts auf Basis von Solidity entwickelt und deployed werden, und wie deren primäres Identifikations- und Berechtigungssystem funktioniert. Im nächsten Schritt sehen sie, wie Sie ausgehend von Ihren .NET-Anwendungen mit vorhandenen .NET-Bibliotheken mit den Funktionen Ihrer Smart Contracts interagieren können.

7a1b0b24e5251ee7f5407681cca7d142?s=128

Ingo Rammer

September 27, 2018
Tweet

Transcript

  1. .NET, Solidity, Permissioned Ethereum So kommt Ihre Anwendung zur Blockchain

    Ingo Rammer ingo.rammer@thinktecture.com
  2. Ingo Rammer Gründer und Geschäftsführer der Thinktecture AG, einem technischen

    Beratungsunternehmen für Software-Architekten, -Entwickler und Entscheider Mein Fokus: Blockchain Technologien für B2B-Verwendung, von den Tiefen der Technologie bis hin zu ISO TC 307 Mitglied der Hyperledger Foundation & Enterprise Ethereum Alliance @ingorammer | ingo.rammer@thinktecture.com | https://thinktecture.com
  3. DEMO-DOWNLOAD Die Demos finden Sie unter der folgenden Adresse zum

    Download: https://www.dropbox.com/s/hojod1mqcpnktgz/SimpleBlockchainDemo-Complete.zip?dl=0
  4. • Ethereum • Konfiguration des Netzwerks • Solidity • .NET

    als Client Drei Teile dieser Session
  5. • Teilnehmer sind bekannt • Proof-of-Authority statt Proof-of-Work (Mining) •

    Bei Ethereum: gleiche Software wie beim öffentlichen Netz, nur andere Konfiguration! Permissioned Blockchains
  6. Ethereum Grundlagen

  7. • Accounts in Ethereum • Transaktionen allgemein • Smart Contracts

    • Solidity Ethereum Basics
  8. • Hat eine Adresse (vom Public Key abgeleitet) • z.B.

    0x6872bf08433dcd52f1f8b8bdf23b16efd9e2b23e • Typischerweise gibt es dazu einen Private Key • Ein Account kann Transaktionen empfangen und (vom Inhaber des Private Keys) senden • Kann ETH besitzen • Wer ein Wallet bzw. Cryptowährungen besitzt der verwaltet diese über einen Sammelaccount bei einer Börse oder über seinen eigenen Account Account
  9. • Werden von einem Account an eine Zieladresse gesendet und

    in Blöcken aggregiert • Verursacht Kosten („Gas“) • Gas Cost • Gas Price • Kann ETH-Transfer beinhalten • Beinhaltet einen freien Datenblock (byte[]) Transaktion
  10. • Zur Verhinderung von Replay-Attacken: jede Transaktion wird mit einer

    Nonce versehen • Nonces werden pro Absenderadresse ausgewertet • Nonces bei 0 und sind streng sequentiell (0, 1, 2, ...) • Eine Transaktion wird erst verarbeitet, wenn ihre Nonce an der Reihe ist • Wichtig bei Public Ethereum: je nach angebotenem Gas Price kann die Ausführung lange dauern. • TX kann nachträglich zu einem höherem Preis mit gleicher Nonce nochmals gesendet werden! Nonces bei Transaktionen
  11. Unser Netzwerk mit Parity

  12. Node 1 (Validator) Node 2 (Validator) Account #1: "node1" (Signer

    für Validator) Account #4: "networkFundingSource" Ether-Quelle Account #2: "node2" (Signer für Validator) Chain Spec (Konfigurationsdatei) Node 3 (Validator) Account #3: "node3" (Signer für Validator)
  13. • Chain Spec für Aura-Konsens • Validatoren • Blocklimits, Taktung,

    Finalität • Dokumentation • https://wiki.parity.io/Chain-specification • https://wiki.parity.io/Proof-of-Authority-Chains • https://wiki.parity.io/Pluggable-Consensus.html#aura Netzwerkdefinition mit Parity
  14. Chain Spec – Schritt 1

  15. Node-Konfiguration –Schritt 1

  16. • parity account new --config node1.toml -- password password.txt •

    Private Key wird angelegt, Ethereum-Adresse des neuen Accounts zurückgegeben Initialaccounts
  17. Node-Konfiguration mit Signer-Info

  18. None
  19. Nodes starten und verbinden

  20. • Zwei REST-APIs: • parity_enode (gibt enode-URL der aktuellen Node

    zurück) • parity_addReservedPeer • Beispiel: 04_connectNodes.js • (Im öffentlichen Ethereum-Netzwerk wird dieser Austausch per Peer-to-Peer-Kommunikation durchgeführt) Bekanntmachen zweier Nodes
  21. • “multi“-Konfiguration (in der Chain Spec) gibt die Blocknummer an,

    ab dem die jeweilige Konfiguration gilt Hinzufügen von weiteren Validatoren
  22. • Weitere Berechtigungen • Netzwerkzugriff • Validatoren per Smart Contract

    verwalten (statt in Chain Spec) • Berechtigungen für Transaktionstypen (Contract Erstellung, Contract Interaktionen, ETH-Transfer) • Service-Transaktionen ohne Kosten (Zero Gas Price) • https://wiki.parity.io/Permissioning Weitere Permissionierung
  23. • Grundlegender Unterschied zwischen Blockchain- Code und „normaler“ Software: Governance-

    Fragen! • Änderungsberechtigungen am Netzwerk oder Programmcode: • Wer? Gründer? Abstimmung? (Welche Stimmrechte?) • Was? Netzwerkzugriffsrechte? Code-Änderungen? • Wie? Off-Chain vs On-Chain? Organisatorisch? Technisch? Governance
  24. • Schwere Geburt: initiale Netzwerkkonfiguration • Konzepte: Chain Spec, Validatoren,

    Accounts, Enodes • In der Praxis typischerweise 100% als Skript • Im Beispiel: 01_initializeNetwork.sh, 02_updateAddressesInConfig.js, 03_startNodes.sh und 04_connectNodes.js OK, aber wo stehen wir jetzt?
  25. Smart Contracts und Solidity

  26. • Solidity wird zu EVM (Ethereum Virtual Machine) Bytecode kompiliert

    • Bytecode wird in einer speziellen Transaktion gesendet um zu instanziieren (im Datenblock der Transaktion) • Die Instanz bekommt eine Adresse (genau wie ein Account) • Zwei Instanzen des gleichen Contracts sind 100% voneinander unabhängig • Nach der Instanziierung ist der Code unveränderlich • Die Contract-Instanz kann ETH besitzen und Transaktionen senden (wie ein Account) • An die Contract-Instanz können Transaktionen gesendet werden. Methodenparameter werden im Datenblock der TX übertragen • Methoden, die keine Daten ändern können direkt (ohne TX) aufgerufen werden Smart Contract – Konzeptionelle Info
  27. • Hauptgenutzte Programmiersprache um Ethereum Smart Contracts zu schreiben •

    Wird mit solc zu Bytecode und ABI (Interface- Beschreibung) kompiliert • Entwicklungstools • remix (remix-ide und remixd) • Truffle • ... Solidity
  28. pragma solidity ^0.4.24; contract SimpleTest { int private value; constructor()

    public { } function setValue(int newValue) public { value = newValue; } function getValue() public view returns (int) { return value; } } Private Felder werden pro Instanz im Storage der Blockchain abgelegt Methoden, die Daten verändert, werden als Transaktion aufgerufen View-Methoden ohne Datenänderungen können direkt beantwortet werden, ohne Blockchain-Transaktion
  29. pragma solidity ^0.4.24; contract SimpleTest { int private value; address

    private owner; constructor() public { owner = msg.sender; } function setValue(int newValue) public { require(newValue > value); value = newValue; } function reset() public { require (msg.sender == owner); value = 0; } function getValue() public view returns (int) { return value; } } Contract kann ermitteln, wer eine Transaktion gesendet hat und die Adresse speichern Regeln werden mit require() geprüft. TX wird abgebrochen, wenn nicht erfüllt. Auch Adressen können verglichen werden! Contract ermittelt, wer die Transaktion gesendet hat und speichert die Adresse Ergebnis: Berechtigungsprüfung! Nur der Ersteller des Contracts kann reset() durchführen.
  30. Basiscontracts & Modifier contract SimpleTest is owned { int private

    value; constructor() public { } function reset() onlyOwner public { value = 0; } // setValue() und getValue() wie bisher } contract owned { constructor() public {owner = msg.sender;} address owner; modifier onlyOwner { require(msg.sender == owner); _; } } Superklasse Abgeleitete Klassen können den Modifier onlyOwner verwenden. (An Stelle des „_“ tritt der Inhalt der dekorierten Methode) Ableitung mit Schlüsselwort „is“ Verwendung des Modifiers ähnlich wie Sichtbarkeits-Definition function reset() public { require(msg.sender == owner); value = 0; }
  31. Events contract SimpleTest is owned { int private value; event

    ValueChanged(address indexed by, int newValue); constructor() public { } function setValue(int newValue) public { require(newValue > value); value = newValue; emit ValueChanged(msg.sender, newValue); } } Definition eines Events. (Nach Parametern, die „indexed“ sind kann bei der Subskription später gefiltert werden) Auslösen des Events mit „emit“
  32. • Remix mit JavaScript VM • remixd -s . •

    remix-ide (oder https://remix.ethereum.org) Tools
  33. .NET Clients für Smart Contracts

  34. • Web3.js für Browser und Node • Web3j für Java

    • Nethereum für .NET SDKs
  35. • Nethereum - https://nethereum.com/ • Kommandozeilentool für Smart Contract Wrapper

    (ABI-zu-C#) • Hat Erweiterungen für die typischen Ethereum- Derivate (geth, Parity, Quorum) • .NET 4.5, .NET Standard, .NET Core, Mono, Unity, ... Entwicklung mit .NET mit Netherum
  36. • ./network à Parity, initiale Verteilung von ETH • ./

    à Contracts & Contract-Scripts • ./generated à Daten für die Demo (Adressen, PKs, Identitäts- Mappings für lesbare Namen...) • ./dotnet/DemoRunner/ à Client • ./dotnet/DemoRunner/Contract à Generiert von Nethereum • Wichtig: DemoRunner simuliert mehrere Identitäten und Tasks • DemoRunner <identität> <kommando> [params] Anatomie der Demo-Anwendung
  37. • npm install -g solc • solcjs --bin --abi SimpleTest.sol

    • Resultat • *.bin à Bytecode des kompilierten Contracts • *.abi à Interfacebeschreibung Kompilierung eines Smart Contracts
  38. • Nethereum hat Kommandozeilenwerkzeuge zum Erstellen von .NET-Wrappern um die

    Smart Contracts • dotnet Nethereum.Generator.Console.dll gen-fromabi -abi <Contract.abi> --namespace <Namespace> -o <OutputDirectory> Generierte Services / Functions
  39. Contract Deployment string bytecode = "..."; // <ContractName>Deployment based on

    generated .NET Wrappers SimpleTestDeployment deployment = new SimpleTestDeployment(bytecode); Web3 web3 = new Web3(...); var receipt = await SimpleTestService.DeployContractAndWaitForReceiptAsync(web3, deployment); Console.WriteLine("Contract instantiated at {0}", receipt.ContractAddress);
  40. Calls (Read-Only) Web3 web3 = new Web3(...); string address =

    "<contractaddress>"; SimpleTestService service = new SimpleTestService(web3, contractaddress); // generated based on the public functions in the ABI GetValueFunction func = new GetValueFunction(); var value = await service.GetValueQueryAsync(func); Console.WriteLine("Current value is {0}", value);
  41. Transaktionen Web3 web3 = new Web3(...); string address = "<contractaddress>";

    SimpleTestService service = new SimpleTestService(web3, contractaddress); SetValueFunction func = new SetValueFunction(); func.NewValue = 1234; var txhash = await service.SetValueRequestAsync(func); Console.WriteLine("Set value to {0} with {1}", value, txhash); // Transaction is not yet mined! This is only a TX hash.
  42. • Möglichkeiten: • Trennung in Logik und Storage • Proxy

    Contracts mit delegatecall • State of the Art: Proxies mit Unstructured Storage • https://blog.zeppelinos.org/upgradeability-using- unstructured-storage/ • https://github.com/zeppelinos/labs/tree/master/ upgradeability_using_unstructured_storage/contracts • Wichtig: Governance muss geklärt sein! Updates vs Immutability
  43. • In der Node selbst (--unlock <address>) • Ethereum Standard

    Key Store Files • + password.txt • In der Applikation (typischerweise Web API), die getrennt von der Node läuft Wo sind die Private Keys?
  44. • Schnelldurchlauf in 60 Minuten • Parity: Netzwerkkonfiguration mit Aura-Konsens

    und zwei Validator-Nodes • Ethereum: Accounts, Transaktionen, Events, Nonces • Solidity: Basics, Contracts, Storage, Modifiers • Nethereum: Deployment, Calls, Transaktionen Summary
  45. Vielen Dank! • Slides: https://speakerdeck.com/ingorammer • Contact: ingo.rammer@thinktecture.com • Twitter:

    @ingorammer
  46. EXTRA CONTENT

  47. • Transaktionen, die abgebrochen werden (zB durch require()) geben keine

    Logs oder Fehlermeldungen zurück • Und: kosten trotzdem Gas • Daher: Trennung der Prüfung in eine view-Funktion (die zB einen Statuscode zurück gibt) und eine schreibende Funktion Check/Perform-Pattern