the payjoin candidate filter (_filterAvailableUtxos, payjoin_repository_impl.dart) removes only locked and non-Bitcoin UTXOs, never confirmation depth, so the receiver can contribute a 0-conf input.
this is a temporal fingerprint: an unconfirmed-ancestor spend is observable on-chain and partitions the payjoin's anonymity set by elimination (receivers that only contribute confirmed inputs are ruled out). A 0-conf parent can also be RBF'd out, invalidating the payjoin.
fix: exclude 0-conf from the payjoin candidates (confirmations > 0). the field already exists on WalletUtxoModel. Scoped to the payjoin receiver path; normal sends are unaffected.
ref: payjoin/rust-payjoin#1597 (comment)
the payjoin candidate filter (
_filterAvailableUtxos,payjoin_repository_impl.dart) removes only locked and non-Bitcoin UTXOs, never confirmation depth, so the receiver can contribute a 0-conf input.this is a temporal fingerprint: an unconfirmed-ancestor spend is observable on-chain and partitions the payjoin's anonymity set by elimination (receivers that only contribute confirmed inputs are ruled out). A 0-conf parent can also be RBF'd out, invalidating the payjoin.
fix: exclude 0-conf from the payjoin candidates (
confirmations > 0). the field already exists onWalletUtxoModel. Scoped to the payjoin receiver path; normal sends are unaffected.ref: payjoin/rust-payjoin#1597 (comment)