20260421 优化内存布局,降低内存峰值需求压低到4.5GB左右,在4c8g 机器上,稳定跑snapshot + delta

This commit is contained in:
2026-04-21 15:21:25 +08:00
parent 542bd7be80
commit 944ea6ca00
7 changed files with 373 additions and 60 deletions

View File

@@ -23,7 +23,6 @@ pub struct CurrentRepoObject {
#[derive(Default, Debug)]
pub struct CurrentRepoIndex {
by_uri: HashMap<String, CurrentRepoEntry>,
by_scope: HashMap<String, HashSet<String>>,
}
pub type CurrentRepoIndexHandle = Arc<Mutex<CurrentRepoIndex>>;
@@ -43,10 +42,12 @@ impl CurrentRepoIndex {
pub fn list_scope_uris(&self, repository_source: &str) -> Vec<String> {
let mut out = self
.by_scope
.get(repository_source)
.map(|set| set.iter().cloned().collect::<Vec<_>>())
.unwrap_or_default();
.by_uri
.iter()
.filter_map(|(rsync_uri, entry)| {
(entry.repository_source == repository_source).then(|| rsync_uri.clone())
})
.collect::<Vec<_>>();
out.sort();
out
}
@@ -56,7 +57,11 @@ impl CurrentRepoIndex {
}
pub fn scope_count(&self) -> usize {
self.by_scope.len()
self.by_uri
.values()
.map(|entry| entry.repository_source.as_str())
.collect::<HashSet<_>>()
.len()
}
pub fn snapshot_objects(&self) -> Vec<CurrentRepoObject> {
@@ -76,7 +81,6 @@ impl CurrentRepoIndex {
pub fn clear(&mut self) {
self.by_uri.clear();
self.by_scope.clear();
}
pub fn apply_repository_view_entries(
@@ -92,11 +96,6 @@ impl CurrentRepoIndex {
fn apply_repository_view_entry(&mut self, entry: &RepositoryViewEntry) -> Result<(), String> {
entry.validate_internal().map_err(|e| e.to_string())?;
let old_scope = self
.by_uri
.get(&entry.rsync_uri)
.map(|existing| existing.repository_source.clone());
match entry.state {
RepositoryViewState::Present | RepositoryViewState::Replaced => {
let repository_source = entry.repository_source.clone().ok_or_else(|| {
@@ -112,17 +111,6 @@ impl CurrentRepoIndex {
)
})?;
let current_hash = decode_sha256_hex_32(&current_hash_hex)?;
if let Some(old_scope) = old_scope.as_ref() {
if old_scope != &repository_source {
self.remove_uri_from_scope(old_scope, &entry.rsync_uri);
}
}
self.by_scope
.entry(repository_source.clone())
.or_default()
.insert(entry.rsync_uri.clone());
self.by_uri.insert(
entry.rsync_uri.clone(),
CurrentRepoEntry {
@@ -135,27 +123,12 @@ impl CurrentRepoIndex {
);
}
RepositoryViewState::Withdrawn => {
if let Some(scope) = entry.repository_source.as_ref().or(old_scope.as_ref()) {
self.remove_uri_from_scope(scope, &entry.rsync_uri);
}
self.by_uri.remove(&entry.rsync_uri);
}
}
Ok(())
}
fn remove_uri_from_scope(&mut self, scope: &str, rsync_uri: &str) {
let empty = if let Some(entries) = self.by_scope.get_mut(scope) {
entries.remove(rsync_uri);
entries.is_empty()
} else {
false
};
if empty {
self.by_scope.remove(scope);
}
}
}
fn decode_sha256_hex_32(value: &str) -> Result<[u8; 32], String> {
@@ -281,7 +254,7 @@ mod tests {
.expect_err("invalid hash should fail");
assert!(err.contains("invalid"), "{err}");
let err = index
index
.apply_repository_view_entries(&[RepositoryViewEntry {
rsync_uri: "rsync://example.test/repo/b.roa".to_string(),
current_hash: Some("22".repeat(32)),