Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Feature Request] Add command to mine a block #183

Open
kdmukai opened this issue Dec 22, 2023 · 8 comments
Open

[Feature Request] Add command to mine a block #183

kdmukai opened this issue Dec 22, 2023 · 8 comments

Comments

@kdmukai
Copy link

kdmukai commented Dec 22, 2023

I'm using nigiri in regtest alongside Sparrow. When I broadcast a tx via Sparrow, I want to be able to issue a nigiri command to mine a block to get a confirmation.

Yes, I could "faucet" or rpc "generatetoaddress" to move it forward, but in either case I have to grab a new address when all I care about is getting a quick confirmation.

Something like: nigiri mine would be straightforward, which already aligns with the Mine method in Chopsticks.

@bordalix
Copy link

You have full access to the bitcoin-cli commands using rpc

You can generate a new block using nigiri rpc --generate 1

@kdmukai
Copy link
Author

kdmukai commented Dec 22, 2023

That definitely helps!

Though I'd still love the noob-friendly convenience of a nigiri mine [n] shortcut.

I'm hoping that nigiri + Sparrow (or other bitcoin software of choice) can be an easy way to encourage less technical people to feel free to experiment via regtest (e.g. build your own multisig, receive a deposit, spent it back out).

Nigiri is already so temptingly close to "max easy mode" and, at least in my brief usage thus far, a trivial nigiri mine command would make it a fait acompli.

If nothing else, if it was its own command it would be listed in nigiri help. Also note that --generate is not listed in the long nigiri rpc help.

@tiero
Copy link
Member

tiero commented Dec 23, 2023

Hey @kdmukai thanks for opening this issue.

Do you know every transaction broadcasted through the POST /tx endpoint on the Esplora service or nigiri push <hex>, automatically mines a block?

This is in my experience 99% of the time you want to mine a block after you broadcast one tx, and usually client software uses Esplora rather to interact with a plain Bitcoin Core node.

That being said I am happy to add a manual command nigiri mine if both workflows are not enough dev/user friendly 👌

@tiero
Copy link
Member

tiero commented Dec 23, 2023

When I broadcast a tx via Sparrow,

@kdmukai Do you know what Sparrow uses to broadcast tx? Does it require a Bitcoin JSONRPC to be available or uses a public Electrum Server?

I wish to support all wallet software in a way the dev/user never has to manually mine blocks, but they should automatically mined for you, when we detect a tx is in the mempool

@kdmukai
Copy link
Author

kdmukai commented Dec 26, 2023

@tiero Sparrow gives you the option to connect directly to bitcoind rpc or an electrum server.

Testing my Sparrow -> nigiri connection shows:

Screenshot 2023-12-26 at 9 47 55 AM

Broadcasting a tx with Sparrow in regtest to nigiri in regtest shows the tx as pending in Sparrow but no confirmations.

The electrs logs show:

electrs  | TRACE - RPC Request("{\"jsonrpc\":\"2.0\",\"method\":\"blockchain.transaction.broadcast\",\"params\":[\"02000000000101d20322d0112e41250077d631376122fbb2ab8f87415a2691a1c8deba8f4885160000000000fdffffff02e6a1e11100000000160014398d7435a34b4f1219923a1a75242a5ff6b06d1580f0fa020000000016001432b907421f38b52ecc13806d653c18e145d24d8b02473044022048185328296636b053b323603007111b26ba4ec0ea739c47d4068cf3c3304cca02204050027d0f72e88b88079a5ef69a019f402c14635155cd35b7bbf93286a45b75012103b0e28c958ab11c14258d9f280dd2c13e8c3d0eb01ab20929c386d2e7737e180a68000000\"],\"id\":210}\n")

And I think this is unrelated, but also saw this about the same tx:

electrs  | TRACE - RPC PeriodicUpdate
electrs  | TRACE - RPC Request("{\"jsonrpc\":\"2.0\",\"method\":\"blockchain.transaction.get\",\"params\":[\"66fe4ca479544383d74d3ae4180d4979fa118b4c6ccc766bc0e21972bd6abcdf\",true],\"id\":211}\n")
electrs  | WARN - rpc #211 blockchain.transaction.get [String("66fe4ca479544383d74d3ae4180d4979fa118b4c6ccc766bc0e21972bd6abcdf"), Bool(true)] failed: Error: verbose transactions are currently unsupported

@tiero
Copy link
Member

tiero commented Dec 26, 2023

ah-ha I see, they use Electrum protocol over TCP, not Esplora REST. I think we could extend nigiri-chopsticks HTTP passthrough to also monitor the Electrum port and mine the block when blockchain.transaction.broadcast is sent. Once we are there we can also react to Bitcoin Core sendrawtransaction.

What do you think? @altafan

@altafan
Copy link
Collaborator

altafan commented Dec 27, 2023

I think we could extend nigiri-chopsticks HTTP passthrough to also monitor the Electrum port and mine the block when blockchain.transaction.broadcast is sent.

not sure if we will find a message containing blockchain.transaction.broadcast by watching electrs' outgoing traffic, for sure we can find it by watching the logs.

We could fetch the logs by setting up a prometheus instance maybe, but the easiest way to me is making use of docker logs electrs-liquid -f to get logs in real-time as electrs doesn't seem to persist them in any file we could eventually read.

Once we are there we can also react to Bitcoin Core sendrawtransaction.

This is even more tricky since chopsticks wraps the Esplora POST /tx that leverages sendrawtransaction to mine a block when broadcasting a tx.
We should find a way to understand if a block is mined once a tx is broadcasted (POST /tx is used) or mine one otherwise.

@tiero I think for now it makes sense to add a nigiri mine [--liquid] rpc to the nigiri CLI that just gives us time to think about a proper design to support this feature, since it's not as simple as it looks.

@tiero
Copy link
Member

tiero commented Dec 28, 2023

Electrs exposes Electrum JSONRPC server over raw TCP, not JSONRPC over HTTP.

I concur that the best thing would be to listen on an additional port for TCP on chopsticks:

  1. Listen on a port of choice
ln, err := net.Listen("tcp", ":1234") // Replace 1234 with your port
if err != nil {
    // handle error
}
for {
    conn, err := ln.Accept()
    if err != nil {
        // handle error
        continue
    }
    go handleConnection(conn)
}
  1. Unmarshall the packets into JSONRPC requests, then make the
func handleConnection(conn net.Conn) {
    // Read data from conn
    // ...
    defer conn.Close()
}
  1. Make a TCP connection to the Electrum server of Electrs
  2. Send the JSON-RPC request
  3. Read the response
  4. Write the response back to conn

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants