Programmierbaren Vertrag bereitstellen

Das Universal Ledger unterstützt programmierbare Verträge, die in einem Netzwerk bereitgestellt werden können, um Vereinbarungen zwischen interessierten Teilnehmern zu automatisieren und durchzusetzen.

In dieser Anleitung werden die Schritte beschrieben, die Entwickler ausführen müssen, um einen programmierbaren Vertrag in einem Universal Ledger-Netzwerk zu entwickeln, bereitzustellen und mit ihm zu interagieren.

Hinweis

Für diese Anleitung benötigen Sie Folgendes:

  • Aktivieren Sie Cloud Shell in der Google Cloud Console.

    Cloud Shell aktivieren

  • Ein Universal Ledger-Nutzerkonto mit der ROLE_CONTRACT_CREATOR. Dieses Konto wird zum Vertragsinhaber.

  • Ein oder mehrere Universal Ledger-Nutzerkonten mit der ROLE_CONTRACT_PARTICIPANT. Es kann dasselbe Konto wie das des Vertragsinhabers sein.

  • Optional können Sie die Universal Ledger CLI einrichten, um Transaktionen im Namen dieser Nutzerkonten zu signieren und zu senden.

Universal Ledger-Rollen können einem Nutzerkonto zugewiesen werden, wenn es von seinem Account Manager erstellt wird, wenn die Transaktion CreateAccount gesendet wird, oder später über eine AddRoles-Transaktion, wenn das Konto bereits vorhanden ist. Zu Testzwecken können Sie auch die Universal Ledger CLI verwenden, um Konten zu verwalten.

Umgebung einrichten

Zur Vereinfachung der Einrichtung wurde diese Anleitung für die Standardumgebung geschrieben, die in einer Cloud Shell-Sitzung bereitgestellt wird. Wenn Sie eine andere Umgebung verwenden, müssen Sie diese Befehle möglicherweise ändern.

Der gculpyc-Compiler nimmt in der GCULpy-Sprache geschriebenen Quellcode und erzeugt Bytecode für das Universal Ledger.

Führen Sie die folgenden Befehle aus, um das Docker-Image gculpyc abzurufen, einen Alias für die Ausführung der Binärdatei zu definieren und zu prüfen, ob die Binärdatei funktioniert.

docker pull us-docker.pkg.dev/gcul-artifacts/images/client/gculpyc:stable
alias gculpyc="docker run --rm -i --user $(id -u):$(id -g) \
    --volume .:/workspace --workdir /workspace \
    us-docker.pkg.dev/gcul-artifacts/images/client/gculpyc:stable"
gculpyc --help

Vertrag aufsetzen

GCULpy ist die Sprache, die zum Schreiben von Verträgen für das Universal Ledger verwendet wird. Es ist eine statisch typisierte Teilmenge von Python, die für eine klare, prüfbare und verständliche Vertragslogik optimiert ist. Bei diesem Design wird das Schreiben von sicherem Code priorisiert und unerwartetes oder unsicheres Verhalten eingeschränkt. Weitere Informationen finden Sie in der Referenz zur GCULpy-Sprache.

Da GCULpy eine strikte Teilmenge von Python ist, können Sie weiterhin Ihre bevorzugten integrierten Entwicklungsumgebungen (IDEs) sowie Ihre vorhandenen Workflows und Entwicklungspraktiken verwenden.

Ihr Code könnte beispielsweise so aussehen:

import gcul

class Counter(gcul.Contract):
    """Example contract implementing a counter."""

    value: int

    def increment(self) -> None:
        """Increments the counter value by 1."""
        self.value += 1

Kopieren Sie diesen Beispielcode und speichern Sie ihn in einer Datei mit dem Namen counter.py.

Lokal testen

In naher Zukunft werden Entwickler Zugriff auf eine lokale Simulationsumgebung haben. Es wird als Teil des Python-Moduls gcul bereitgestellt und soll die erforderlichen Funktionen für die native Simulation eines Universal Ledger-Netzwerks in einer Python-Umgebung bieten. So können Sie Verträge lokal ausführen und Unit-Tests mit Ihren bevorzugten Test-Frameworks schreiben, um die Zuverlässigkeit und Richtigkeit Ihrer Verträge vor der Bereitstellung zu prüfen.

Vertrag zusammenstellen

Kompilieren Sie den vorherigen Quellcode des Vertrags mit dem folgenden gculpyc-Befehl in Bytecode:

gculpyc --source_file counter.py --output_file counter.bin

Vertrag bereitstellen

Stellen Sie den Vertrag in einem Universal Ledger-Netzwerk bereit, indem Sie eine CreateContract-Transaktion senden, die von einem Nutzerkonto mit dem ROLE_CONTRACT_CREATOR signiert wurde.

Wenn Sie die Universal Ledger-Befehlszeile verwenden, können Sie dazu den folgenden Befehl ausführen:

ul-cli contracts create \
    --alias counter-contract \
    --sender OWNER_ALIAS \
    counter.bin

Ersetzen Sie Folgendes:

  • OWNER_ALIAS: der Alias eines Nutzerkontos mit der ROLE_CONTRACT_CREATOR.

Wenn die Transaktion abgeschlossen ist, enthält die Ausgabe dieses Befehls die ID des neu bereitgestellten Vertrags. Beispiel:

Contract created: 1:CTR:005XvYfiSm3913Jwv4y8HVQucStJ2Ev15Sar6A1kNNX10

Vertragsmethode aufrufen

Sobald ein Vertrag bereitgestellt wurde, kann jedes Nutzerkonto mit der Rolle ROLE_CONTRACT_PARTICIPANT eine InvokeContractMethod-Transaktion senden, um eine der öffentlichen Methoden im Vertrag aufzurufen.

Wenn Sie die Universal Ledger-Befehlszeile verwenden, können Sie dazu den folgenden Befehl ausführen:

ul-cli contracts invoke \
    --alias counter-contract \
    --method-name increment \
    --sender PARTICIPANT_ALIAS

Ersetzen Sie Folgendes:

  • PARTICIPANT_ALIAS: der Alias eines Nutzerkontos mit der ROLE_CONTRACT_PARTICIPANT.

Vertragsstatus lesen

Zum Abschluss dieser Anleitung können Sie eine QueryAccount-Anfrage senden, um den Status des im Ledger gespeicherten Vertrags zu lesen und zu prüfen. Dies ist dieselbe API-Methode, die zum Abfragen und Abrufen der Details eines beliebigen Universal Ledger-Kontos verwendet wird.

Mit der Universal Ledger CLI können Sie Folgendes ausführen:

ul-cli accounts describe --alias counter-contract

Der Zählerwert sollte jetzt auf 1 gesetzt sein. Die Ausgabe sollte in etwa so aussehen:

Account: 1:CTR:005XvYfiSm3913Jwv4y8HVQucStJ2Ev15Sar6A1kNNX10
Contract account details:
  Owner: 1:USR:XCL:022uF6cVkTJBaa6pViqTuYqP4455jnRbRc4bWannZGg0b
  Contract fields:
    value: int64_value:1

  Balances:
    None

Nächste Schritte