Skip to content

Commit

Permalink
Share const error_codes between core modules
Browse files Browse the repository at this point in the history
Well-known error codes are used in both send and receive modules. Using constants makes it harder
for a maintainer to accidentally produce or parse the wrong code.
  • Loading branch information
DanGould committed Jan 24, 2025
1 parent acff5cf commit 0e7ce7d
Show file tree
Hide file tree
Showing 4 changed files with 44 additions and 21 deletions.
14 changes: 14 additions & 0 deletions payjoin/src/error_codes.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
//! Well-known error codes as defined in BIP-78
//! See: https://github.com/bitcoin/bips/blob/master/bip-0078.mediawiki#receivers-well-known-errors
/// The payjoin endpoint is not available for now.
pub const UNAVAILABLE: &str = "unavailable";

/// The receiver added some inputs but could not bump the fee of the payjoin proposal.
pub const NOT_ENOUGH_MONEY: &str = "not-enough-money";

/// This version of payjoin is not supported.
pub const VERSION_UNSUPPORTED: &str = "version-unsupported";

/// The receiver rejected the original PSBT.
pub const ORIGINAL_PSBT_REJECTED: &str = "original-psbt-rejected";
3 changes: 3 additions & 0 deletions payjoin/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -55,3 +55,6 @@ pub use bitcoin::base64;
pub use uri::{PjParseError, PjUri, Uri, UriExt};
#[cfg(feature = "_core")]
pub use url::{ParseError, Url};

#[cfg(feature = "_core")]
pub(crate) mod error_codes;
27 changes: 14 additions & 13 deletions payjoin/src/receive/error.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
use std::{error, fmt};

use crate::error_codes::{ORIGINAL_PSBT_REJECTED, UNAVAILABLE, VERSION_UNSUPPORTED};
#[cfg(feature = "v1")]
use crate::receive::v1;
#[cfg(feature = "v2")]
Expand Down Expand Up @@ -43,7 +44,7 @@ impl JsonError for Error {
fn to_json(&self) -> String {
match self {
Self::Validation(e) => e.to_json(),
Self::Implementation(_) => serialize_json_error("unavailable", "Receiver error"),
Self::Implementation(_) => serialize_json_error(UNAVAILABLE, "Receiver error"),
}
}
}
Expand Down Expand Up @@ -206,29 +207,29 @@ impl JsonError for PayloadError {
use InternalPayloadError::*;

match &self.0 {
Utf8(_) => serialize_json_error("original-psbt-rejected", self),
ParsePsbt(_) => serialize_json_error("original-psbt-rejected", self),
Utf8(_) => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
ParsePsbt(_) => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
SenderParams(e) => match e {
super::optional_parameters::Error::UnknownVersion { supported_versions } => {
let supported_versions_json =
serde_json::to_string(supported_versions).unwrap_or_default();
serialize_json_plus_fields(
"version-unsupported",
VERSION_UNSUPPORTED,
"This version of payjoin is not supported.",
&format!(r#""supported": {}"#, supported_versions_json),
)
}
_ => serialize_json_error("sender-params-error", self),
},
InconsistentPsbt(_) => serialize_json_error("original-psbt-rejected", self),
PrevTxOut(_) => serialize_json_error("original-psbt-rejected", self),
MissingPayment => serialize_json_error("original-psbt-rejected", self),
OriginalPsbtNotBroadcastable => serialize_json_error("original-psbt-rejected", self),
InputOwned(_) => serialize_json_error("original-psbt-rejected", self),
InputWeight(_) => serialize_json_error("original-psbt-rejected", self),
InputSeen(_) => serialize_json_error("original-psbt-rejected", self),
PsbtBelowFeeRate(_, _) => serialize_json_error("original-psbt-rejected", self),
FeeTooHigh(_, _) => serialize_json_error("original-psbt-rejected", self),
InconsistentPsbt(_) => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
PrevTxOut(_) => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
MissingPayment => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
OriginalPsbtNotBroadcastable => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
InputOwned(_) => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
InputWeight(_) => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
InputSeen(_) => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
PsbtBelowFeeRate(_, _) => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
FeeTooHigh(_, _) => serialize_json_error(ORIGINAL_PSBT_REJECTED, self),
}
}
}
Expand Down
21 changes: 13 additions & 8 deletions payjoin/src/send/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,10 @@ use bitcoin::locktime::absolute::LockTime;
use bitcoin::transaction::Version;
use bitcoin::Sequence;

use crate::error_codes::{
NOT_ENOUGH_MONEY, ORIGINAL_PSBT_REJECTED, UNAVAILABLE, VERSION_UNSUPPORTED,
};

/// Error building a Sender from a SenderBuilder.
///
/// This error is unrecoverable.
Expand Down Expand Up @@ -279,7 +283,7 @@ impl ResponseError {
json.as_object().and_then(|v| v.get("errorCode")).and_then(|v| v.as_str())
{
match error_code {
"version-unsupported" => {
code if code == VERSION_UNSUPPORTED => {
let supported = json
.as_object()
.and_then(|v| v.get("supported"))
Expand All @@ -288,9 +292,10 @@ impl ResponseError {
.unwrap_or_default();
WellKnownError::VersionUnsupported { message, supported }.into()
}
"unavailable" => WellKnownError::Unavailable(message).into(),
"not-enough-money" => WellKnownError::NotEnoughMoney(message).into(),
"original-psbt-rejected" => WellKnownError::OriginalPsbtRejected(message).into(),
code if code == UNAVAILABLE => WellKnownError::Unavailable(message).into(),
code if code == NOT_ENOUGH_MONEY => WellKnownError::NotEnoughMoney(message).into(),
code if code == ORIGINAL_PSBT_REJECTED =>
WellKnownError::OriginalPsbtRejected(message).into(),
_ => Self::Unrecognized { error_code: error_code.to_string(), message },
}
} else {
Expand Down Expand Up @@ -369,10 +374,10 @@ pub enum WellKnownError {
impl WellKnownError {
pub fn error_code(&self) -> &str {
match self {
WellKnownError::Unavailable(_) => "unavailable",
WellKnownError::NotEnoughMoney(_) => "not-enough-money",
WellKnownError::VersionUnsupported { .. } => "version-unsupported",
WellKnownError::OriginalPsbtRejected(_) => "original-psbt-rejected",
WellKnownError::Unavailable(_) => UNAVAILABLE,
WellKnownError::NotEnoughMoney(_) => NOT_ENOUGH_MONEY,
WellKnownError::VersionUnsupported { .. } => VERSION_UNSUPPORTED,
WellKnownError::OriginalPsbtRejected(_) => ORIGINAL_PSBT_REJECTED,
}
}
pub fn message(&self) -> &str {
Expand Down

0 comments on commit 0e7ce7d

Please sign in to comment.