about summary refs log tree commit diff
path: root/src/fs.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/fs.rs')
-rw-r--r--src/fs.rs52
1 files changed, 28 insertions, 24 deletions
diff --git a/src/fs.rs b/src/fs.rs
index e13f405..d9b8810 100644
--- a/src/fs.rs
+++ b/src/fs.rs
@@ -1,6 +1,9 @@
 use camino::{Utf8Path, Utf8PathBuf};
+use core::fmt;
 use std::{io, ops::Deref, str::FromStr};
 
+use crate::RuntimeError;
+
 /// Webpath is the path we get from HTTP requests. It's garunteed to not fall
 /// below the webroot and will never start or end with a slash.
 #[derive(Clone, Debug, PartialEq)]
@@ -60,9 +63,16 @@ impl PartialEq<str> for Webpath {
 	}
 }
 
+impl fmt::Display for Webpath {
+	fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+		write!(f, "/{}", self.webcanon)
+	}
+}
+
 const ROOT_INDEX: &str = "home.html";
 const DIRFILE_EXT: &str = "html";
 
+#[derive(Clone, Debug)]
 pub struct Filesystem {
 	webroot: Utf8PathBuf,
 }
@@ -74,7 +84,8 @@ impl Filesystem {
 		}
 	}
 
-	fn resolve(&self, webpath: &Webpath) -> Result<Utf8PathBuf, RuntimeError> {
+	pub fn resolve(&self, webpath: &Webpath) -> Result<Utf8PathBuf, RuntimeError> {
+		println!("resolve = {webpath}");
 		if webpath.is_index() || webpath == ROOT_INDEX {
 			return Ok(self.webroot.join(ROOT_INDEX));
 		}
@@ -102,35 +113,28 @@ impl Filesystem {
 		}
 	}
 
-	fn metadata<P: AsRef<Utf8Path>>(path: P) -> Result<std::fs::Metadata, RuntimeError> {
+	pub fn metadata<P: AsRef<Utf8Path>>(path: P) -> Result<std::fs::Metadata, RuntimeError> {
 		path.as_ref()
 			.metadata()
 			.map_err(|ioe| RuntimeError::from_io(ioe, path.as_ref().to_owned()))
 	}
-}
 
-#[derive(Debug, snafu::Snafu)]
-pub enum RuntimeError {
-	#[snafu(display("the path was not found: {path}"))]
-	NotFound {
-		source: io::Error,
-		path: Utf8PathBuf,
-	},
-	#[snafu(display("io error: {path}: {source}"))]
-	UnknownIo {
-		source: io::Error,
-		path: Utf8PathBuf,
-	},
-	#[snafu(display("path tried to go below webroot: {path}"))]
-	PathTooLow { path: String },
-}
+	pub async fn open<P: AsRef<Utf8Path>>(path: P) -> Result<tokio::fs::File, RuntimeError> {
+		tokio::fs::File::open(path.as_ref())
+			.await
+			.map_err(|ioe| RuntimeError::from_io(ioe, path.as_ref().to_owned()))
+	}
 
-impl RuntimeError {
-	pub fn from_io(source: io::Error, path: Utf8PathBuf) -> Self {
-		match source.kind() {
-			io::ErrorKind::NotFound => RuntimeError::NotFound { source, path },
-			_ => RuntimeError::UnknownIo { source, path },
-		}
+	pub async fn read<P: AsRef<Utf8Path>>(path: P) -> Result<Vec<u8>, RuntimeError> {
+		tokio::fs::read(path.as_ref())
+			.await
+			.map_err(|ioe| RuntimeError::from_io(ioe, path.as_ref().to_owned()))
+	}
+
+	pub async fn read_to_string<P: AsRef<Utf8Path>>(path: P) -> Result<String, RuntimeError> {
+		tokio::fs::read_to_string(path.as_ref())
+			.await
+			.map_err(|ioe| RuntimeError::from_io(ioe, path.as_ref().to_owned()))
 	}
 }