summaryrefslogtreecommitdiffstats
path: root/src/data.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/data.rs')
-rw-r--r--src/data.rs66
1 files changed, 66 insertions, 0 deletions
diff --git a/src/data.rs b/src/data.rs
new file mode 100644
index 0000000..2734f38
--- /dev/null
+++ b/src/data.rs
@@ -0,0 +1,66 @@
+use crate::schema::{Person, Team};
+use failure::{Error, ResultExt};
+use serde::Deserialize;
+use std::collections::HashMap;
+use std::ffi::OsStr;
+
+#[derive(Debug)]
+pub(crate) struct Data {
+ people: HashMap<String, Person>,
+ teams: HashMap<String, Team>,
+}
+
+impl Data {
+ pub(crate) fn load() -> Result<Self, Error> {
+ let mut data = Data {
+ people: HashMap::new(),
+ teams: HashMap::new(),
+ };
+
+ data.load_dir("people", |this, person: Person| {
+ this.people.insert(person.github().to_string(), person);
+ })?;
+
+ data.load_dir("teams", |this, team: Team| {
+ this.teams.insert(team.name().to_string(), team);
+ })?;
+
+ Ok(data)
+ }
+
+ fn load_dir<T, F>(&mut self, dir: &str, f: F) -> Result<(), Error>
+ where
+ T: for<'de> Deserialize<'de>,
+ F: Fn(&mut Self, T),
+ {
+ for entry in std::fs::read_dir(dir)? {
+ let path = entry?.path();
+
+ if path.is_file() && path.extension() == Some(OsStr::new("toml")) {
+ let content = std::fs::read(&path)
+ .with_context(|_| format!("failed to read {}", path.display()))?;
+ let parsed: T = toml::from_slice(&content)
+ .with_context(|_| format!("failed to parse {}", path.display()))?;
+ f(self, parsed);
+ }
+ }
+
+ Ok(())
+ }
+
+ pub(crate) fn team(&self, name: &str) -> Option<&Team> {
+ self.teams.get(name)
+ }
+
+ pub(crate) fn teams(&self) -> impl Iterator<Item = &Team> {
+ self.teams.values()
+ }
+
+ pub(crate) fn person(&self, name: &str) -> Option<&Person> {
+ self.people.get(name)
+ }
+
+ pub(crate) fn people(&self) -> impl Iterator<Item = &Person> {
+ self.people.values()
+ }
+}