Skip to content

Check for spendable UTXOs before payjoin operations#1071

Merged
arminsabouri merged 1 commit into
payjoin:masterfrom
0xZaddyy:fix-utxo-error
Dec 4, 2025
Merged

Check for spendable UTXOs before payjoin operations#1071
arminsabouri merged 1 commit into
payjoin:masterfrom
0xZaddyy:fix-utxo-error

Conversation

@0xZaddyy

@0xZaddyy 0xZaddyy commented Sep 15, 2025

Copy link
Copy Markdown
Contributor

This PR improves error handling when a wallet has no UTXOs.
Previously, attempting to send or receive without UTXOs returned a generic Error: Obtained failure status(500): Internal Server Error.
This change lets the code now performs UTXO checks and provides informative error messages for both send and receive operations.
This makes failures more user-friendly and easier to debug.
Closes #1070

Pull Request Checklist

Please confirm the following before requesting review:

@coveralls

coveralls commented Sep 15, 2025

Copy link
Copy Markdown
Collaborator

Pull Request Test Coverage Report for Build 17735121824

Details

  • 13 of 22 (59.09%) changed or added relevant lines in 4 files are covered.
  • 3 unchanged lines in 1 file lost coverage.
  • Overall coverage decreased (-0.1%) to 85.688%

Changes Missing Coverage Covered Lines Changed/Added Lines %
payjoin-cli/src/app/mod.rs 2 5 40.0%
payjoin-cli/src/app/v1.rs 2 8 25.0%
Files with Coverage Reduction New Missed Lines %
payjoin-cli/src/app/v2/mod.rs 3 79.07%
Totals Coverage Status
Change from base Build 17685450439: -0.1%
Covered Lines: 8065
Relevant Lines: 9412

💛 - Coveralls

@arminsabouri arminsabouri left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

cACK

New validation and its use look correct to me. I had one suggestion for the error messages. Lastly, do you mind re-writing your commit message to include the rationale for the change. Not just what changes were made.

Great work 🔥

Comment thread payjoin-cli/src/app/v1.rs Outdated
if candidate_inputs.is_empty() {
return Err(ImplementationError::from(
anyhow::anyhow!(
"No spendable UTXOs available in wallet. Cannot contribute inputs to payjoin."

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nit: Lets add a call to action.

Suggested change
"No spendable UTXOs available in wallet. Cannot contribute inputs to payjoin."
"No spendable UTXOs available in wallet. Please fund your wallet before resuming this session"

This gives the user two thing todo:

  1. Fund the wallet
  2. Resume the session

@0xZaddyy

Copy link
Copy Markdown
Contributor Author

cACK

New validation and its use look correct to me. I had one suggestion for the error messages. Lastly, do you mind re-writing your commit message to include the rationale for the change. Not just what changes were made.

Great work 🔥

Thank you @arminsabouri
i'll fix it now

Previously, attempting payjoin operations with an empty wallet resulted in a generic "500 Internal Server Error" from bitcoind. This created a poor user experience because users could not understand why their payjoin failed or what action to take.
@spacebear21

Copy link
Copy Markdown
Collaborator

Is this actually a payjoin-cli issue or was our RPC client (ripped out in #1063) just just not displaying the bitcoind error properly?

@spacebear21 spacebear21 left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ACK 213f98b

@arminsabouri arminsabouri left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We have one follow up task for the receiver. Otherwise the error messaging seems like a strict improvement over what we have.

Comment on lines +476 to +480
if candidate_inputs.is_empty() {
return Err(anyhow::anyhow!(
"No spendable UTXOs available in wallet. Cannot contribute inputs to payjoin."
));
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This check if fine as the internal error is opaque and this is checked in the input selection logic https://github.com/payjoin/rust-payjoin/blob/3f057e130d45c423a22c5e41007529cc0ee6894f/payjoin/src/core/receive/common/mod.rs#L273C51-L273C87

But ideally the receiver should fallback here instead. And we propogate the internally error somehow so we don't have a duplicate check

Comment thread payjoin-cli/src/app/v1.rs
let candidate_inputs =
wallet.list_unspent().map_err(|e| ImplementationError::from(e.into_boxed_dyn_error()))?;

if candidate_inputs.is_empty() {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same comment as v2 applies here

@arminsabouri
arminsabouri merged commit 956c8b6 into payjoin:master Dec 4, 2025
10 checks passed
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

Successfully merging this pull request may close these issues.

Payjoin-cli should check for spendable utxos before trying to payjoin

4 participants