replace raw HashMap with Storages

This commit is contained in:
qwjyh 2024-03-10 13:00:28 +09:00
parent 4283e1e98a
commit 7e026ec229
7 changed files with 224 additions and 124 deletions

View file

@ -2,11 +2,15 @@
use anyhow::{anyhow, Context, Result};
use serde::{Deserialize, Serialize};
use std::{collections::HashMap, fmt, path};
use std::{
collections::HashMap,
fmt::{self, format},
path,
};
use crate::devices;
use super::{local_info::LocalInfo, Storage, StorageExt};
use super::{local_info::LocalInfo, Storage, StorageExt, Storages};
/// Subdirectory of other [Storage]s.
#[derive(Serialize, Deserialize, Debug)]
@ -44,9 +48,10 @@ impl Directory {
path: path::PathBuf,
notes: String,
device: &devices::Device,
storages: &HashMap<String, Storage>,
storages: &Storages,
) -> Result<Directory> {
let (parent_name, diff_path) = storages
.list
.iter()
.filter(|(_k, v)| v.has_alias(&device))
.filter_map(|(k, v)| {
@ -84,24 +89,12 @@ impl Directory {
)
}
/// Get parent `&Storage` of directory.
pub fn parent<'a>(&'a self, storages: &'a HashMap<String, Storage>) -> Result<&Storage> {
let parent = &self.parent;
storages.get(parent).context(format!(
"No parent {} exists for directory {}",
parent,
self.name()
))
}
/// Resolve mount path of directory with current device.
fn mount_path(
&self,
device: &devices::Device,
storages: &HashMap<String, Storage>,
) -> Result<path::PathBuf> {
let parent = self.parent(&storages)?;
let parent_mount_path = parent.mount_path(&device, &storages)?;
fn mount_path(&self, device: &devices::Device, storages: &Storages) -> Result<path::PathBuf> {
let parent_mount_path = self
.parent(&storages)?
.context("Can't find parent storage")?
.mount_path(&device, &storages)?;
Ok(parent_mount_path.join(self.relative_path.clone()))
}
}
@ -122,7 +115,7 @@ impl StorageExt for Directory {
fn mount_path(
&self,
device: &devices::Device,
storages: &HashMap<String, Storage>,
storages: &Storages,
) -> Result<path::PathBuf> {
Ok(self.mount_path(device, storages)?)
}
@ -141,6 +134,17 @@ impl StorageExt for Directory {
};
Ok(())
}
// Get parent `&Storage` of directory.
fn parent<'a>(&'a self, storages: &'a Storages) -> Result<Option<&Storage>> {
match storages.get(&self.parent).context(format!(
"No parent {} exists for directory {}",
&self.parent, &self.name
)) {
Ok(s) => Ok(Some(s)),
Err(e) => Err(anyhow!(e)),
}
}
}
impl fmt::Display for Directory {
@ -164,7 +168,7 @@ mod test {
devices::Device,
storages::{
self, local_info::LocalInfo, physical_drive_partition::PhysicalDrivePartition, Storage,
StorageExt,
StorageExt, Storages,
},
};
@ -195,20 +199,14 @@ mod test {
"some note".to_string(),
local_infos,
);
let mut storages: HashMap<String, Storage> = HashMap::new();
storages.insert(
physical.name().to_string(),
Storage::PhysicalStorage(physical),
);
storages.insert(
directory.name().to_string(),
Storage::SubDirectory(directory),
);
let mut storages = Storages::new();
storages.add(storages::Storage::PhysicalStorage(physical)).unwrap();
storages.add(Storage::SubDirectory(directory)).unwrap();
// assert_eq!(directory.name(), "test_name");
assert_eq!(storages.get("test_name").unwrap().name(), "test_name");
assert_eq!(storages.get(&"test_name".to_string()).unwrap().name(), "test_name");
assert_eq!(
storages
.get("test_name")
.get(&"test_name".to_string())
.unwrap()
.mount_path(&device, &storages)
.unwrap(),

View file

@ -11,7 +11,7 @@ use crate::devices;
use super::{
local_info::{self, LocalInfo},
StorageExt,
StorageExt, Storages,
};
#[derive(Serialize, Deserialize, Debug)]
@ -57,7 +57,7 @@ impl StorageExt for OnlineStorage {
fn mount_path(
&self,
device: &devices::Device,
_storages: &HashMap<String, super::Storage>,
_storages: &Storages,
) -> Result<std::path::PathBuf> {
Ok(self
.local_infos
@ -81,6 +81,13 @@ impl StorageExt for OnlineStorage {
};
Ok(())
}
fn parent(
&self,
storages: &Storages,
) -> Result<Option<&super::Storage>> {
Ok(None)
}
}
impl fmt::Display for OnlineStorage {

View file

@ -2,7 +2,7 @@
use crate::devices;
use crate::devices::Device;
use crate::storages::{Storage, StorageExt};
use crate::storages::{Storage, StorageExt, Storages};
use anyhow::{anyhow, Context, Result};
use byte_unit::Byte;
use inquire::Text;
@ -106,7 +106,10 @@ impl PhysicalDrivePartition {
#[cfg(test)]
mod test {
use crate::{devices::Device, storages::{local_info::LocalInfo, StorageExt}};
use crate::{
devices::Device,
storages::{local_info::LocalInfo, StorageExt},
};
use std::path::PathBuf;
use super::PhysicalDrivePartition;
@ -141,11 +144,7 @@ impl StorageExt for PhysicalDrivePartition {
self.local_infos.get(&device.name())
}
fn mount_path(
&self,
device: &devices::Device,
_: &HashMap<String, Storage>,
) -> Result<path::PathBuf> {
fn mount_path(&self, device: &devices::Device, _: &Storages) -> Result<path::PathBuf> {
Ok(self
.local_infos
.get(&device.name())
@ -168,6 +167,10 @@ impl StorageExt for PhysicalDrivePartition {
};
Ok(())
}
fn parent(&self, storages: &Storages) -> Result<Option<&Storage>> {
Ok(None)
}
}
impl fmt::Display for PhysicalDrivePartition {
@ -189,7 +192,7 @@ impl fmt::Display for PhysicalDrivePartition {
/// Interactively select physical storage from available disks in sysinfo.
pub fn select_physical_storage(
device: Device,
storages: &HashMap<String, Storage>,
storages: &Storages,
) -> Result<(String, PhysicalDrivePartition)> {
trace!("select_physical_storage");
// get disk info fron sysinfo
@ -208,7 +211,7 @@ pub fn select_physical_storage(
trace!("{}", disk_name);
loop {
disk_name = Text::new("Name for the disk:").prompt()?;
if storages.iter().all(|(k, v)| k != &disk_name) {
if storages.list.iter().all(|(k, v)| k != &disk_name) {
break;
}
println!("The name {} is already used.", disk_name);