This guide is for building and using c-lightning
on the Liquid sidechain to create Lightning payment channels. With these payment channels, users can transact Liquid-BTC (bitcoin transferred to the Liquid sidechain) instantly and privately.
Support for Confidential Transactions and Issued Assets is planned, so users will be able to transact any asset issued on the Liquid Network in a Lightning payment channel — such as tokenized fiat, crypto assets, attested assets (e.g. gold coins), or completely new assets. Also, support for swapping on-chain BTC for L-BTC in a payment channel is being worked on.
Using c-lightning
on Liquid is practically the same procedure as using it on the Bitcoin mainnet, so if you’re familiar with that then the steps here will be easy to follow (although they’re fairly easy regardless :-)).
Sections
Installing the required software
Running lightningd
Opening a Lightning payment channel
Transacting L-BTC via a Lightning payment
Closing the payment channel
Contributing to c-lightning
Installing the required software
To begin, a synced Bitcoin node and an Elements node synced to the Liquid chain are required to open Lightning payment channels on the Liquid sidechain.
Follow these guides to get each running:
(For Elements, add chain=liquidv1
to elements.conf
to sync to Liquid)
Once both nodes are synced, make sure you have all of the dependencies, then grab the lightning-elements
branch from Christian Decker’s Github repository.
Install dependencies:
sudo apt-get install -y \
autoconf automake build-essential git libtool libgmp-dev \
libsqlite3-dev python python3 net-tools zlib1g-dev libsodium-dev
Download the lightning-elements
branch:
$ git clone https://github.com/elementsproject/lightning
$ cd lightning
Build the code:
$ ./configure
$ make
Now there should be Elements / Liquid-compatible binaries in their respective directories, including lightningd/lightningd
and cli/lightning-cli
.
Running lightningd
lightningd
provides a --network
argument to choose which blockchain one wants to run on, such as the Bitcoin mainnet, testnet, regtest, and so on. The lightning-elements
branch also supports the liquid
sidechain, so let’s use that option to get started.
$ ./lightningd/lightningd --network liquid ... <other arguments>
This will sync to the Liquid sidechain and start running.
Opening a Lightning payment channel
Now we can begin funding an address in order to open a Lightning channel. Simply use lightning-cli
to generate a p2sh-segwit address and send it some L-BTC.
To acquire Liquid-BTC (L-BTC), either obtain some from a Liquid member exchange such as Bitfinex, The Rock Trading, or shapeshift.ai, or perform a peg-in manually by following this guide.
Generate the p2sh-segwit address:
$ ./cli/lightning-cli newaddr p2sh-segwit
{
"address" : "Gqkico7M9JGyQmk2TjFgqXwYMrrT2ExwXL",
"p2sh-segwit" : "Gqkico7M9JGyQmk2TjFgqXwYMrrT2ExwXL"
}
Fund that address with some L-BTC, then connect to a Liquid Lightning peer.
(For this guide / demo, a peer running on the local network is used)
connect public_key@ip_address:port
$ ./cli/lightning-cli connect 0322d8d3fb7e77a88f373fa369a3e91cb63a24f1313c480ae09c5ffc56dbef7ead@192.168.1.230
{
"id" : "0322d8d3fb7e77a88f373fa369a3e91cb63a24f1313c480ae09c5ffc56dbef7ead"
}
The peer will be shown with the listpeers
command.
$ ./cli/lightning-cli listpeers
{
"peers" : [
{
"id" : "0322d8d3fb7e77a88f373fa369a3e91cb63a24f1313c480ae09c5ffc56dbef7ead",
"connected" : true,
"netaddr" : [
"192.168.1.230:9735"
],
"globalfeatures" : "",
"localfeatures" : "aa",
"channels" : []
}
]
}
The L-BTC transaction will have confirmed by now due to the fast settlement times on the Liquid sidechain (1–2 minutes).
$ ./cli/lightning-cli listfunds
{
"outputs" : [
{
"txid" : "1ca26aa0c5938997b82abd9de25e5207bedb08bf46635ff40b067e2e91d735e4",
"output" : 0,
"value" : 100000,
"amount_msat" : "100000000msat",
"address" : "Gqkico7M9JGyQmk2TjFgqXwYMrrT2ExwXL",
"status" : "confirmed"
}, ],
"channels" : []
}
As shown in bold, the output is 0.00100000 L-BTC.
Open a channel
Now that an address is funded with some L-BTC, initiate a channel opening.
fundchannel <peer id> <amount in satoshis>
The amount can also be all
to use all available L-BTC in the wallet.
$ ./cli/lightning-cli fundchannel 0322d8d3fb7e77a88f373fa369a3e91cb63a24f1313c480ae09c5ffc56dbef7ead 100000
The text output after entering that command will be the transaction hex, ID, and the channel ID.
{
"tx" : "020000000102167ff7b6501b78069db92d0dc1abc56bd12e3e12a049a7e668ea0023ed68db9f00000000171600144c36e234a654d79b3c052a98c087ca51a69077a9ffffffffe435d7912e7e060bf45f6346bf08dbbe07525ee29dbd2ab8978993c5a06aa21c00000000171600144c36e234a654d79b3c052a98c087ca51a69077a9ffffffff03016d521c38ec1ea15734ae22b7c46064412829c0d0579f0a713d1c04ede979026f0100000000000186a000220020f6c2e31f79596b12c103fa6b6d42dbe422e42bf3ca208247301ebb6a34f16f2e016d521c38ec1ea15734ae22b7c46064412829c0d0579f0a713d1c04ede979026f010000000000957e5d00160014aefd2d126fc8f9bbbeea3aad39dab5564c7b92ae016d521c38ec1ea15734ae22b7c46064412829c0d0579f0a713d1c04ede979026f010000000000000192000000000000000002483045022100fe77d62b82afb07cf77a4a332cec1e5bce9f9419ca17c7c7385515790c9c4e1102202ac8d4f74f9c4d40fb51515ea12603e3bea1d3fb5749beab475a3de9bc861b7e0121022b46e22dea88d566d894d98e406b1a24b8b985821457875dd4fc909dd2522bfc0000000247304402203f43266df0423aedc1a4c78999f470e34fd698ab993787644f76885c9c372ed802204665f7ff9644ff7f9b7c3a13ec16bf1ed96120a1d348aaa7a96fc1df49c9d6090121022b46e22dea88d566d894d98e406b1a24b8b985821457875dd4fc909dd2522bfc00000000000000",
"txid" : "e6dda930c3fca7102bae1222928d022b3cf8664667a1b3b33680955ad2c0cf41",
"channel_id" : "41cfc0d25a958036b3b3a1674666f83c2b028d922212ae2b10a7fcc330a9dde6"
}
The channel will then be shown in listpeers
as ”state” : “CHANNELD_AWAITING_LOCKIN”
.
listpeers
will show “CHANNELD_NORMAL:Funding transaction locked.”
after 3 Liquid blocks (3 minutes).
Now the Lightning channel is open!
Transacting L-BTC via a Lightning payment
Now that a channel is open to a peer on the local network, we can generate a Lightning invoice and send an L-BTC micropayment.
Generate an invoice
The arguments for invoice
are as follows:
invoice msatoshi label description
In this example, an invoice for 1 millisatoshi of L-BTC with the label “test1” and description “testing lightning on liquid” is created on the receiving node. The invoice itself is a long string of seemingly random numbers and letters beginning with ln
.
$ ./cli/lightning-cli invoice 1 test1 "testing lightning on liquid"
{
"payment_hash" : "1c03f18a5e3f36a7100c6524794cef9ef8873f3fb22ed5ec6311936e794b71cb",
"expires_at" : 1562629445,
"bolt11" : "lnex10p1pw34xk9pp5rsplrzj78um2wyqvv5j8jn80nmugw0elkghdtmrrzxfku72tw89sdpvw3jhxarfdenjqmrfva58gmnfdenjqmmwypkxjut4d9jqxqyjw5qcqp2mvzgw7fk48sn0n3jwuycs9ahqtl4nc7qp8j69g6sfphjyktztcnyqtsynjjykqc30820p5avqaf9af2mcsjctwwxj8avkpjfv2vh0dqq2wyzpa",
}
Decoding the invoice
On the sending node, use decodepay
to decode the bech32 Lightning invoice.
$ ./cli/lightning-cli decodepay lnex10p1pw34xk9pp5rsplrzj78um2wyqvv5j8jn80nmugw0elkghdtmrrzxfku72tw89sdpvw3jhxarfdenjqmrfva58gmnfdenjqmmwypkxjut4d9jqxqyjw5qcqp2mvzgw7fk48sn0n3jwuycs9ahqtl4nc7qp8j69g6sfphjyktztcnyqtsynjjykqc30820p5avqaf9af2mcsjctwwxj8avkpjfv2vh0dqq2wyzpa
{
"currency" : "ex",
"created_at" : 1562024645,
"expiry" : 604800,
"payee" : "0322d8d3fb7e77a88f373fa369a3e91cb63a24f1313c480ae09c5ffc56dbef7ead",
"msatoshi" : 1,
"amount_msat" : "1msat",
"description" : "testing lightning on liquid",
"min_final_cltv_expiry" : 10,
"payment_hash" : "1c03f18a5e3f36a7100c6524794cef9ef8873f3fb22ed5ec6311936e794b71cb",
"signature" : "3045022100db04877936a9e137ce3277098817b702ff59e3c009e5a2a350486f2259625e260220402e049ca44b031179d4f0d3ac07525ea55bc42585b9c691facb0649629977b4"
}
Finally, pay the invoice
On the sending node, use pay
to pay the 0.00000000001 L-BTC.
$ ./cli/lightning-cli pay lnex10p1pw34xk9pp5rsplrzj78um2wyqvv5j8jn80nmugw0elkghdtmrrzxfku72tw89sdpvw3jhxarfdenjqmrfva58gmnfdenjqmmwypkxjut4d9jqxqyjw5qcqp2mvzgw7fk48sn0n3jwuycs9ahqtl4nc7qp8j69g6sfphjyktztcnyqtsynjjykqc30820p5avqaf9af2mcsjctwwxj8avkpjfv2vh0dqq2wyzpa
{
"id" : 1,
"payment_hash" : "1c03f18a5e3f36a7100c6524794cef9ef8873f3fb22ed5ec6311936e794b71cb",
"destination" : "0322d8d3fb7e77a88f373fa369a3e91cb63a24f1313c480ae09c5ffc56dbef7ead",
"msatoshi" : 1,
"amount_msat" : "1msat",
"msatoshi_sent" : 1,
"amount_sent_msat" : "1msat",
"created_at" : 1562024759,
"status" : "complete",
"payment_preimage" : "7c6357460a3782ed806c8661b0b20c65287ecdc9cf7c6a9c2e85399ffff88f15",
"bolt11" : "lnex10p1pw34xk9pp5rsplrzj78um2wyqvv5j8jn80nmugw0elkghdtmrrzxfku72tw89sdpvw3jhxarfdenjqmrfva58gmnfdenjqmmwypkxjut4d9jqxqyjw5qcqp2mvzgw7fk48sn0n3jwuycs9ahqtl4nc7qp8j69g6sfphjyktztcnyqtsynjjykqc30820p5avqaf9af2mcsjctwwxj8avkpjfv2vh0dqq2wyzpa"
}
The "status" : "complete",
shows that the payment is complete and the invoice is paid!
Closing the payment channel
Feel free to send L-BTC back and forth between your nodes. After you’re done testing and want to close the channel, follow these steps.
On one of the nodes, initiate a cooperative channel closing by issuing a close
command with lightning-cli
.
$ ./cli/lightning-cli close <channel id>
This will submit a closing transaction on-chain and the channel will be closed.
Contributing to c-lightning
If you’re interested in contributing to c-lightning or Elements / Liquid development, feel free to check out the code on Github and join #c-lightning and #sidechains-dev on Freenode to chat with Blockstream engineers and other independent developers.
Thanks for reading!