dotenv/
iter.rs

1use std::collections::HashMap;
2use std::env;
3use std::io::{BufReader, Lines};
4use std::io::prelude::*;
5
6use crate::errors::*;
7use crate::parse;
8
9pub struct Iter<R> {
10    lines: Lines<BufReader<R>>,
11    substitution_data: HashMap<String, Option<String>>,
12}
13
14impl<R: Read> Iter<R> {
15    pub fn new(reader: R) -> Iter<R> {
16        Iter {
17            lines: BufReader::new(reader).lines(),
18            substitution_data: HashMap::new(),
19        }
20    }
21
22    pub fn load(self) -> Result<()> {
23        for item in self {
24            let (key, value) = item?;
25            if env::var(&key).is_err() {
26                env::set_var(&key, value);
27            }
28        }
29
30        Ok(())
31    }
32}
33
34impl<R: Read> Iterator for Iter<R> {
35    type Item = Result<(String, String)>;
36
37    fn next(&mut self) -> Option<Self::Item> {
38        loop {
39            let line = match self.lines.next() {
40                Some(Ok(line)) => line,
41                Some(Err(err)) => return Some(Err(Error::Io(err))),
42                None => return None,
43            };
44
45            match parse::parse_line(&line, &mut self.substitution_data) {
46                Ok(Some(result)) => return Some(Ok(result)),
47                Ok(None) => {}
48                Err(err) => return Some(Err(err)),
49            }
50        }
51    }
52}