Skip to content
Snippets Groups Projects
Commit f4d6db30 authored by codecraft's avatar codecraft :crocodile:
Browse files

Start the from_str implementation of Cookie

parent b9320218
No related branches found
No related tags found
1 merge request!1Initial feature merge
use std::{error::Error, str::FromStr, time::Duration};
use crate::{handling::response::CookieBuilder, utils::urlencoded::DeCodable};
/// Structure representing a Cookie
/// # Creating a Cookie:
/// ```
......@@ -8,6 +10,7 @@ use std::{error::Error, str::FromStr, time::Duration};
///
/// let cookie = CookieBuilder::build("name", "value").finish();
/// ```
#[derive(PartialEq, Eq, PartialOrd, Ord, Debug)]
pub struct Cookie {
/// Storage for the cookie string. Only used if this structure was derived
/// from a string that was subsequently parsed.
......@@ -93,6 +96,7 @@ pub struct ParseCookieError {
#[derive(Debug, PartialEq, PartialOrd, Eq, Ord)]
pub enum CookieError {
MissingEqual,
InvalidAttribute,
}
impl std::fmt::Display for ParseCookieError {
......@@ -104,7 +108,44 @@ impl std::fmt::Display for ParseCookieError {
impl FromStr for Cookie {
type Err = ParseCookieError;
fn from_str(s: &str) -> Result<Self, Self::Err> {
todo!()
let mut final_result = CookieBuilder::build("", "");
let mut first = true;
for part in s.split(';') {
let trimmed_part = part.trim();
if first {
let Some(name_val) = part.split_once('=') else {
return Err(Self::Err { inner: CookieError::MissingEqual });
};
unsafe {
final_result = CookieBuilder::build(
&String::from_utf8_unchecked(if let Ok(name) = name_val.0.decode() {
name
} else {
name_val.0.into()
}),
&String::from_utf8_unchecked(if let Ok(value) = name_val.1.decode() {
value
} else {
name_val.1.into()
}),
);
}
first = false;
break;
}
final_result = match trimmed_part {
"Secure" => final_result.secure(true),
"HttpOnly" => final_result.http_only(true),
"Partitioned" => final_result.partitioned(true),
_ => {
return Err(Self::Err {
inner: CookieError::InvalidAttribute,
});
}
}
}
println!("{:?}", final_result);
Ok(final_result.finish())
}
}
......@@ -112,7 +153,7 @@ impl FromStr for Cookie {
mod test {
use std::time::Duration;
use crate::handling::response::CookieBuilder;
use crate::handling::response::{Cookie, CookieBuilder};
use super::SameSite;
......@@ -133,13 +174,16 @@ mod test {
.http_only(true)
.partitioned(true)
.expires("Monday")
.finish()
.to_string();
.finish();
let test_cookie3_res = "Set-Cookie: ab=ss; HttpOnly; Partitioned; \
Max-Age=24; Domain=codecraft.com; Path=/; SameSite=None; Secure; Expires=Monday";
Max-Age=24; Domain=codecraft.com; Path=%2F; SameSite=None; Secure; Expires=Monday";
let test_cookie4_res = "ab=ss; HttpOnly; Partitioned; \
Max-Age=24; Domain=codecraft.com; Path=%2F; SameSite=None; Secure; Expires=Monday";
assert_eq!(test_cookie1_res, test_cookie1);
assert_eq!(test_cookie2_res, test_cookie2);
assert_eq!(test_cookie3_res, test_cookie3);
assert_eq!(test_cookie3_res, test_cookie3.to_string());
assert_eq!(test_cookie4_res.parse::<Cookie>().unwrap(), test_cookie3);
}
}
......@@ -13,6 +13,7 @@ use super::{Cookie, SameSite};
///
/// let cookie = CookieBuilder::build("name", "value").path("/").finish();
/// ```
#[derive(Debug)]
pub struct CookieBuilder {
/// Cookie under the hood
inner: Cookie,
......
......@@ -18,7 +18,7 @@ impl UrlEncodeData {
pub fn from_raw<T: AsRef<[u8]>>(raw: T) -> Self {
Self {
raw: raw.as_ref().to_owned(),
encoded: raw.as_ref().encode(),
encoded: raw.encode(),
raw_string: String::from_utf8(raw.as_ref().into()).ok(),
}
}
......@@ -45,7 +45,7 @@ impl UrlEncodeData {
}
/// Gets an Optional string slice to the raw data
pub fn raw_string(&self) -> Option<&str> {
self.raw_string.as_ref().map(|x| x.as_str())
self.raw_string.as_deref()
}
}
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment