Finished out Entry's new and get functions.
This commit is contained in:
		@@ -1,5 +1,5 @@
 | 
				
			|||||||
use super::{DBError, FileData, SessionData, Store};
 | 
					use super::{DBError, FileData, SessionData, Store};
 | 
				
			||||||
use async_std::{fs::write, path::Path};
 | 
					use async_std::{fs::{read, write}, path::Path};
 | 
				
			||||||
use rand::{distributions::Alphanumeric, thread_rng, Rng};
 | 
					use rand::{distributions::Alphanumeric, thread_rng, Rng};
 | 
				
			||||||
use std::{
 | 
					use std::{
 | 
				
			||||||
    cell::Cell,
 | 
					    cell::Cell,
 | 
				
			||||||
@@ -94,6 +94,16 @@ impl Entry {
 | 
				
			|||||||
    async fn new(filename: String, data: DataType) -> Result<Self, DBError> {
 | 
					    async fn new(filename: String, data: DataType) -> Result<Self, DBError> {
 | 
				
			||||||
        if Path::new(&filename).exists().await {
 | 
					        if Path::new(&filename).exists().await {
 | 
				
			||||||
            return Err(DBError::new("entry already exists"));
 | 
					            return Err(DBError::new("entry already exists"));
 | 
				
			||||||
 | 
					        } else {
 | 
				
			||||||
 | 
					            let filepath = Path::new(&filename);
 | 
				
			||||||
 | 
					            match write(filepath, data.to_bytes()).await {
 | 
				
			||||||
 | 
					                Ok(_) => (),
 | 
				
			||||||
 | 
					                Err(err) => {
 | 
				
			||||||
 | 
					                    let mut error = DBError::new("failed to write");
 | 
				
			||||||
 | 
					                    error.add_source(err);
 | 
				
			||||||
 | 
					                    return Err(error);
 | 
				
			||||||
 | 
					                }
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
        Ok(Self {
 | 
					        Ok(Self {
 | 
				
			||||||
            data: data,
 | 
					            data: data,
 | 
				
			||||||
@@ -102,7 +112,12 @@ impl Entry {
 | 
				
			|||||||
        })
 | 
					        })
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    fn elapsed(&self) -> Duration {
 | 
				
			||||||
 | 
					        self.last_used.get().elapsed()
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    async fn get(&self) -> Result<DataType, DBError> {
 | 
					    async fn get(&self) -> Result<DataType, DBError> {
 | 
				
			||||||
 | 
					        self.last_used.set(Instant::now());
 | 
				
			||||||
        Ok(self.data.clone())
 | 
					        Ok(self.data.clone())
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
@@ -167,9 +182,9 @@ mod datatype_file {
 | 
				
			|||||||
        let mut store = Store::new();
 | 
					        let mut store = Store::new();
 | 
				
			||||||
        let mut dt_store = DataType::new("store").unwrap();
 | 
					        let mut dt_store = DataType::new("store").unwrap();
 | 
				
			||||||
        let mut expected = dt_store.to_bytes();
 | 
					        let mut expected = dt_store.to_bytes();
 | 
				
			||||||
        store.add("database", name, id);
 | 
					        store.add("database", name, id).unwrap();
 | 
				
			||||||
        expected.append(&mut store.to_bytes());
 | 
					        expected.append(&mut store.to_bytes());
 | 
				
			||||||
        dt_store.add("database", name, id);
 | 
					        dt_store.add("database", name, id).unwrap();
 | 
				
			||||||
        assert_eq!(dt_store.to_bytes(), expected);
 | 
					        assert_eq!(dt_store.to_bytes(), expected);
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -224,8 +239,21 @@ mod datatype_file {
 | 
				
			|||||||
#[cfg(test)]
 | 
					#[cfg(test)]
 | 
				
			||||||
mod entry {
 | 
					mod entry {
 | 
				
			||||||
    use super::*;
 | 
					    use super::*;
 | 
				
			||||||
 | 
					    use std::error::Error;
 | 
				
			||||||
    use tempfile::tempdir;
 | 
					    use tempfile::tempdir;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    #[async_std::test]
 | 
				
			||||||
 | 
					    async fn get_elapsed_time() {
 | 
				
			||||||
 | 
					        let dir = tempdir().unwrap();
 | 
				
			||||||
 | 
					        let data = DataType::new("store").unwrap();
 | 
				
			||||||
 | 
					        let filepath = dir.path().join("count");
 | 
				
			||||||
 | 
					        let filename = filepath.to_str().unwrap();
 | 
				
			||||||
 | 
					        let item = Entry::new(filename.to_string(), data).await.unwrap();
 | 
				
			||||||
 | 
					        assert!(Duration::from_secs(1) > item.elapsed(), "last_used should have been now.");
 | 
				
			||||||
 | 
					        item.last_used.set(Instant::now() - Duration::from_secs(500));
 | 
				
			||||||
 | 
					        assert!(Duration::from_secs(499) < item.elapsed(), "The duration should have increased.");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    #[async_std::test]
 | 
					    #[async_std::test]
 | 
				
			||||||
    async fn create() {
 | 
					    async fn create() {
 | 
				
			||||||
        let dir = tempdir().unwrap();
 | 
					        let dir = tempdir().unwrap();
 | 
				
			||||||
@@ -236,15 +264,36 @@ mod entry {
 | 
				
			|||||||
        let item = Entry::new(filename.to_string(), data.clone())
 | 
					        let item = Entry::new(filename.to_string(), data.clone())
 | 
				
			||||||
            .await
 | 
					            .await
 | 
				
			||||||
            .unwrap();
 | 
					            .unwrap();
 | 
				
			||||||
 | 
					        assert!(Duration::from_secs(1) > item.elapsed(), "last_used should have been now.");
 | 
				
			||||||
        let output = item.get().await.unwrap();
 | 
					        let output = item.get().await.unwrap();
 | 
				
			||||||
        assert_eq!(
 | 
					        assert_eq!(
 | 
				
			||||||
            data.list(["database"].to_vec()).unwrap(),
 | 
					            data.list(["database"].to_vec()).unwrap(),
 | 
				
			||||||
            output.list(["database"].to_vec()).unwrap()
 | 
					            output.list(["database"].to_vec()).unwrap()
 | 
				
			||||||
        );
 | 
					        );
 | 
				
			||||||
 | 
					        assert!(filepath.is_file(), "Should have created the entry file.");
 | 
				
			||||||
 | 
					        let content = read(&filepath).await.unwrap();
 | 
				
			||||||
 | 
					        assert_eq!(content, data.to_bytes());
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    #[async_std::test]
 | 
					    #[async_std::test]
 | 
				
			||||||
    async fn no_over_writes() -> Result<(), DBError> {
 | 
					    async fn create_errors_on_bad_files() -> Result<(), DBError> {
 | 
				
			||||||
 | 
					        let dir = tempdir().unwrap();
 | 
				
			||||||
 | 
					        let data = DataType::new("store").unwrap();
 | 
				
			||||||
 | 
					        let filepath = dir.path().join("bad").join("path");
 | 
				
			||||||
 | 
					        let filename = filepath.to_str().unwrap();
 | 
				
			||||||
 | 
					        match Entry::new(filename.to_string(), data).await {
 | 
				
			||||||
 | 
					            Ok(_) => Err(DBError::new("bad file names should raise an error")),
 | 
				
			||||||
 | 
					            Err(err) => {
 | 
				
			||||||
 | 
					                assert_eq!(err.to_string(), "failed to write");
 | 
				
			||||||
 | 
					                assert!(err.source().is_some(), "Must include the source error.");
 | 
				
			||||||
 | 
					                assert!(err.source().unwrap().to_string().contains("could not write to file"));
 | 
				
			||||||
 | 
					                Ok(())
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    #[async_std::test]
 | 
				
			||||||
 | 
					    async fn create_does_not_over_writes() -> Result<(), DBError> {
 | 
				
			||||||
        let dir = tempdir().unwrap();
 | 
					        let dir = tempdir().unwrap();
 | 
				
			||||||
        let id = "wicked";
 | 
					        let id = "wicked";
 | 
				
			||||||
        let file = dir.path().join(id);
 | 
					        let file = dir.path().join(id);
 | 
				
			||||||
@@ -263,6 +312,18 @@ mod entry {
 | 
				
			|||||||
            }
 | 
					            }
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    #[async_std::test]
 | 
				
			||||||
 | 
					    async fn get_updates_last_used() {
 | 
				
			||||||
 | 
					        let dir = tempdir().unwrap();
 | 
				
			||||||
 | 
					        let data = DataType::new("store").unwrap();
 | 
				
			||||||
 | 
					        let filepath = dir.path().join("holder");
 | 
				
			||||||
 | 
					        let filename = filepath.to_str().unwrap();
 | 
				
			||||||
 | 
					        let item = Entry::new(filename.to_string(), data).await.unwrap();
 | 
				
			||||||
 | 
					        item.last_used.set(Instant::now() - Duration::from_secs(300));
 | 
				
			||||||
 | 
					        item.get().await.unwrap();
 | 
				
			||||||
 | 
					        assert!(Duration::from_secs(1) > item.elapsed(), "last_used should have been reset.");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#[cfg(test)]
 | 
					#[cfg(test)]
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user