Skip to content

Commit

Permalink
Merge pull request #146 from DuskSystems/145-ensure-we-use-terms-path…
Browse files Browse the repository at this point in the history
…-and-route-correctly

Ensure 'path' and 'route' terms are used consistently
  • Loading branch information
CathalMullan authored Sep 7, 2024
2 parents 77ad7a1 + 5f5d037 commit 0a3ceb0
Show file tree
Hide file tree
Showing 21 changed files with 690 additions and 644 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,10 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- Router display now uses different characters to represent root and matchable nodes.
- Successful matches now return a flattened representation of node data.

### Fixed

- Be consistent with the use of terms "path" and "route".

## [0.2.1] - 2024-09-04

### Changed
Expand Down
6 changes: 3 additions & 3 deletions src/decode.rs
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
use crate::errors::PathError;
use crate::errors::EncodingError;
use std::borrow::Cow;

/// Try and percent-decode input bytes.
/// Does not do any sort of normalization, simply decodes hex characters.
pub fn percent_decode(input: &[u8]) -> Result<Cow<'_, [u8]>, PathError> {
pub fn percent_decode(input: &[u8]) -> Result<Cow<'_, [u8]>, EncodingError> {
if !input.contains(&b'%') {
return Ok(Cow::Borrowed(input));
}
Expand All @@ -20,7 +20,7 @@ pub fn percent_decode(input: &[u8]) -> Result<Cow<'_, [u8]>, PathError> {
if let Some(decoded) = decode_hex(a, b) {
output.push(decoded);
} else {
return Err(PathError::InvalidEncoding {
return Err(EncodingError::InvalidEncoding {
input: String::from_utf8_lossy(input).to_string(),
position: i,
character: [b'%', a, b],
Expand Down
3 changes: 3 additions & 0 deletions src/errors.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,9 @@ pub use constraint::ConstraintError;
pub(crate) mod delete;
pub use delete::DeleteError;

pub(crate) mod encoding;
pub use encoding::EncodingError;

pub(crate) mod insert;
pub use insert::InsertError;

Expand Down
18 changes: 9 additions & 9 deletions src/errors/delete.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,30 +7,30 @@ pub enum DeleteError {
/// A [`RouteError`] that occurred during the delete.
RouteError(RouteError),

/// Path to be deleted was not found in the router.
/// Route to be deleted was not found in the router.
///
/// # Examples
///
/// ```rust
/// use wayfind::errors::DeleteError;
///
/// let error = DeleteError::NotFound {
/// path: "/not_found".to_string(),
/// route: "/not_found".to_string(),
/// };
///
/// let display = "
/// not found
///
/// Path: /not_found
/// Route: /not_found
///
/// The specified path does not exist in the router
/// The specified route does not exist in the router
/// ";
///
/// assert_eq!(error.to_string(), display.trim());
/// ```
NotFound {
/// The path that was not found in the router.
path: String,
/// The route that was not found in the router.
route: String,
},
}

Expand All @@ -40,13 +40,13 @@ impl Display for DeleteError {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
Self::RouteError(error) => error.fmt(f),
Self::NotFound { path } => write!(
Self::NotFound { route } => write!(
f,
r#"not found
Path: {path}
Route: {route}
The specified path does not exist in the router"#
The specified route does not exist in the router"#
),
}
}
Expand Down
67 changes: 67 additions & 0 deletions src/errors/encoding.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
use std::{error::Error, fmt::Display};

/// Errors relating to attempting to decode percent-encoded strings.
#[derive(Debug, PartialEq, Eq)]
pub enum EncodingError {
/// Invalid percent-encoding sequence encountered.
///
/// # Examples
///
/// ```rust
/// use wayfind::errors::EncodingError;
///
/// let error = EncodingError::InvalidEncoding {
/// input: "/hello%GGworld".to_string(),
/// position: 6,
/// character: [b'%', b'G', b'G'],
/// };
///
/// let display = "
/// invalid percent-encoding
///
/// Input: /hello%GGworld
/// ^^^
///
/// Expected: '%' followed by two hexadecimal digits (a-F, 0-9)
/// Found: '%GG'
/// ";
///
/// assert_eq!(error.to_string(), display.trim());
/// ```
InvalidEncoding {
/// The unaltered input string.
input: String,
/// The position in the input where the invalid encoding was found.
position: usize,
/// The invalid character sequence.
character: [u8; 3],
},
}

impl Error for EncodingError {}

impl Display for EncodingError {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
Self::InvalidEncoding {
input,
position,
character,
} => {
let character = String::from_utf8_lossy(character);
let arrow = " ".repeat(*position) + "^^^";

write!(
f,
"invalid percent-encoding
Input: {input}
{arrow}
Expected: '%' followed by two hexadecimal digits (a-F, 0-9)
Found: '{character}'",
)
}
}
}
}
56 changes: 28 additions & 28 deletions src/errors/insert.rs
Original file line number Diff line number Diff line change
@@ -1,67 +1,67 @@
use super::{route::RouteError, PathError};
use super::{route::RouteError, EncodingError};
use std::{error::Error, fmt::Display};

/// Errors relating to attempting to insert a route into a [`Router`](crate::Router).
#[derive(Debug, PartialEq, Eq)]
pub enum InsertError {
/// A [`PathError`] that occurred at the start of the insert operation.
PathError(PathError),
/// A [`EncodingError`] that occurred during the decoding.
EncodingError(EncodingError),

/// A [`RouteError`] that occurred during the insert operation.
RouteError(RouteError),

/// The path provided was percent-encoded.
/// The route provided was percent-encoded.
///
/// # Examples
///
/// ```rust
/// use wayfind::errors::InsertError;
///
/// let error = InsertError::EncodedPath {
/// let error = InsertError::EncodedRoute {
/// input: "/hello%20world".to_string(),
/// decoded: "/hello world".to_string(),
/// };
///
/// let display = "
/// encoded path
/// encoded route
///
/// Input: /hello%20world
/// Decoded: /hello world
///
/// The router expects paths to be in their decoded form
/// The router expects routes to be in their decoded form
/// ";
///
/// assert_eq!(error.to_string(), display.trim());
/// ```
EncodedPath {
/// The original encoded input path.
EncodedRoute {
/// The original encoded input route.
input: String,
/// The decoded version of the path.
/// The decoded version of the route.
decoded: String,
},

/// The path being inserted already exists in the router.
/// The route being inserted already exists in the router.
///
/// # Examples
///
/// ```rust
/// use wayfind::errors::InsertError;
///
/// let error = InsertError::DuplicatePath {
/// path: "/existing/path".to_string(),
/// let error = InsertError::DuplicateRoute {
/// route: "/existing/route".to_string(),
/// };
///
/// let display = "
/// duplicate path
/// duplicate route
///
/// Path: /existing/path
/// Route: /existing/route
/// ";
///
/// assert_eq!(error.to_string(), display.trim());
/// ```
DuplicatePath {
/// The path that already exists in the router.
path: String,
DuplicateRoute {
/// The route that already exists in the router.
route: String,
},

/// The constraint specified in the route is not recognized by the router.
Expand Down Expand Up @@ -96,22 +96,22 @@ impl Error for InsertError {}
impl Display for InsertError {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
Self::PathError(error) => error.fmt(f),
Self::EncodingError(error) => error.fmt(f),
Self::RouteError(error) => error.fmt(f),
Self::EncodedPath { input, decoded } => write!(
Self::EncodedRoute { input, decoded } => write!(
f,
r#"encoded path
r#"encoded route
Input: {input}
Decoded: {decoded}
The router expects paths to be in their decoded form"#
The router expects routes to be in their decoded form"#
),
Self::DuplicatePath { path } => write!(
Self::DuplicateRoute { route } => write!(
f,
r#"duplicate path
r#"duplicate route
Path: {path}"#
Route: {route}"#
),
Self::UnknownConstraint { constraint } => write!(
f,
Expand All @@ -125,9 +125,9 @@ The router doesn't recognize this constraint"#
}
}

impl From<PathError> for InsertError {
fn from(error: PathError) -> Self {
Self::PathError(error)
impl From<EncodingError> for InsertError {
fn from(error: EncodingError) -> Self {
Self::EncodingError(error)
}
}

Expand Down
65 changes: 12 additions & 53 deletions src/errors/path.rs
Original file line number Diff line number Diff line change
@@ -1,67 +1,26 @@
use std::{error::Error, fmt::Display};

/// Errors relating to attempting to decode and validate path.
use super::EncodingError;

/// Errors relating to attempting to decode and validate path.
#[derive(Debug, PartialEq, Eq)]
pub enum PathError {
/// Invalid percent-encoding sequence encountered.
///
/// # Examples
///
/// ```rust
/// use wayfind::errors::PathError;
///
/// let error = PathError::InvalidEncoding {
/// input: "/hello%GGworld".to_string(),
/// position: 6,
/// character: [b'%', b'G', b'G'],
/// };
///
/// let display = "
/// invalid percent-encoding
///
/// Input: /hello%GGworld
/// ^^^
///
/// Expected: '%' followed by two hexadecimal digits (a-F, 0-9)
/// Found: '%GG'
/// ";
///
/// assert_eq!(error.to_string(), display.trim());
/// ```
InvalidEncoding {
/// The unaltered input string.
input: String,
/// The position in the input where the invalid encoding was found.
position: usize,
/// The invalid character sequence.
character: [u8; 3],
},
/// A [`EncodingError`] that occurred during the decoding.
EncodingError(EncodingError),
}

impl Error for PathError {}

impl Display for PathError {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
Self::InvalidEncoding {
input,
position,
character,
} => {
let character = String::from_utf8_lossy(character);
let arrow = " ".repeat(*position) + "^^^";

write!(
f,
"invalid percent-encoding
Input: {input}
{arrow}
Expected: '%' followed by two hexadecimal digits (a-F, 0-9)
Found: '{character}'",
)
}
Self::EncodingError(error) => error.fmt(f),
}
}
}

impl From<EncodingError> for PathError {
fn from(error: EncodingError) -> Self {
Self::EncodingError(error)
}
}
Loading

0 comments on commit 0a3ceb0

Please sign in to comment.