-
Notifications
You must be signed in to change notification settings - Fork 385
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
Add channel scoring to get_route #1124
Add channel scoring to get_route #1124
Conversation
Codecov Report
@@ Coverage Diff @@
## main #1124 +/- ##
==========================================
+ Coverage 90.60% 91.36% +0.76%
==========================================
Files 66 67 +1
Lines 34474 37698 +3224
==========================================
+ Hits 31235 34443 +3208
- Misses 3239 3255 +16
Continue to review full report at Codecov.
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Benchmarks are probably about what I'd expect given the expansion of of in-cmp logic. Something to look into eventually, probably:
Latest git
test ln::channelmanager::bench::bench_sends ... bench: 9,128,177 ns/iter (+/- 1,349,843)
test routing::network_graph::benches::read_network_graph ... bench: 1,777,566,078 ns/iter (+/- 23,897,528)
test routing::network_graph::benches::write_network_graph ... bench: 159,355,206 ns/iter (+/- 5,292,557)
test routing::router::benches::generate_mpp_routes ... bench: 74,852,606 ns/iter (+/- 55,662,508)
test routing::router::benches::generate_routes ... bench: 72,321,963 ns/iter (+/- 56,925,293)
test bench::bench_sends ... bench: 211,670,987 ns/iter (+/- 188,695,358)
This PR:
test ln::channelmanager::bench::bench_sends ... bench: 8,284,024 ns/iter (+/- 443,276)
test routing::network_graph::benches::read_network_graph ... bench: 1,614,888,492 ns/iter (+/- 2,280,811)
test routing::network_graph::benches::write_network_graph ... bench: 143,246,612 ns/iter (+/- 458,059)
test routing::router::benches::generate_mpp_routes ... bench: 96,742,965 ns/iter (+/- 52,848,627)
test routing::router::benches::generate_routes ... bench: 96,963,520 ns/iter (+/- 62,975,254)
test bench::bench_sends ... bench: 190,069,734 ns/iter (+/- 168,900,474)
Note for comparison bench for 0.0.101 was (there's obviously a ton of noise in these numbers from github CI).
|
All good feedback! Thanks for divining into benchmarks. All comments addressed. |
Github CI now says (which is, uhmmmm, faster than latest git? yea, no, that's just cause github's CI machines are clearly very heterogeneous....last time I look at that output.........)
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Needs tests but otherwise good.
lightning/src/routing/router.rs
Outdated
@@ -163,12 +164,19 @@ struct RouteGraphNode { | |||
/// The effective htlc_minimum_msat at this hop. If a later hop on the path had a higher HTLC | |||
/// minimum, we use it, plus the fees required at each earlier hop to meet it. | |||
path_htlc_minimum_msat: u64, | |||
/// All penalties incurred *after* this hop on the way to the destination, as calculated using | |||
/// channel scoring. | |||
next_hops_penalty_msat: u64, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use of next_hops
in these confused me somewhat - next_hops_fee_msat
(both in a PathBuildingHop
and in the add_node macro) refers to only fee after the hop but not including the fee charged at the hop, whereas here we're using it to include the penalty charged at a hop. Maybe path_penalty_msat
or so?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah, right. I was a little confused by the naming, but now I see the pattern. Should be consistent now.
lightning/src/ln/functional_tests.rs
Outdated
@@ -25,6 +25,7 @@ use ln::{chan_utils, onion_utils}; | |||
use ln::chan_utils::HTLC_SUCCESS_TX_WEIGHT; | |||
use routing::network_graph::{NetworkUpdate, RoutingFees}; | |||
use routing::router::{Route, RouteHop, RouteHint, RouteHintHop, get_route, get_keysend_route}; | |||
use routing::scorer::DefaultScorer; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we use either a TestScorer
in tests or a DefaultScorer
with a score of 0? I find it a bit...awkward? to change all of our routing parameters in all our tests, even if they still pass it kinda makes me nervous.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sure thing. I removed TestScorer
and renamed DefaultScorer
to Scorer
, using it with 0 in all tests excepted for the newly added one.
lightning/src/routing/scorer.rs
Outdated
impl Default for DefaultScorer { | ||
/// Creates a new scorer using 100 msat as the channel penalty. | ||
fn default() -> Self { | ||
DefaultScorer::new(100) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: I think default should be 500, just kinda gut-feel. Lots of "good" nodes charge 1 sat per payment, and we should probably be willing to prefer that over two-three "free" hops IMO. Maybe even 1k. We can tune this later, but 100 just seems very low.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Changed to 500 msats.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I added a test but was getting a little confused with the fee_msat
assertions. Let me know if it looks sane. I could add more tests if needed.
lightning/src/routing/router.rs
Outdated
@@ -163,12 +164,19 @@ struct RouteGraphNode { | |||
/// The effective htlc_minimum_msat at this hop. If a later hop on the path had a higher HTLC | |||
/// minimum, we use it, plus the fees required at each earlier hop to meet it. | |||
path_htlc_minimum_msat: u64, | |||
/// All penalties incurred *after* this hop on the way to the destination, as calculated using | |||
/// channel scoring. | |||
next_hops_penalty_msat: u64, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah, right. I was a little confused by the naming, but now I see the pattern. Should be consistent now.
lightning/src/ln/functional_tests.rs
Outdated
@@ -25,6 +25,7 @@ use ln::{chan_utils, onion_utils}; | |||
use ln::chan_utils::HTLC_SUCCESS_TX_WEIGHT; | |||
use routing::network_graph::{NetworkUpdate, RoutingFees}; | |||
use routing::router::{Route, RouteHop, RouteHint, RouteHintHop, get_route, get_keysend_route}; | |||
use routing::scorer::DefaultScorer; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sure thing. I removed TestScorer
and renamed DefaultScorer
to Scorer
, using it with 0 in all tests excepted for the newly added one.
lightning/src/routing/scorer.rs
Outdated
impl Default for DefaultScorer { | ||
/// Creates a new scorer using 100 msat as the channel penalty. | ||
fn default() -> Self { | ||
DefaultScorer::new(100) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Changed to 500 msats.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nice to get an initial version of this in!
lightning/src/routing/scorer.rs
Outdated
//! | ||
//! # Example | ||
//! | ||
//! TODO: Fill in example once interface has been finalized. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we're good to fill this in?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done. Not much to it yet, but could expand if we add more configurations. Also, may want to have an example with InvoicePayer
for event handling once that is in. Or at least reference those docs.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM 🚀
Can you squash :). |
Failed payments may be retried, but calling get_route may return a Route with the same failing path. Add a routing::Score trait used to parameterize get_route, which it calls to determine how much a channel should be penalized in terms of msats willing to pay to avoid the channel. Also, add a Scorer struct that implements routing::Score with a constant constant penalty. Subsequent changes will allow for more robust scoring by feeding back payment path success and failure to the scorer via event handling.
84c0a48
to
e15a18a
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Diff since val's ack was just a squash:
$ git diff-tree -U1 84c0a486e e15a18a50
$
Failed payments may be retried, but calling
get_route
may return aRoute
with the same failing path. Add arouting::Score
trait used to parameterizeget_route
, which it calls to determine how much a channel should be penalized in terms of msats willing to pay to avoid the channel.Also, add a
Scorer
struct that implementsrouting::Score
with a constant penalty. Subsequent changes will allow for more robust scoring by feeding back payment path success and failure to the scorer via event handling.