Lightning Network Developers
この記事は、以下URLのチュートリアルを翻訳したものです。Go,btcd,lndの環境構築はこちらのDockerリポジトリを参照ください。
ステージ1-ローカルクラスターのセットアップ
前書き
このステージのチュートリアルでは、Alice、Bob、Charlieのノードのローカルクラスターをセットアップし、相互に通信してチャネルをセットアップし支払いを相互にルーティングする方法を学習します。また、lndでの開発の一環として連携する必要のあるさまざまなコンポーネントの基礎について理解します。
このチュートリアルでは、simnetでGo、btcd、およびlndのインストールが完了していることを前提としています。そうでない場合は、インストール手順を参照してください。このチュートリアルでは、testnetを同期する必要はなく、完了する必要があるインストール手順の最後のセクションは「btcdのインストール」です。
スキーマは次のようになります。ローカルのlndインスタンスを実行するだけで、このネットワークを簡単に拡張して、David、Eveなどのノードを追加できることに注意してください。
(1) (1) (1)
+ ----- + + --- + + ------- +
| Alice | <--- channel ---> | Bob | <--- channel ---> | Charlie |
+ ----- + + --- + + ------- +
| | |
| | |
+ - - - - - - - - - - - - + - - - - - - - - - - - - - +
|
+ --------------- +
| BTC/LTC network | <--- (2)
+ --------------- +
コンポーネントを理解する
LND
lnd は、対話型の主要なコンポーネントです。 lndは、Lightning Network Daemonの略で、チャネルの開閉、ルーティング、支払いの送信、および基になるビットコインネットワーク自体とは別のすべてのLightningネットワーク状態の管理を処理します。
lndノードを実行すると、支払いを待機し、ブロックチェーンを監視している事になります。デフォルトでは、ユーザーの入力を待機しています。
lncli は、lndノードと対話するために使用されるコマンドラインクライアントです。通常、各lndノードは独自のターミナルウィンドウで実行されるため、ログ出力を確認できます。したがって、lncliコマンドは別のターミナルウィンドウから実行されます。
BTCD
btcdは、lndノードがBitcoin / Litecoinネットワークと対話するために使用するゲートウェイを表します。 lndは、オンチェーンアドレスまたはトランザクションの作成、ブロックチェーンの更新の監視、およびチャネルの開閉にbtcdを必要とします。現在のスキーマでは、3つのノードすべてが同じbtcdインスタンスに接続されています。より現実的なシナリオでは、各lndノードは、btcdまたは同等の独自のインスタンスに接続されます。
また、testnetの代わりにsimnetを使用します。 Simnetはローカルで実行される開発/テストネットワークであり、自由にブロックを生成できるため、オンチェーン機能のためにブロックが到着するのを待つ時間のかかるプロセスを回避できます。
環境設定について
lndでの開発は非常に複雑になる可能性があります。これは、より多くの動く部分があるためです。そのプロセスを簡素化するために、推奨されるワークフローを説明します。
btcdの実行
まだ実行していない場合は、btcdを実行することから始めましょう。新しいターミナルウィンドウを開き、$ GOPATHが設定されていることを確認して、次を実行します。
btcd --txindex --simnet --rpcuser=kek --rpcpass=kek
(注:このチュートリアルでは、かなりの数のターミナルウィンドウを開く必要があります。tmuxやscreenなどのマルチプレクサーを使い慣れていると便利です。)
オプションの内容:
--txindexは、lndクライアントがbtcdから履歴トランザクションを照会できるようにするために必要です。
--simnetは、simnetネットワークを使用していることを指定します。これは--testnetに変更するか、実際のビットコイン/ライトコインネットワークに接続するために完全に省略することができます。
--rpcuserおよびrpcpassは、btcdインスタンスの認証用のデフォルトパスワードを設定します。
lndの開始(Aliceのノード)
それでは、3つのlndノードをセットアップしましょう。できる限りクリーンで分離した状態に保つには、新しいターミナルウィンドウを開き、PATHに$ GOPATHセットと$ GOPATH / binがあることを確認し、開発スペースを表すdevと呼ばれる新しいディレクトリを$ GOPATHの下に作成します。Alice、Bob、Charlie の状態を保存する個別のフォルダーを作成し、Dockerを使用してネットワークを少し簡単にする代わりに、すべてのlndノードを異なるlocalhostポートで実行します。
# Create our development space
cd $GOPATH
mkdir dev
cd dev
# Create folders for each of our nodes
mkdir alice bob charlie
ディレクトリ構造は次のようになります。
$ tree $GOPATH -L 2
├── bin
│ └── ...
├── dev
│ ├── alice
│ ├── bob
│ └── charlie
├── pkg
│ └── ...
├── rpc
│ └── ...
└── src
└── ...
aliceディレクトリ内からAliceノードを起動します。
cd $GOPATH/dev/alice
alice$ lnd --rpclisten=localhost:10001 --listen=localhost:10011 --restlisten=localhost:8001 --datadir=data --logdir=log --debuglevel=info --bitcoin.simnet --bitcoin.active --bitcoin.node=btcd --btcd.rpcuser=kek --btcd.rpcpass=kek
これで、Aliceノードが実行され、「Walting for wallet encryption password」で始まる行で終わる出力が表示されます。
オプションの内容:
--rpclisten:RPCサーバーをリッスンするhost:port。これは、アプリケーションがlndと通信する主な方法です
--listen:着信P2P接続をリッスンするhost:port。これはネットワークレベルであり、LightningチャネルネットワークおよびBitcoin / Litcoinネットワーク自体とは異なります。
--restlisten:HTTPを介してlndと対話するためのREST APIを公開するhost:port。たとえば、localhost:8001 / v1 / channelsにGETリクエストを送信することで、Alice のチャンネル残高を取得できます。これはこのチュートリアルでは必要ありませんが、ここでいくつかの例を見ることができます。
--datadir:lndのデータが内部に保存されるディレクトリ
--logdir:出力を記録するディレクトリ。
--debuglevel:すべてのサブシステムのログレベル。トレース、デバッグ、情報、警告、エラー、クリティカルに設定できます。
--bitcoin.simnet:simnetまたはtestnetを使用するかどうかを指定します
--bitcoin.active:ビットコインがアクティブであることを指定します。 Litecoinをアクティブにするために--litecoin.activeを含めることもできます。
--bitcoin.node = btcd:btcdフルノードを使用して、ブロックチェーンとインターフェイスします。 Litecoinを使用する場合、オプションは--litecoin.node = btcdであることに注意してください。
--btcd.rpcuserおよび--btcd.rpcpass:btcdインスタンスのユーザー名とパスワード。 Litecoinを使用する場合、オプションは--ltcd.rpcuserと--ltcd.rpcpassであることに注意してください。
Bob のノードと Charlie のノードの開始
Aliceで行ったように、bobディレクトリ内からBobノードを起動し、charlieディレクトリ内からCharlieノードを起動します。そうすることで、datadirとlogdirが別々の場所に配置され、競合が発生しなくなります。
設定する追加のターミナルウィンドウごとに、$ GOPATHを設定し、PATHに$ GOPATH / binを含める必要があることに注意してください。次の行を含むセットアップスクリプトの作成を検討してください。
export GOPATH=~/gocode # if you exactly followed the install guide
export PATH=$PATH:$GOPATH/bin
そして、lndで動作する新しいターミナルウィンドウを起動するたびに実行します。
# In a new terminal window
cd $GOPATH/dev/bob
bob$ lnd --rpclisten=localhost:10002 --listen=localhost:10012 --restlisten=localhost:8002 --datadir=data --logdir=log --debuglevel=info --bitcoin.simnet --bitcoin.active --bitcoin.node=btcd --btcd.rpcuser=kek --btcd.rpcpass=kek
# In another terminal window
cd $GOPATH/dev/charlie
charlie$ lnd --rpclisten=localhost:10003 --listen=localhost:10013 --restlisten=localhost:8003 --datadir=data --logdir=log --debuglevel=info --bitcoin.simnet --bitcoin.active --bitcoin.node=btcd --btcd.rpcuser=kek --btcd.rpcpass=kek
lnd.confの構成
毎回コマンドラインでたくさんのフラグをタイプする必要をスキップするために、代わりにlnd.confを変更することができ、そこで指定された引数は自動的にlndにロードされます。コマンドライン引数として追加された追加の構成は、lnd.confから読み取った後に適用され、該当する場合はlnd.confオプションを上書きします。
MacOSでは、lnd.confは次の場所にあります。/ Users / [username] / Library / Application \ Support / Lnd / lnd.conf
Linuxの場合:〜/ .lnd / lnd.conf
以下に、コマンドラインオプションを再指定する手間を省くlnd.confの例を示します。
[Application Options]
datadir=data
logdir=log
debuglevel=info
[Bitcoin]
bitcoin.simnet=1
bitcoin.active=1
bitcoin.node=btcd
[btcd]
btcd.rpcuser=kek
btcd.rpcpass=kek
この設定により、以後ノードを起動するときは、以下のパラメータだけで実行できます。
alice$ lnd --rpclisten=localhost:10001 --listen=localhost:10011 --restlisten=localhost:8001
bob$ lnd --rpclisten=localhost:10002 --listen=localhost:10012 --restlisten=localhost:8002
charlie$ lnd --rpclisten=localhost:10003 --listen=localhost:10013 --restlisten=localhost:8003
lncliと認証の使用
これでlndノードが起動して実行されたので、それらと対話しましょう! lndを制御するには、コマンドラインインターフェイスであるlncliを使用する必要があります。
lndはrpcサーバーへの認証にマカロンを使用します。 lncliは通常、Lndホームディレクトリでadmin.macaroonファイルを探しますが、アプリケーションデータの場所を変更したため、次のコマンドで--macaroonpathを設定する必要があります。マカロンを無効にするには、-no-macaroonsフラグをlncliとlndの両方に渡します。
lndを使用すると、ウォレットをパスフレーズで暗号化し、オプションで暗号シードパスフレーズも暗号化できます。これは--noencryptwalletをlndまたはlnd.confに渡すことでオフにできます。このプロセスを少なくとも1回実行して、lndのセキュリティおよび認証機能に慣れることをお勧めします。
Aliceノードへのrpc接続をテストします。次のコマンドでは、-rpcserverをここで指定します。これは、Alice lndノードの起動時に設定した--rpcport = 10001に対応します。
新しいターミナルウィンドウを開き、$ GOPATHを設定し、通常どおりPATHに$ GOPATH / binを含めます。アリスの財布を作成してパスフレーズを設定しましょう。
cd $GOPATH/dev/alice
alice$ lncli --rpcserver=localhost:10001 --macaroonpath=data/admin.macaroon create
Aliceのウォレットパスワードを入力して確認するよう求められます。これは8文字より長くする必要があります。暗号シードにパスフレーズを追加するオプションもあります。現時点では、既存のニーモニックがあるかどうかのプロンプトが表示されたら「n」を入力してこの手順をスキップし、Enterを押してパスフレーズなしで続行します。
これで、次のようにいくつかの基本情報をリクエストできます。
alice$ lncli --rpcserver=localhost:10001 --macaroonpath=data/admin.macaroon getinfo
lncliは、Alice lndノードに対してRPC呼び出しを行いました。これは、ノードが稼働中であり、lncliが適切に機能しているかどうかをテストするのに適した方法です。将来のセッションでは、lncli unlockを呼び出して、設定したパスワードでノードをロック解除する必要がある場合があることに注意してください。
新しいターミナルウィンドウを開き、ボブとチャーリーについても同じ操作を行います。 alice $またはbob $は、それぞれAliceまたはBob lncliウィンドウからコマンドを実行することを示します。
# In a new terminal window, setting $GOPATH, etc.
cd $GOPATH/dev/bob
bob$ lncli --rpcserver=localhost:10002 --macaroonpath=data/admin.macaroon create
# Note that you'll have to enter an 8+ character password and "n" for the mnemonic.
# In a new terminal window:
cd $GOPATH/dev/charlie
charlie$ lncli --rpcserver=localhost:10003 --macaroonpath=data/admin.macaroon create
# Note that you'll have to enter an 8+ character password and "n" for the mnemonic.
--rpcserver = localhost:1000Xおよび--macaroonpathフラグを毎回入力しないように、エイリアスを設定できます。以下を.bashrcに追加します。
alias lncli-alice="lncli --rpcserver=localhost:10001 --macaroonpath=data/admin.macaroon"
alias lncli-bob="lncli --rpcserver=localhost:10002 --macaroonpath=data/admin.macaroon"
alias lncli-charlie="lncli --rpcserver=localhost:10003 --macaroonpath=data/admin.macaroon"
これが現在のすべてのターミナルウィンドウに適用されたことを確認するには、.bashrcファイルを再実行します。
alice$ source ~/.bashrc
bob$ source ~/.bashrc
charlie$ source ~/.bashrc
簡単にするために、チュートリアルの残りの部分では、このステップが完了したと仮定します。
lncliオプション
lncliで使用可能なすべてのコマンドを表示するには、単にlncli --helpまたはlncli -hと入力します。
ビットコインアドレスを設定する
Alice の新しいビットコインアドレスを作成しましょう。これは、Alice のオンチェーン残高を保存するアドレスになります。 np2wkhはアドレスのタイプを指定し、Pest to Nested Witness Key Hashの略です。
alice$ lncli-alice newaddress np2wkh
{
"address": <ALICE_ADDRESS>
}
そしてボブとチャーリーの場合:
bob$ lncli-bob newaddress np2wkh
{
"address": <BOB_ADDRESS>
}
charlie$ lncli-charlie newaddress np2wkh
{
"address": <CHARLIE_ADDRESS>
}
資金調達
ここからさらに設定していきます!この時点で、アリス、ボブ、チャーリーのオンチェーンアドレスを生成しました。ここで、btcdを使用した練習を行い、これらのアドレスにsimnet Bitcoinで資金を提供します。
btcdを終了して再実行し、Aliceをすべてのマイニング報酬の受信者として設定します。
btcd --simnet --txindex --rpcuser=kek --rpcpass=kek --miningaddr=<ALICE_ADDRESS>
アリスが報酬を得るように、400ブロックを生成します。コインベースの資金は100回の確認が完了するまで使用できないため、少なくとも100ブロックが必要です。セグウィットを有効にするには約300ブロックが必要です。 $ GOPATHと$ PATHが設定された新しいウィンドウで:
alice$ btcctl --simnet --rpcuser=kek --rpcpass=kek generate 400
segwitがアクティブであることを確認します。
btcctl --simnet --rpcuser=kek --rpcpass=kek getblockchaininfo | grep -A 1 segwit
アリスのウォレットの残高を確認してください。
alice$ lncli-alice walletbalance
アリスだけがお金を持っていると面白くない。チャーリーにもいくつかあげましょう。
# Quit the btcd process that was previously started with Alice's mining address,
# and then restart it with:
btcd --txindex --simnet --rpcuser=kek --rpcpass=kek --miningaddr=<CHARLIE_ADDRESS>
# Generate more blocks
btcctl --simnet --rpcuser=kek --rpcpass=kek generate 100
# Check Charlie's balance
charlie$ lncli-charlie walletbalance
P2Pネットワークの作成
アリスとチャーリーがsimnetビットコインを手に入れたので、それらを接続し始めましょう。
アリスをボブに接続します。
# Get Bob's identity pubkey:
bob$ lncli-bob getinfo
{
--->"identity_pubkey": <BOB_PUBKEY>,
"alias": "",
"num_pending_channels": 0,
"num_active_channels": 0,
"num_peers": 0,
"block_height": 450,
"block_hash": "2a84b7a2c3be81536ef92cf382e37ab77f7cfbcf229f7d553bb2abff3e86231c",
"synced_to_chain": true,
"testnet": false,
"chains": [
"bitcoin"
],
"uris": [
],
"best_header_timestamp": "1533350134",
"version": "0.4.2-beta commit=7a5a824d179c6ef16bd78bcb7a4763fda5f3f498"
}
# Connect Alice and Bob together
alice$ lncli-alice connect <BOB_PUBKEY>@localhost:10012
{
}
localhost:10012は、Bob lndノードの起動時に設定した--peerport = 10012フラグに対応していることに注意してください。
アリスとボブがお互いを認識していることを確認しましょう。
# Check that Alice has added Bob as a peer:
alice$ lncli-alice listpeers
{
"peers": [
{
"pub_key": <BOB_PUBKEY>,
"address": "127.0.0.1:10012",
"bytes_sent": "7",
"bytes_recv": "7",
"sat_sent": "0",
"sat_recv": "0",
"inbound": false,
"ping_time": "0"
}
]
}
# Check that Bob has added Alice as a peer:
bob$ lncli-bob listpeers
{
"peers": [
{
"pub_key": <ALICE_PUBKEY>,
"address": "127.0.0.1:60104",
"bytes_sent": "318",
"bytes_recv": "318",
"sat_sent": "0",
"sat_recv": "0",
"inbound": true,
"ping_time": "5788"
}
]
}
BobをCharlieに接続して、P2Pネットワークを完成させます。
charlie$ lncli-charlie connect <BOB_PUBKEY>@localhost:10012
Lightningネットワークのセットアップ
支払いを送信する前に、AliceからBob、およびBobからCharlieへの支払いチャネルを設定する必要があります。
最初に、Alice <–> Bobチャンネルを開きましょう。
alice$ lncli-alice openchannel --node_key=<BOB_PUBKEY> --local_amt=1000000
--local_amtは、Aliceがチャネルにコミットする金額を指定します。オプションの完全なリストを表示するには、lncli openchannel --helpを試してください。
チャネルが有効と見なされるように、6つのブロックをマイニングする必要があります。
btcctl --simnet --rpcuser=kek --rpcpass=kek generate 6
Alice <–> Bobチャネルが作成されたことを確認します。
alice$ lncli-alice listchannels
{
"channels": [
{
"active": true,
"remote_pubkey": <BOB_PUBKEY>,
"channel_point": "2622b779a8acca471a738b0796cd62e4457b79b33265cbfa687aadccc329023a:0",
"chan_id": "495879744192512",
"capacity": "1000000",
"local_balance": "991312",
"remote_balance": "0",
"commit_fee": "8688",
"commit_weight": "600",
"fee_per_kw": "12000",
"unsettled_balance": "0",
"total_satoshis_sent": "0",
"total_satoshis_received": "0",
"num_updates": "0",
"pending_htlcs": [
],
"csv_delay": 144,
"private": false
}
]
}
シングルホップ支払いの送信
最後に、エキサイティングな部分-支払いの送信!アリスからボブに支払いを送ってみましょう。
最初に、Bobは請求書を生成する必要があります。
bob$ lncli-bob addinvoice --amt=10000
{
"r_hash": "<a_random_rhash_value>",
"pay_req": "<encoded_invoice>",
"add_index": 1
}
AliceからBobに支払いを送信します。
alice$ lncli-alice sendpayment --pay_req=<encoded_invoice>
{
"payment_error": "",
"payment_preimage": "baf6929fc95b3824fb774a4b75f6c8a1ad3aaef04efbf26cc064904729a21e28",
"payment_route": {
"total_time_lock": 650,
"total_amt": 10000,
"hops": [
{
"chan_id": 495879744192512,
"chan_capacity": 1000000,
"amt_to_forward": 10000,
"expiry": 650,
"amt_to_forward_msat": 10000000
}
],
"total_amt_msat": 10000000
}
}
# Check that Alice's channel balance was decremented accordingly:
alice$ lncli-alice listchannels
# Check that Bob's channel was credited with the payment amount:
bob$ lncli-bob listchannels
マルチホップ支払い
シングルホップ支払いの送信方法がわかったので、マルチホップ支払いの送信はそれほど難しくありません。 Bob <–> Charlieからチャンネルを設定しましょう:
charlie$ lncli-charlie openchannel --node_key=<BOB_PUBKEY> --local_amt=800000 --push_amt=200000
# Mine the channel funding tx
btcctl --simnet --rpcuser=kek --rpcpass=kek generate 6
今回は--push_amt引数を指定したことに注意してください。これは、最初のチャネル状態で相手に持たせたい金額を指定します。
ボブを経由してアリスからチャーリーに支払いをしましょう。
charlie$ lncli-charlie addinvoice --amt=10000
alice$ lncli-alice sendpayment --pay_req=<encoded_invoice>
# Check that Charlie's channel was credited with the payment amount (e.g. that
# the `remote_balance` has been decremented by 10000)
charlie$ lncli-charlie listchannels
チェンネルの閉鎖
練習のために、チャンネルを閉じてみましょう。チュートリアルの次の段階で再開します。
alice$ lncli-alice listchannels
{
"channels": [
{
"active": true,
"remote_pubkey": "0343bc80b914aebf8e50eb0b8e445fc79b9e6e8e5e018fa8c5f85c7d429c117b38",
---->"channel_point": "3511ae8a52c97d957eaf65f828504e68d0991f0276adff94c6ba91c7f6cd4275:0",
"chan_id": "1337006139441152",
"capacity": "1005000",
"local_balance": "990000",
"remote_balance": "10000",
"unsettled_balance": "0",
"total_satoshis_sent": "10000",
"total_satoshis_received": "0",
"num_updates": "2"
}
]
}
チャネルポイントは、チャネルを一意に識別するコロンで区切られた2つの数字で構成されます。最初の数値は資金調達_txidで、2番目の数値はoutput_indexです。
# Close the Alice<-->Bob channel from Alice's side.
alice$ lncli-alice closechannel --funding_txid=<funding_txid> --output_index=<output_index>
# Mine a block including the channel close transaction to close the channel:
btcctl --simnet --rpcuser=kek --rpcpass=kek generate 1
# Check that Bob's on-chain balance was credited by his settled amount in the
# channel. Recall that Bob previously had no on-chain Bitcoin:
alice$ lncli-bob walletbalance
{
"total_balance": "20001",
"confirmed_balance": "20001",
"unconfirmed_balance": "0"
}
この時点で、btcd、btcctl、lnd、およびlncliの操作方法を学習しました。ステージ2では、Web GUIクライアントを使用してlndを設定および操作する方法を学習します。
将来的には、simnetではなくtestnetでこのワークフローを実行してみてください。testnetLightning Faucetノードを介して対話し、支払いを送信できます。詳細については、DockerガイドのLightning Faucetノードへの接続セクションを参照するか、Lightning Network Faucet・リポジトリをご覧ください。