forked from proxmox-mirrors/proxmox
		
	rrd: try to load database if not already present in cache
Before, a call to `update` was necessary to load an existing database into the cache. If `update` was never called, `extract_cached_data` would simply return no data. Signed-off-by: Lukas Wagner <l.wagner@proxmox.com>
This commit is contained in:
		
							parent
							
								
									f01c1e0ce9
								
							
						
					
					
						commit
						7ea63a6fb9
					
				@ -12,7 +12,7 @@ use crossbeam_channel::{bounded, TryRecvError};
 | 
			
		||||
 | 
			
		||||
use proxmox_sys::fs::{create_path, CreateOptions};
 | 
			
		||||
 | 
			
		||||
use crate::rrd::{AggregationFn, Archive, DataSourceType, Database};
 | 
			
		||||
use crate::rrd::{AggregationFn, DataSourceType, Database};
 | 
			
		||||
use crate::Entry;
 | 
			
		||||
 | 
			
		||||
mod journal;
 | 
			
		||||
@ -58,7 +58,8 @@ impl Cache {
 | 
			
		||||
        file_options: Option<CreateOptions>,
 | 
			
		||||
        dir_options: Option<CreateOptions>,
 | 
			
		||||
        apply_interval: f64,
 | 
			
		||||
        load_rrd_cb: fn(path: &Path, rel_path: &str, dst: DataSourceType) -> Database,
 | 
			
		||||
        load_rrd_cb: fn(path: &Path, rel_path: &str) -> Option<Database>,
 | 
			
		||||
        create_rrd_cb: fn(dst: DataSourceType) -> Database,
 | 
			
		||||
    ) -> Result<Self, Error> {
 | 
			
		||||
        let basedir = basedir.as_ref().to_owned();
 | 
			
		||||
 | 
			
		||||
@ -80,7 +81,7 @@ impl Cache {
 | 
			
		||||
        });
 | 
			
		||||
 | 
			
		||||
        let state = JournalState::new(Arc::clone(&config))?;
 | 
			
		||||
        let rrd_map = RRDMap::new(Arc::clone(&config), load_rrd_cb);
 | 
			
		||||
        let rrd_map = RRDMap::new(Arc::clone(&config), load_rrd_cb, create_rrd_cb);
 | 
			
		||||
 | 
			
		||||
        Ok(Self {
 | 
			
		||||
            config: Arc::clone(&config),
 | 
			
		||||
@ -248,10 +249,24 @@ impl Cache {
 | 
			
		||||
        start: Option<u64>,
 | 
			
		||||
        end: Option<u64>,
 | 
			
		||||
    ) -> Result<Option<Entry>, Error> {
 | 
			
		||||
        self.rrd_map
 | 
			
		||||
            .read()
 | 
			
		||||
            .unwrap()
 | 
			
		||||
            .extract_cached_data(base, name, cf, resolution, start, end)
 | 
			
		||||
        let res = {
 | 
			
		||||
            let map = self.rrd_map.read().unwrap();
 | 
			
		||||
            map.extract_cached_data(base, name, cf, resolution, start, end)?
 | 
			
		||||
        };
 | 
			
		||||
 | 
			
		||||
        match res {
 | 
			
		||||
            Some(entry) => Ok(Some(entry)),
 | 
			
		||||
            None => {
 | 
			
		||||
                let mut map = self.rrd_map.write().unwrap();
 | 
			
		||||
                let loaded = map.load(&format!("{base}/{name}"))?;
 | 
			
		||||
 | 
			
		||||
                if loaded {
 | 
			
		||||
                    map.extract_cached_data(base, name, cf, resolution, start, end)
 | 
			
		||||
                } else {
 | 
			
		||||
                    Ok(None)
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										41
									
								
								proxmox-rrd/src/cache/rrd_map.rs
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										41
									
								
								proxmox-rrd/src/cache/rrd_map.rs
									
									
									
									
										vendored
									
									
								
							@ -14,18 +14,21 @@ use crate::Entry;
 | 
			
		||||
pub struct RRDMap {
 | 
			
		||||
    config: Arc<CacheConfig>,
 | 
			
		||||
    map: HashMap<String, Database>,
 | 
			
		||||
    load_rrd_cb: fn(path: &Path, rel_path: &str, dst: DataSourceType) -> Database,
 | 
			
		||||
    load_rrd_cb: fn(path: &Path, rel_path: &str) -> Option<Database>,
 | 
			
		||||
    create_rrd_cb: fn(dst: DataSourceType) -> Database,
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
impl RRDMap {
 | 
			
		||||
    pub(crate) fn new(
 | 
			
		||||
        config: Arc<CacheConfig>,
 | 
			
		||||
        load_rrd_cb: fn(path: &Path, rel_path: &str, dst: DataSourceType) -> Database,
 | 
			
		||||
        load_rrd_cb: fn(path: &Path, rel_path: &str) -> Option<Database>,
 | 
			
		||||
        create_rrd_cb: fn(dst: DataSourceType) -> Database,
 | 
			
		||||
    ) -> Self {
 | 
			
		||||
        Self {
 | 
			
		||||
            config,
 | 
			
		||||
            map: HashMap::new(),
 | 
			
		||||
            load_rrd_cb,
 | 
			
		||||
            create_rrd_cb,
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -44,13 +47,18 @@ impl RRDMap {
 | 
			
		||||
        } else {
 | 
			
		||||
            let mut path = self.config.basedir.clone();
 | 
			
		||||
            path.push(rel_path);
 | 
			
		||||
            create_path(
 | 
			
		||||
                path.parent().unwrap(),
 | 
			
		||||
                Some(self.config.dir_options.clone()),
 | 
			
		||||
                Some(self.config.dir_options.clone()),
 | 
			
		||||
            )?;
 | 
			
		||||
            let mut rrd = match (self.load_rrd_cb)(&path, rel_path) {
 | 
			
		||||
                None => {
 | 
			
		||||
                    create_path(
 | 
			
		||||
                        path.parent().unwrap(),
 | 
			
		||||
                        Some(self.config.dir_options.clone()),
 | 
			
		||||
                        Some(self.config.dir_options.clone()),
 | 
			
		||||
                    )?;
 | 
			
		||||
 | 
			
		||||
            let mut rrd = (self.load_rrd_cb)(&path, rel_path, dst);
 | 
			
		||||
                    (self.create_rrd_cb)(dst)
 | 
			
		||||
                }
 | 
			
		||||
                Some(rrd) => rrd,
 | 
			
		||||
            };
 | 
			
		||||
 | 
			
		||||
            if !new_only || time > rrd.last_update() {
 | 
			
		||||
                rrd.update(time, value);
 | 
			
		||||
@ -94,4 +102,21 @@ impl RRDMap {
 | 
			
		||||
            None => Ok(None),
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    pub fn load(&mut self, rel_path: &str) -> Result<bool, Error> {
 | 
			
		||||
        if self.map.get(rel_path).is_some() {
 | 
			
		||||
            // Already loaded, do nothing
 | 
			
		||||
            return Ok(true);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        let mut path = self.config.basedir.clone();
 | 
			
		||||
        path.push(rel_path);
 | 
			
		||||
 | 
			
		||||
        if let Some(rrd) = (self.load_rrd_cb)(&path, rel_path) {
 | 
			
		||||
            self.map.insert(rel_path.to_string(), rrd);
 | 
			
		||||
            return Ok(true);
 | 
			
		||||
        } else {
 | 
			
		||||
            return Ok(false);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
		Loading…
	
		Reference in New Issue
	
	Block a user