sp_wasm_memfs/
file.rs

1use super::node::*;
2use std::io::{self, Read, Write};
3use std::sync::{Arc, Mutex};
4
5#[derive(Debug)]
6pub struct File {
7    node: Arc<Mutex<Node>>,
8    rdr_pos: usize,
9}
10
11impl File {
12    pub(crate) fn new(node: Arc<Mutex<Node>>) -> Self {
13        Self { node, rdr_pos: 0 }
14    }
15
16    pub fn reset(&mut self) {
17        self.rdr_pos = 0;
18    }
19}
20
21impl Read for File {
22    fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
23        if self.rdr_pos == self.node.lock().unwrap().contents.len() {
24            return Ok(0);
25        }
26
27        let result = (&self.node.lock().unwrap().contents[self.rdr_pos..]).read(buf);
28        result.map(|count| {
29            self.rdr_pos += count;
30            count
31        })
32    }
33}
34
35impl Write for File {
36    fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
37        self.node.lock().unwrap().contents.write(buf)
38    }
39
40    fn flush(&mut self) -> io::Result<()> {
41        self.node.lock().unwrap().contents.flush()
42    }
43}
44
45#[cfg(test)]
46mod test {
47    use super::*;
48
49    #[test]
50    fn read() {
51        let mut file = File::new(new_file_node("test.txt"));
52        file.node
53            .lock()
54            .unwrap()
55            .contents
56            .write_all(b"Hello world!")
57            .unwrap();
58
59        let mut contents = Vec::new();
60        file.read_to_end(&mut contents).unwrap();
61        assert_eq!(file.node.lock().unwrap().contents, contents);
62
63        // once read, need to reset to read again
64        let mut contents = Vec::new();
65        file.read_to_end(&mut contents).unwrap();
66        assert!(contents.is_empty());
67
68        file.reset();
69        let mut contents = Vec::new();
70        file.read_to_end(&mut contents).unwrap();
71        assert_eq!(file.node.lock().unwrap().contents, contents);
72    }
73
74    #[test]
75    fn write() {
76        let mut file = File::new(new_file_node("test.txt"));
77
78        let contents = b"Hello world!";
79        file.write_all(contents).unwrap();
80        assert_eq!(file.node.lock().unwrap().contents, b"Hello world!");
81
82        let contents = b" This is a test...";
83        file.write_all(contents).unwrap();
84        assert_eq!(
85            file.node.lock().unwrap().contents,
86            b"Hello world! This is a test..."
87        );
88
89        assert!(file.flush().is_ok());
90    }
91}