bread_cli/
ascii.rs

1use crate::byte_writer::ByteWriter;
2use crate::error::{InError, OutError};
3use crate::util;
4use std::io::{Bytes, Read, Write};
5
6/// An iterator over Result<u8,[InError]>
7///
8/// Reads bytes from the input stream as ASCII characters, so only values in the range (0, 127) are
9/// allowed
10///
11/// [InError]: crate::error::InError
12pub struct Reader<R: Read> {
13    in_bytes: Bytes<R>,
14}
15
16impl<R: Read> Reader<R> {
17    pub fn new(read: R) -> Self {
18        Reader {
19            in_bytes: read.bytes(),
20        }
21    }
22}
23
24impl<R: Read> Iterator for Reader<R> {
25    type Item = Result<u8, InError>;
26    fn next(&mut self) -> Option<Self::Item> {
27        match self.in_bytes.next()? {
28            Ok(c) => {
29                if c.is_ascii() {
30                    Some(Ok(c))
31                } else {
32                    Some(Err(InError::InvalidByte(c as char))) // todo: maybe better as u8?
33                }
34            }
35            Err(e) => Some(Err(InError::StdIO(e))),
36        }
37    }
38}
39
40/// Writes ASCII characters to the output stream
41///
42/// Produced characters are valid ASCII;
43/// byte values provided for writing must be in the range (0,127)
44pub struct Writer<W: Write> {
45    out_bytes: W,
46}
47
48impl<W: Write> Writer<W> {
49    pub fn new(out_bytes: W) -> Self {
50        Writer { out_bytes }
51    }
52}
53
54impl<W: Write> ByteWriter for Writer<W> {
55    fn write(&mut self, byte: u8) -> Result<(), OutError> {
56        if byte.is_ascii() {
57            util::write(&mut self.out_bytes, &[byte], 1)
58        } else {
59            Err(OutError::InvalidByte(byte))
60        }
61    }
62}
63
64#[cfg(test)]
65mod tests {
66    use super::*;
67    use crate::util::literals::*;
68
69    #[test]
70    fn read() {
71        let input = [_B, _A, _EXCL, _STAR];
72        let mut reader = Reader::new(input.as_slice());
73        for b in input {
74            assert_eq!(b, reader.next().unwrap().unwrap());
75        }
76        assert!(reader.next().is_none());
77    }
78
79    #[test]
80    fn write() {
81        let input = _STAR;
82        let mut output = [0u8, 1];
83        let mut writer = Writer::new(output.as_mut_slice());
84        writer.write(input).unwrap();
85        assert_eq!(input, output[0]);
86    }
87}