Facebook謹製のLibra、テストネットでトランザクション生成までやってみた


2019年6月18日に公開されたばかりのFacabook謹製のブロックチェーンを利用したLibra。日本でも話題になっているので、テストネットでトランザクションの生成までやってみました。実際に動かしてみると色々なことが分かってきました。

前提

  • Libraのテストネットは、MacOSとLinuxで動きます。
  • 今回はDockerでコンテナを立ち上げて試しました。

FLOCがブロックチェーンのスクールを運営していることもあり、再現性を高めるためにDockerを利用しました。(今回に関してはなくても全然大丈夫です。)

なお、筆者の環境は以下の通りです。

  • Macbook Pro 2018 13-inch
  • macOS Mojave 10.14.5
  • Docker 18.09.2

そもそもLibraって?

LibraはFacabookが作ったブロックチェーンで、イーサリアムのような汎用性とテザーをはじめとするステーブルコインの価値の安定性を持ちます。

既存のブロックチェーンが持つスケーラビリティ問題や価値の不安定さといった課題を解決すべく開発されています。

また、独自言語としてMoveも開発されており、スマートコントラクト開発に利用できるようになっています。

ホワイトペーパーも公開されているのでぜひこちらも合わせて御覧ください。より技術的に専門性の高いテクニカルペーパーも用意されています。
>>>Libraホワイトペーパー
>>>Libraテクニカルペーパー

Docker周りの準備

Dockerが入っていない場合は、インストールしておく必要があります。

何はともあれ、Dockerfileを用意します。

Dockerfile
FROM ubuntu:19.04
RUN apt-get update && apt-get -y upgrade && \
    apt-get install -y git curl sudo cmake golang protobuf-compiler vim
RUN git clone https://github.com/libra/libra.git
WORKDIR /libra

ここはお好みですが、起動するときに色々と入力するのが面倒くさいという方は以下のようにdocker-compose.ymlを作成しましょう。

docker-compose.yml
version: '3'
services:
 libra-test:
   image: libra
   build: .
   container_name: 'libra-test'
   tty: true

Dockerfileやdocker-compose.ymlは自分の使いやすいディレクトリに保存しておきましょう。そのディレクトリにターミナルで移動して、docker-compose up -dを実行します。

うまくコンテナが立ち上がったら、docker exec -it libra-test /bin/bashを打ち込んでコンテナに乗り込みます。

実行環境の構築

コンテナに乗り込んで最初にすることは、./scripts/dev_setup.shを実行することです。実行するとウェルカムLibraへ!と歓迎されたあとに、必要なパッケージをインストールしてもいいかを確認されるのでyを入力してあとは流れに任せます。

すべての依存パッケージをインストールするとCargoに関する処理を行います。CargoはRustのパッケージ管理&ビルドツールですね。具体的には、source /root/.cargo/envcargo buildを順番に実行します。ここからは少し時間がかかるのでコーヒーでも飲みながら待ちましょう。

すべて実行できれば、./scripts/cli/start_cli_testnet.shを実行します。これは、テストネットをスタートさせるためのコマンドです。

ここまで問題なくできれば、ようやくトランザクションの生成ができるようになります。

テストネットでトランザクション生成

いよいよ本題、トランザクションの生成へと移りましょう!

コマンドの確認

Libraのテストネットのコマンドはいくつか用意されています。

コマンド      意味
account アカウント作成などアカウントにまつわる処理を行う
query 色々なデータを取得する際に利用する
transfer 送金処理を行う
submit ファイルからトランザクションの生データをロードしたり、ネットワークへ送ったりする処理を行う
help 困ったときはhelpを叩くとヒントをくれる
quit 修了するときの処理

他にも、それぞれのコマンドにより細かいコマンドが用意されています。とはいえ、テストネットなのでそれほど機能も多くはないです。

アカウントの作成

トランザクションの生成にあたり、アカウントを作成しなくてはいけません。account createで簡単に生成できます。今回は送金を試すため、2つ作成しましょう。インデックスが0と1のものの両方が作成できます。

libra% account create
>> Creating/retrieving next account from wallet
Created/retrieved account #0 address cdbe0a60fe35e48db3eb0f893107bec69dc8b40c4333b9c31a2532560fed79bc

libra% account create
>> Creating/retrieving next account from wallet
Created/retrieved account #1 address 0c3842afb40568954e77bb8f30d4f0f8790165cd3018b9a8c9b593491e50572e

account listで作成したアカウントの一覧を確認できます。

libra% account list
User account index: 0, address: cdbe0a60fe35e48db3eb0f893107bec69dc8b40c4333b9c31a2532560fed79bc, sequence number: 0, status: Local
User account index: 1, address: 0c3842afb40568954e77bb8f30d4f0f8790165cd3018b9a8c9b593491e50572e, sequence number: 0, status: Local

アカウントへの入金

作成した2つのアカウントにそれぞれ100Libraと50Libraを入金しましょう。特定のインデックスのアカウントに入金する時は以下のように実行します。

account mint {金額}

今回であれば、account mint 0 100account mint 1 50を実行します。

libra% account mint 0 100
>> Minting coins
Mint request submitted

libra% account mint 1 50
>> Minting coins
Mint request submitted

quary balance {インデックス}で残高が確認できるので、quary balance 0quary balance 1をそれぞれ実行してみましょう。

libra% query balance 0
Balance is: 100.000000

libra% query balance 1
Balance is: 50.000000

送金してみる

次にいよいよ送金です!送金はtransferコマンドを利用して以下のように記述します。

transfer {送金元のインデックス} {送金先のインデックス} {金額}

今回はAさんからBさんに20Libraを送金するとすると、以下のように実行します。

transfer 0 1 20

実行すると「Transaction submitted to validator」と表記されているので、Libraのホワイトペーパーにある通り、承認者によって承認するタイプのコンセンサスアルゴリズムを使っていることがここからも分かります。

libra% transfer 0 1 20
>> Transferring
Transaction submitted to validator
To query for transaction status, run: query txn_acc_seq 0 0 <fetch_events=true|false>

うまくいったか確認するため、quary balance 0quary balance 1を実行してみましょう。

libra% query balance 0
Balance is: 80.000000

libra% query balance 1
Balance is: 70.000000

うまく行っているみたいですね!

トランザクションデータの確認

トランザクションデータのより詳細を見るためには、以下のコマンドを実行します。

query txn_acc_seq 0 0 true

libra% query txn_acc_seq 0 0 true
>> Getting committed transaction by account and sequence number
Committed transaction: SignedTransaction { 
 raw_txn: RawTransaction { 
    sender: cdbe0a60fe35e48db3eb0f893107bec69dc8b40c4333b9c31a2532560fed79bc, 
    sequence_number: 0, 
    payload: {, 
        transaction: peer_to_peer_transaction, 
        args: [ 
            {ADDRESS: 0c3842afb40568954e77bb8f30d4f0f8790165cd3018b9a8c9b593491e50572e},
            {U64: 20000000}, 
        ]
    }, 
    max_gas_amount: 10000, 
    gas_unit_price: 0, 
    expiration_time: 1562298424s, 
}, 
 public_key: 947127600327e626cc0dd2b52724387b15bf2508384d8dfc4d08ba3bd6aba39f, 
 signature: Signature( R: CompressedEdwardsY: [174, 224, 169, 0, 160, 42, 169, 128, 122, 211, 110, 36, 135, 2, 100, 132, 32, 50, 24, 138, 22, 252, 79, 6, 43, 42, 179, 128, 48, 240, 81, 114], s: Scalar{
    bytes: [24, 225, 182, 137, 147, 170, 79, 219, 198, 3, 213, 26, 116, 93, 211, 246, 20, 80, 152, 151, 77, 253, 204, 184, 61, 254, 46, 101, 192, 79, 15, 9],
} ), 
 }
Events: 
ContractEvent { access_path: AccessPath { address: cdbe0a60fe35e48db3eb0f893107bec69dc8b40c4333b9c31a2532560fed79bc, type: Resource, hash: "217da6c6b3e19f1825cfb2676daecce3bf3de03cf26647c78df00b371b25cc97", suffix: "/sent_events_count/" } , index: 0, event_data: AccountEvent { account: 0c3842afb40568954e77bb8f30d4f0f8790165cd3018b9a8c9b593491e50572e, amount: 20000000 } }
ContractEvent { access_path: AccessPath { address: 0c3842afb40568954e77bb8f30d4f0f8790165cd3018b9a8c9b593491e50572e, type: Resource, hash: "217da6c6b3e19f1825cfb2676daecce3bf3de03cf26647c78df00b371b25cc97", suffix: "/received_events_count/" } , index: 0, event_data: AccountEvent { account: cdbe0a60fe35e48db3eb0f893107bec69dc8b40c4333b9c31a2532560fed79bc, amount: 20000000 } }

SenderとADDREESSの部分にそれぞれ送金元アドレスであるcdbe0a60fe35e48db3eb0f893107bec69dc8b40c4333b9c31a2532560fed79bcと送金先アドレスである0c3842afb40568954e77bb8f30d4f0f8790165cd3018b9a8c9b593491e50572eが入っていることが分かります。また、gasという単語がraw_txnの部分に見えますが、イーサリアムと同じくスマートコントラクトを実行するための仕掛けを感じさせます。

また、最後のEvents: と書かれた部分もスマートコントラクトのデザインになっています。上部がsuffix: "/sent_events_count/"、下部がsuffix: "/received_events_count/"となっており、それぞれ送金と受け取りのイベントとして処理されています。

わかったこと

  • ビットコインとイーサリアム、ステーブルコインをちゃんと研究して作っていることがひしひしと伝わる。

  • トランザクションの承認が承認者によるものなので承認そのものは速いだろうが、発表によると今後パブリックチェーンに移行するらしい。どんな段階を踏むのかプロセスをもっと知りたい。

  • 言語としてRustを使っており、Moveはこれに似ている独自言語。Rustは学習難易度が高い言語で有名ですが、、早めに手を出しておこうか、、

  • 何より、短期間でこれだけのものをデザインして、実装まで持ってきたFacebookの技術力に脱帽です。。