Move locations to their own cache

This commit is contained in:
Mark Sinclair
2021-10-06 20:44:15 +01:00
parent f1a628dee4
commit e0e1ca992f
3 changed files with 38 additions and 52 deletions
+1 -21
View File
@@ -34,27 +34,7 @@ pub(crate) struct PrettyMixNodeBondWithLocation {
pub(crate) async fn list(
state: &State<ExplorerApiStateContext>,
) -> Json<Vec<PrettyMixNodeBondWithLocation>> {
Json(
state
.inner
.mix_nodes
.get()
.await
.value
.values()
.map(|i| {
let mix_node = i.bond.clone();
PrettyMixNodeBondWithLocation {
location: i.location.clone(),
bond_amount: mix_node.bond_amount,
total_delegation: mix_node.total_delegation,
owner: mix_node.owner,
layer: mix_node.layer,
mix_node: mix_node.mix_node,
}
})
.collect::<Vec<PrettyMixNodeBondWithLocation>>(),
)
Json(state.inner.mix_nodes.get_mixnodes_with_location().await)
}
#[openapi(tag = "mix_node")]
+36 -25
View File
@@ -7,6 +7,7 @@ use std::time::{Duration, SystemTime};
use rocket::tokio::sync::RwLock;
use serde::{Deserialize, Serialize};
use crate::mix_node::http::PrettyMixNodeBondWithLocation;
use crate::mix_nodes::utils::map_2_letter_to_3_letter_country_code;
use mixnet_contract::{Delegation, MixNodeBond, RawDelegationData, UnpackedDelegation};
use network_defaults::{
@@ -53,10 +54,6 @@ impl Location {
}
}
#[derive(Clone, Debug)]
pub(crate) struct MixNodeBondWithLocation {
pub(crate) location: Option<Location>,
pub(crate) bond: MixNodeBond,
}
#[derive(Clone, Debug)]
@@ -92,23 +89,28 @@ impl ThreadsafeMixNodesResult {
}
}
pub(crate) async fn is_location_valid(&self, identity_key: &str) -> bool {
self.inner
.read()
.await
.location_cache
.get(identity_key)
.map(|cache_item| cache_item.valid_until > SystemTime::now())
.unwrap_or(false)
}
pub(crate) async fn get_location_cache(&self) -> LocationCache {
self.inner.read().await.location_cache.clone()
}
pub(crate) async fn set_location(&self, identity_key: &str, location: Location) {
pub(crate) async fn set_location(&self, identity_key: &str, location: Option<Location>) {
let mut guard = self.inner.write().await;
// cache the location for this mix node so that it can be used when the mix node list is refreshed
guard
.location_cache
.insert(identity_key.to_string(), location.clone());
// add the location to the mix node
guard
.value
.entry(identity_key.to_string())
.and_modify(|item| item.location = Some(location));
guard.location_cache.insert(
identity_key.to_string(),
LocationCacheItem::new_from_location(location),
);
}
pub(crate) async fn get(&self) -> MixNodesResult {
@@ -124,25 +126,34 @@ impl ThreadsafeMixNodesResult {
self.inner.read().await.clone()
}
pub(crate) async fn refresh_and_get(&self) -> MixNodesResult {
self.refresh().await;
self.inner.read().await.clone()
pub(crate) async fn get_mixnodes_with_location(&self) -> Vec<PrettyMixNodeBondWithLocation> {
let guard = self.inner.read().await;
guard
.value
.values()
.map(|bond| {
let location = guard.location_cache.get(&bond.mix_node.identity_key);
let copy = bond.clone();
PrettyMixNodeBondWithLocation {
location: location.and_then(|l| l.location.clone()),
bond_amount: copy.bond_amount,
total_delegation: copy.total_delegation,
owner: copy.owner,
layer: copy.layer,
mix_node: copy.mix_node,
}
})
.collect()
}
async fn refresh(&self) {
pub(crate) async fn refresh(&self) {
// get mixnodes and cache the new value
let value = retrieve_mixnodes().await;
let location_cache = self.inner.read().await.location_cache.clone();
*self.inner.write().await = MixNodesResult {
value: value
.into_iter()
.map(|bond| {
let location = location_cache.get(&bond.mix_node.identity_key).cloned(); // add the location, if we've located this mix node before
(
bond.mix_node.identity_key.to_string(),
MixNodeBondWithLocation { location, bond },
)
})
.map(|bond| (bond.mix_node.identity_key.to_string(), bond))
.collect(),
valid_until: SystemTime::now() + Duration::from_secs(60 * 10), // valid for 10 minutes
location_cache,
+1 -6
View File
@@ -27,12 +27,7 @@ pub struct ExplorerApiState {
impl ExplorerApiState {
pub(crate) async fn get_mix_node(&self, pubkey: &str) -> Option<MixNodeBond> {
self.mix_nodes
.get()
.await
.value
.get(pubkey)
.map(|cache_item| cache_item.bond.clone())
self.mix_nodes.get().await.value.get(pubkey).cloned()
}
}