use log::debug;
use smartcore::linalg::basic::matrix::DenseMatrix;
use sprs::CsMat;
use std::path::{Path, PathBuf};
use crate::StorageResult;
use crate::metadata::GeneMetadata;
pub trait StorageBackend: Send + Sync {
fn get_base(&self) -> String;
fn get_name(&self) -> String;
fn path_to_uri(path: &Path) -> String;
fn exists(path: &str) -> (bool, Option<PathBuf>) {
let base_path = std::path::PathBuf::from(path);
if !base_path.exists() {
debug!("StorageBackend: path {:?} does not exist", base_path);
return (false, None);
}
if let Ok(entries) = std::fs::read_dir(&base_path) {
for entry in entries.flatten() {
let path = entry.path();
if let Some(name) = path.file_name().and_then(|n| n.to_str())
&& name.ends_with("_metadata.json")
{
debug!("StorageBackend::exists: found metadata file at {:?}", path);
return (true, Some(path));
}
}
}
(false, None)
}
fn base_path(&self) -> PathBuf;
fn metadata_path(&self) -> PathBuf;
fn basepath_to_uri(&self) -> String;
async fn load_dense_from_file(&self, path: &Path) -> StorageResult<DenseMatrix<f64>>;
fn file_path(&self, key: &str) -> PathBuf;
async fn save_dense(
&self,
key: &str,
matrix: &DenseMatrix<f64>,
md_path: &Path,
) -> StorageResult<()>;
async fn load_dense(&self, key: &str) -> StorageResult<DenseMatrix<f64>>;
async fn save_sparse(
&self,
key: &str,
matrix: &CsMat<f64>,
md_path: &Path,
) -> StorageResult<()>;
async fn load_sparse(&self, key: &str) -> StorageResult<CsMat<f64>>;
async fn save_lambdas(&self, lambdas: &[f64], md_path: &Path) -> StorageResult<()>;
async fn load_lambdas(&self) -> StorageResult<Vec<f64>>;
async fn save_metadata(&self, metadata: &GeneMetadata) -> StorageResult<PathBuf>;
async fn load_metadata(&self) -> StorageResult<GeneMetadata>;
#[allow(dead_code)]
async fn save_index(&self, key: &str, vector: &[usize], md_path: &Path) -> StorageResult<()>;
async fn save_vector(&self, key: &str, vector: &[f64], md_path: &Path) -> StorageResult<()>;
async fn save_centroid_map(&self, map: &[usize], md_path: &Path) -> StorageResult<()>;
async fn load_centroid_map(&self) -> StorageResult<Vec<usize>>;
async fn save_subcentroid_lambdas(&self, lambdas: &[f64], md_path: &Path) -> StorageResult<()>;
async fn load_subcentroid_lambdas(&self) -> StorageResult<Vec<f64>>;
async fn save_subcentroids(
&self,
subcentroids: &DenseMatrix<f64>,
md_path: &Path,
) -> StorageResult<()>;
async fn load_subcentroids(&self) -> StorageResult<Vec<Vec<f64>>>;
async fn save_item_norms(&self, item_norms: &[f64], md_path: &Path) -> StorageResult<()>;
async fn load_item_norms(&self) -> StorageResult<Vec<f64>>;
async fn save_cluster_assignments(
&self,
assignments: &[Option<usize>],
md_path: &Path,
) -> StorageResult<()>;
async fn load_cluster_assignments(&self) -> StorageResult<Vec<Option<usize>>>;
#[allow(dead_code)]
async fn load_index(&self, key: &str) -> StorageResult<Vec<usize>>;
async fn load_vector(&self, key: &str) -> StorageResult<Vec<f64>>;
async fn save_dense_to_file(data: &DenseMatrix<f64>, path: &PathBuf) -> StorageResult<()>;
}