Skip to content

Commit c98a403

Browse files
committed
Refactor may_announce_channel to return AnnounceError
This error type can provide more context to callers about why the node configuration does not support channel announcements.
1 parent f8005de commit c98a403

File tree

4 files changed

+95
-44
lines changed

4 files changed

+95
-44
lines changed

src/builder.rs

+18-4
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,8 @@
77

88
use crate::chain::{ChainSource, DEFAULT_ESPLORA_SERVER_URL};
99
use crate::config::{
10-
default_user_config, Config, EsploraSyncConfig, DEFAULT_LOG_FILENAME, DEFAULT_LOG_LEVEL,
11-
WALLET_KEYS_SEED_LEN,
10+
default_user_config, may_announce_channel, AnnounceError, Config, EsploraSyncConfig,
11+
DEFAULT_LOG_FILENAME, DEFAULT_LOG_LEVEL, WALLET_KEYS_SEED_LEN,
1212
};
1313

1414
use crate::connection::ConnectionManager;
@@ -32,8 +32,7 @@ use crate::types::{
3232
};
3333
use crate::wallet::persist::KVStoreWalletPersister;
3434
use crate::wallet::Wallet;
35-
use crate::Node;
36-
use crate::{io, NodeMetrics};
35+
use crate::{io, Node, NodeMetrics};
3736

3837
use lightning::chain::{chainmonitor, BestBlock, Watch};
3938
use lightning::io::Cursor;
@@ -912,6 +911,21 @@ fn build_with_store_internal(
912911
liquidity_source_config: Option<&LiquiditySourceConfig>, seed_bytes: [u8; 64],
913912
logger: Arc<Logger>, kv_store: Arc<DynStore>,
914913
) -> Result<Node, BuildError> {
914+
if let Err(err) = may_announce_channel(&config) {
915+
if config.announcement_addresses.is_some() {
916+
log_error!(logger, "Announcement addresses were set but some required configuration options for node announcement are missing: {}", err);
917+
return Err(match err {
918+
AnnounceError::MissingNodeAlias => BuildError::InvalidNodeAlias,
919+
_ => BuildError::InvalidListeningAddresses,
920+
});
921+
}
922+
923+
if config.node_alias.is_some() {
924+
log_error!(logger, "Node alias was set but some required configuration options for node announcement are missing: {}", err);
925+
return Err(BuildError::InvalidListeningAddresses);
926+
}
927+
}
928+
915929
// Initialize the status fields.
916930
let is_listening = Arc::new(AtomicBool::new(false));
917931
let node_metrics = match read_node_metrics(Arc::clone(&kv_store), Arc::clone(&logger)) {

src/config.rs

+48-9
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ use lightning::util::config::UserConfig;
1919
use bitcoin::secp256k1::PublicKey;
2020
use bitcoin::Network;
2121

22+
use std::fmt;
2223
use std::time::Duration;
2324

2425
// Config defaults
@@ -261,9 +262,37 @@ pub fn default_config() -> Config {
261262
Config::default()
262263
}
263264

264-
pub(crate) fn may_announce_channel(config: &Config) -> bool {
265-
config.node_alias.is_some()
266-
&& config.listening_addresses.as_ref().map_or(false, |addrs| !addrs.is_empty())
265+
#[derive(Debug, PartialEq)]
266+
pub(crate) enum AnnounceError {
267+
MissingNodeAlias,
268+
MissingListeningAddresses,
269+
MissingBoth,
270+
}
271+
272+
impl fmt::Display for AnnounceError {
273+
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
274+
match self {
275+
AnnounceError::MissingNodeAlias => write!(f, "Node alias is not configured"),
276+
AnnounceError::MissingListeningAddresses => {
277+
write!(f, "Listening addresses are not configured")
278+
},
279+
AnnounceError::MissingBoth => {
280+
write!(f, "Node alias and listening addresses are not configured")
281+
},
282+
}
283+
}
284+
}
285+
286+
pub(crate) fn may_announce_channel(config: &Config) -> Result<(), AnnounceError> {
287+
let has_listening_addresses =
288+
config.listening_addresses.as_ref().map_or(false, |addrs| !addrs.is_empty());
289+
290+
match (config.node_alias.is_some(), has_listening_addresses) {
291+
(true, true) => Ok(()),
292+
(true, false) => Err(AnnounceError::MissingListeningAddresses),
293+
(false, true) => Err(AnnounceError::MissingNodeAlias),
294+
(false, false) => Err(AnnounceError::MissingBoth),
295+
}
267296
}
268297

269298
pub(crate) fn default_user_config(config: &Config) -> UserConfig {
@@ -278,7 +307,7 @@ pub(crate) fn default_user_config(config: &Config) -> UserConfig {
278307
user_config.channel_handshake_config.negotiate_anchors_zero_fee_htlc_tx =
279308
config.anchor_channels_config.is_some();
280309

281-
if !may_announce_channel(config) {
310+
if may_announce_channel(config).is_err() {
282311
user_config.accept_forwards_to_priv_channels = false;
283312
user_config.channel_handshake_config.announce_for_forwarding = false;
284313
user_config.channel_handshake_limits.force_announced_channel_preference = true;
@@ -443,6 +472,7 @@ mod tests {
443472
use std::str::FromStr;
444473

445474
use super::may_announce_channel;
475+
use super::AnnounceError;
446476
use super::Config;
447477
use super::NodeAlias;
448478
use super::SocketAddress;
@@ -451,7 +481,7 @@ mod tests {
451481
fn node_announce_channel() {
452482
// Default configuration with node alias and listening addresses unset
453483
let mut node_config = Config::default();
454-
assert!(!may_announce_channel(&node_config));
484+
assert_eq!(may_announce_channel(&node_config), Err(AnnounceError::MissingBoth));
455485

456486
// Set node alias with listening addresses unset
457487
let alias_frm_str = |alias: &str| {
@@ -460,24 +490,33 @@ mod tests {
460490
NodeAlias(bytes)
461491
};
462492
node_config.node_alias = Some(alias_frm_str("LDK_Node"));
463-
assert!(!may_announce_channel(&node_config));
493+
assert_eq!(
494+
may_announce_channel(&node_config),
495+
Err(AnnounceError::MissingListeningAddresses)
496+
);
464497

465498
// Set announcement addresses with listening addresses unset
466499
let announcement_address = SocketAddress::from_str("123.45.67.89:9735")
467500
.expect("Socket address conversion failed.");
468501
node_config.announcement_addresses = Some(vec![announcement_address]);
469-
assert!(!may_announce_channel(&node_config));
502+
assert_eq!(
503+
may_announce_channel(&node_config),
504+
Err(AnnounceError::MissingListeningAddresses)
505+
);
470506

471507
// Set node alias with an empty list of listening addresses
472508
node_config.listening_addresses = Some(vec![]);
473-
assert!(!may_announce_channel(&node_config));
509+
assert_eq!(
510+
may_announce_channel(&node_config),
511+
Err(AnnounceError::MissingListeningAddresses)
512+
);
474513

475514
// Set node alias with a non-empty list of listening addresses
476515
let socket_address =
477516
SocketAddress::from_str("localhost:8000").expect("Socket address conversion failed.");
478517
if let Some(ref mut addresses) = node_config.listening_addresses {
479518
addresses.push(socket_address);
480519
}
481-
assert!(may_announce_channel(&node_config));
520+
assert!(may_announce_channel(&node_config).is_ok());
482521
}
483522
}

src/event.rs

+15-17
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ use crate::{
1212
UserChannelId,
1313
};
1414

15-
use crate::config::{may_announce_channel, Config};
15+
use crate::config::{may_announce_channel, AnnounceError, Config};
1616
use crate::connection::ConnectionManager;
1717
use crate::fee_estimator::ConfirmationTarget;
1818
use crate::liquidity::LiquiditySource;
@@ -1057,23 +1057,21 @@ where
10571057
is_announced,
10581058
params: _,
10591059
} => {
1060-
if is_announced && !may_announce_channel(&*self.config) {
1061-
log_error!(
1062-
self.logger,
1063-
"Rejecting inbound announced channel from peer {} as not all required details are set. Please ensure node alias and listening addresses have been configured.",
1064-
counterparty_node_id,
1065-
);
1060+
if is_announced {
1061+
if let Err(err) = may_announce_channel(&*self.config) {
1062+
log_error!(self.logger, "Rejecting inbound announced channel from peer {} due to missing configuration: {}", counterparty_node_id, err);
10661063

1067-
self.channel_manager
1068-
.force_close_without_broadcasting_txn(
1069-
&temporary_channel_id,
1070-
&counterparty_node_id,
1071-
"Channel request rejected".to_string(),
1072-
)
1073-
.unwrap_or_else(|e| {
1074-
log_error!(self.logger, "Failed to reject channel: {:?}", e)
1075-
});
1076-
return Ok(());
1064+
self.channel_manager
1065+
.force_close_without_broadcasting_txn(
1066+
&temporary_channel_id,
1067+
&counterparty_node_id,
1068+
"Channel request rejected".to_string(),
1069+
)
1070+
.unwrap_or_else(|e| {
1071+
log_error!(self.logger, "Failed to reject channel: {:?}", e)
1072+
});
1073+
return Ok(());
1074+
}
10771075
}
10781076

10791077
let anchor_channel = channel_type.requires_anchors_zero_fee_htlc_tx();

src/lib.rs

+14-14
Original file line numberDiff line numberDiff line change
@@ -123,8 +123,8 @@ pub use builder::NodeBuilder as Builder;
123123

124124
use chain::ChainSource;
125125
use config::{
126-
default_user_config, may_announce_channel, ChannelConfig, Config, NODE_ANN_BCAST_INTERVAL,
127-
PEER_RECONNECTION_INTERVAL, RGS_SYNC_INTERVAL,
126+
default_user_config, may_announce_channel, AnnounceError, ChannelConfig, Config,
127+
NODE_ANN_BCAST_INTERVAL, PEER_RECONNECTION_INTERVAL, RGS_SYNC_INTERVAL,
128128
};
129129
use connection::ConnectionManager;
130130
use event::{EventHandler, EventQueue};
@@ -414,7 +414,7 @@ impl Node {
414414
let bcast_node_metrics = Arc::clone(&self.node_metrics);
415415
let mut stop_bcast = self.stop_sender.subscribe();
416416
let node_alias = self.config.node_alias.clone();
417-
if may_announce_channel(&self.config) {
417+
if may_announce_channel(&self.config).is_ok() {
418418
runtime.spawn(async move {
419419
// We check every 30 secs whether our last broadcast is NODE_ANN_BCAST_INTERVAL away.
420420
#[cfg(not(test))]
@@ -1211,19 +1211,19 @@ impl Node {
12111211
&self, node_id: PublicKey, address: SocketAddress, channel_amount_sats: u64,
12121212
push_to_counterparty_msat: Option<u64>, channel_config: Option<ChannelConfig>,
12131213
) -> Result<UserChannelId, Error> {
1214-
if may_announce_channel(&self.config) {
1215-
self.open_channel_inner(
1216-
node_id,
1217-
address,
1218-
channel_amount_sats,
1219-
push_to_counterparty_msat,
1220-
channel_config,
1221-
true,
1222-
)
1223-
} else {
1224-
log_error!(self.logger, "Failed to open announced channel as the node hasn't been sufficiently configured to act as a forwarding node. Please make sure to configure listening addreesses and node alias");
1214+
if let Err(err) = may_announce_channel(&self.config) {
1215+
log_error!(self.logger, "Failed to open announced channel as the node hasn't been sufficiently configured to act as a forwarding node: {}", err);
12251216
return Err(Error::ChannelCreationFailed);
12261217
}
1218+
1219+
self.open_channel_inner(
1220+
node_id,
1221+
address,
1222+
channel_amount_sats,
1223+
push_to_counterparty_msat,
1224+
channel_config,
1225+
true,
1226+
)
12271227
}
12281228

12291229
/// Manually sync the LDK and BDK wallets with the current chain state and update the fee rate

0 commit comments

Comments
 (0)