Search code examples
linuxunit-testingtestingrustdirectory

How can I induce failure from std::env::current_dir()?


I am creating a function that will check the current directory at some point. From the signature, current_dir() can return an error and I want to test the case it does. However I couldn't figure out how to do it.

Here's my code (playground):

use std::env;
 
#[allow(unused)]
fn check_current_dir() -> Result<(), &'static str> {
    if let Ok(current_dir) = env::current_dir() {
        println!("Current dir is ok: {:?}", current_dir);
        return Ok(());
    } else {
        return Err("Currentdir failed");
    }
}

#[cfg(test)]
mod check_current_dir {
    use super::*;

    #[test]
    fn current_dir_fail() {
        assert!(check_current_dir().is_ok()) // want to make it fail
    }
}

I tried creating a directory, moving the current directory to it, and removing that directory, but that failed. I tried using a symlink directory, but current_dir() still returned Ok(_). This is designed to run on Linux if that matters.

Does any one have an idea?


Solution

  • From the manpage of getcwd which current_dir uses on Unix these are the possible failures:

    ERRORS
           EACCES Permission to read or search a component of the filename was denied.
    
           ENAMETOOLONG
                  getwd(): The size of the null-terminated absolute pathname string exceeds PATH_MAX bytes.
    
           ENOENT The current working directory has been unlinked.
    
           ENOMEM Out of memory.
    

    From wich I excluded EFAULT, EINVAL and ERANGE since Rusts std is handling buf and size for you. So for example this test which removes the current directory will fail:

    use std::fs;
    
    use super::*;
    
    #[test]
    fn current_dir_fail() {
        fs::create_dir("bogus").unwrap();
        std::env::set_current_dir("bogus").unwrap();
        fs::remove_dir("../bogus").unwrap();
        assert!(check_current_dir().is_ok()) //want to make it fail
    }
    

    But with your current implementation of check_current_dir, that's essentially testing std which is well tested and you shouldn't need to do it.