1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
use crate::file_format::OutputFormat;
use crate::{Cosmogony, Zone};
use failure::Error;
use std::path::Path;
fn read_zones(
reader: impl std::io::BufRead,
) -> impl std::iter::Iterator<Item = Result<Zone, Error>> {
reader
.lines()
.map(|l| l.map_err(|e| failure::err_msg(e.to_string())))
.map(|l| {
l.and_then(|l| serde_json::from_str(&l).map_err(|e| failure::err_msg(e.to_string())))
})
}
fn from_json_stream(reader: impl std::io::BufRead) -> Result<Cosmogony, Error> {
let zones = read_zones(reader).collect::<Result<_, _>>()?;
Ok(Cosmogony {
zones,
..Default::default()
})
}
pub fn load_cosmogony_from_file(input: impl AsRef<Path>) -> Result<Cosmogony, Error> {
let format = OutputFormat::from_filename(input.as_ref())?;
let f = std::fs::File::open(&input)?;
let f = std::io::BufReader::new(f);
load_cosmogony(f, format)
}
pub fn read_zones_from_file(
input: impl AsRef<Path>,
) -> Result<Box<dyn std::iter::Iterator<Item = Result<Zone, Error>>>, Error> {
let format = OutputFormat::from_filename(input.as_ref())?;
let f = std::fs::File::open(input.as_ref())?;
let f = std::io::BufReader::new(f);
match format {
OutputFormat::JsonGz | OutputFormat::Json => {
let cosmo = load_cosmogony(f, format)?;
Ok(Box::new(cosmo.zones.into_iter().map(|z| Ok(z))))
}
OutputFormat::JsonStream => Ok(Box::new(read_zones(f))),
OutputFormat::JsonStreamGz => {
let r = flate2::bufread::GzDecoder::new(f);
let r = std::io::BufReader::new(r);
Ok(Box::new(read_zones(r)))
}
}
}
fn load_cosmogony(reader: impl std::io::BufRead, format: OutputFormat) -> Result<Cosmogony, Error> {
match format {
OutputFormat::JsonGz => {
let r = flate2::read::GzDecoder::new(reader);
serde_json::from_reader(r).map_err(|e| failure::err_msg(e.to_string()))
}
OutputFormat::Json => {
serde_json::from_reader(reader).map_err(|e| failure::err_msg(e.to_string()))
}
OutputFormat::JsonStream => from_json_stream(reader),
OutputFormat::JsonStreamGz => {
let r = flate2::bufread::GzDecoder::new(reader);
let r = std::io::BufReader::new(r);
from_json_stream(r)
}
}
}