Page through the received routes, on the status page and in the API
/api/routes/received now returns one page: {routes, next_after,
prev_before}. Pages are in prefix order and begin at a prefix (after= or
before=), not at a count, so a table that changes between two pages does
not make them overlap or leave a gap. A page holds whole prefixes, about
`limit` routes' worth.
The table keeps prefixes in no order, so a page is found by looking at
every prefix once and keeping the nearest few; the routes of the others
are not touched (RibTable::for_each_prefix).
The status page shows about 100 routes with first / previous / next
links; the place is kept in the page's address with the lookup.
The response of /api/routes/received was an array before: this changes
its shape.
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
This commit is contained in:
1 parent
f9ef781d51
commit
1f84235e87
10 files changed
+536
-67
No files matched your search
@@ -185,7 +185,7 @@ async fn test_several_routes_for_a_prefix_from_one_peer() -> Result<()> {
|
||||
.await?
|
||||
.json()
|
||||
.await?;
|
||||
let mut ids: Vec<u64> = routes
|
||||
let mut ids: Vec<u64> = routes["routes"]
|
||||
.as_array()
|
||||
.unwrap()
|
||||
.iter()
|
||||
|
||||
@@ -172,7 +172,7 @@ async fn test_a_leaked_route_is_refused_and_the_rest_are_taken() -> Result<()> {
|
||||
let request = client.get(format!("{base}{path}"));
|
||||
async move { Ok::<Value, eyre::Report>(request.send().await?.error_for_status()?.json().await?) }
|
||||
};
|
||||
let routes = get("/api/routes/received").await?;
|
||||
let routes = get("/api/routes/received").await?["routes"].take();
|
||||
let validity: Vec<(&str, &str)> = routes
|
||||
.as_array()
|
||||
.unwrap()
|
||||
@@ -323,7 +323,7 @@ async fn test_a_peer_can_be_exempt_from_path_verification() -> Result<()> {
|
||||
.await?
|
||||
.json()
|
||||
.await?;
|
||||
assert_eq!(routes[0]["aspa"], "invalid");
|
||||
assert_eq!(routes["routes"][0]["aspa"], "invalid");
|
||||
assert!(server.refusals.peers().is_empty());
|
||||
Ok(())
|
||||
}
|
||||
|
||||
@@ -113,7 +113,7 @@ async fn test_the_best_route_is_chosen_and_replaced_when_it_goes() -> Result<()>
|
||||
let status = get_json(&client, &format!("{base}/api/status")).await?;
|
||||
assert_eq!(status["received_routes"], 2);
|
||||
assert_eq!(status["received_prefixes"], 1);
|
||||
let routes = get_json(&client, &format!("{base}/api/routes/received")).await?;
|
||||
let routes = get_json(&client, &format!("{base}/api/routes/received")).await?["routes"].take();
|
||||
let best: Vec<&Value> = routes
|
||||
.as_array()
|
||||
.unwrap()
|
||||
@@ -226,7 +226,7 @@ async fn test_received_routes_are_returned_up_to_a_limit() -> Result<()> {
|
||||
peer.send(&announcement(&prefixes, &[65001])).await?;
|
||||
wait_for_routes(&server, 40).await?;
|
||||
|
||||
let count = |routes: Value| routes.as_array().unwrap().len();
|
||||
let count = |page: Value| page["routes"].as_array().unwrap().len();
|
||||
let url = format!("{base}/api/routes/received");
|
||||
assert_eq!(count(get_json(&client, &url).await?), 40);
|
||||
assert_eq!(
|
||||
|
||||
@@ -42,8 +42,8 @@ async fn routes(client: &reqwest::Client, base: &str, query: &str) -> Result<Vec
|
||||
.send()
|
||||
.await?
|
||||
.error_for_status()?;
|
||||
let routes: Value = reply.json().await?;
|
||||
Ok(routes
|
||||
let page: Value = reply.json().await?;
|
||||
Ok(page["routes"]
|
||||
.as_array()
|
||||
.unwrap()
|
||||
.iter()
|
||||
@@ -131,7 +131,9 @@ async fn test_routes_can_be_looked_up() -> Result<()> {
|
||||
]
|
||||
);
|
||||
assert_eq!(routes(&client, &base, "").await?.len(), 5);
|
||||
assert_eq!(routes(&client, &base, "limit=2").await?.len(), 2);
|
||||
// A page holds whole prefixes: at most the limit, unless one prefix
|
||||
// alone has more.
|
||||
assert!((1..=2).contains(&routes(&client, &base, "limit=2").await?.len()));
|
||||
|
||||
// One peer's routes, by its address; a peer that is not there has none.
|
||||
assert_eq!(routes(&client, &base, "peer=127.0.0.1").await?.len(), 5);
|
||||
|
||||
@@ -169,7 +169,8 @@ async fn test_received_routes_summary() -> Result<()> {
|
||||
|
||||
let received = tokio::time::timeout(TIMEOUT, async {
|
||||
loop {
|
||||
let v = get_json(&client, &format!("{base}/api/routes/received")).await?;
|
||||
let v =
|
||||
get_json(&client, &format!("{base}/api/routes/received")).await?["routes"].take();
|
||||
if !v.as_array().unwrap().is_empty() {
|
||||
return Ok::<_, eyre::Error>(v);
|
||||
}
|
||||
|
||||
@@ -184,7 +184,7 @@ async fn test_an_invalid_route_is_refused_and_the_rest_are_taken() -> Result<()>
|
||||
async move { Ok::<Value, eyre::Report>(request.send().await?.error_for_status()?.json().await?) }
|
||||
};
|
||||
// Each route says how it stands.
|
||||
let routes = get("/api/routes/received").await?;
|
||||
let routes = get("/api/routes/received").await?["routes"].take();
|
||||
let validity: Vec<(&str, &str)> = routes
|
||||
.as_array()
|
||||
.unwrap()
|
||||
@@ -314,7 +314,7 @@ async fn test_a_peer_can_be_exempt_from_validation() -> Result<()> {
|
||||
.await?
|
||||
.json()
|
||||
.await?;
|
||||
assert_eq!(routes[0]["rpki"], "invalid");
|
||||
assert_eq!(routes["routes"][0]["rpki"], "invalid");
|
||||
assert!(server.refusals.peers().is_empty());
|
||||
Ok(())
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user