mirror of
https://github.com/lennart-k/rustical.git
synced 2025-12-14 19:32:29 +00:00
basic implementation for mkcol
This commit is contained in:
@@ -70,6 +70,29 @@ pub fn write_invalid_props_response<W: Write>(
|
|||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn write_propstat_element<F, W: Write>(
|
||||||
|
writer: &mut Writer<W>,
|
||||||
|
status: StatusCode,
|
||||||
|
prop_closure: F,
|
||||||
|
) -> Result<(), quick_xml::Error>
|
||||||
|
where
|
||||||
|
F: FnOnce(&mut Writer<W>) -> Result<(), quick_xml::Error>,
|
||||||
|
{
|
||||||
|
writer
|
||||||
|
.create_element("propstat")
|
||||||
|
.write_inner_content(|writer| {
|
||||||
|
writer
|
||||||
|
.create_element("prop")
|
||||||
|
.write_inner_content(prop_closure)?;
|
||||||
|
|
||||||
|
writer
|
||||||
|
.create_element("status")
|
||||||
|
.write_text_content(BytesText::new(&format!("HTTP/1.1 {}", status)))?;
|
||||||
|
Ok(())
|
||||||
|
})?;
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
// Writes a propstat response into a multistatus
|
// Writes a propstat response into a multistatus
|
||||||
// closure hooks into the <prop> element
|
// closure hooks into the <prop> element
|
||||||
pub fn write_propstat_response<F, W: Write>(
|
pub fn write_propstat_response<F, W: Write>(
|
||||||
@@ -88,18 +111,7 @@ where
|
|||||||
.create_element("href")
|
.create_element("href")
|
||||||
.write_text_content(BytesText::new(href))?;
|
.write_text_content(BytesText::new(href))?;
|
||||||
|
|
||||||
writer
|
write_propstat_element(writer, status, prop_closure)?;
|
||||||
.create_element("propstat")
|
|
||||||
.write_inner_content(|writer| {
|
|
||||||
writer
|
|
||||||
.create_element("prop")
|
|
||||||
.write_inner_content(prop_closure)?;
|
|
||||||
|
|
||||||
writer
|
|
||||||
.create_element("status")
|
|
||||||
.write_text_content(BytesText::new(&format!("HTTP/1.1 {}", status)))?;
|
|
||||||
Ok(())
|
|
||||||
})?;
|
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
})?;
|
})?;
|
||||||
@@ -124,3 +136,22 @@ where
|
|||||||
std::str::from_utf8(&output_buffer)?
|
std::str::from_utf8(&output_buffer)?
|
||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn generate_mkcol_response<'a, F, A>(namespaces: A, closure: F) -> Result<String>
|
||||||
|
where
|
||||||
|
F: FnOnce(&mut Writer<&mut Vec<u8>>) -> Result<(), quick_xml::Error>,
|
||||||
|
A: IntoIterator,
|
||||||
|
A::Item: Into<Attribute<'a>>,
|
||||||
|
{
|
||||||
|
let mut output_buffer = Vec::new();
|
||||||
|
let mut writer = Writer::new_with_indent(&mut output_buffer, b' ', 2);
|
||||||
|
writer
|
||||||
|
.create_element("mkcol-response")
|
||||||
|
.with_attributes(namespaces)
|
||||||
|
.write_inner_content(closure)?;
|
||||||
|
|
||||||
|
Ok(format!(
|
||||||
|
"<?xml version=\"1.0\" encoding=\"utf-8\"?>\n{}",
|
||||||
|
std::str::from_utf8(&output_buffer)?
|
||||||
|
))
|
||||||
|
}
|
||||||
|
|||||||
@@ -1,5 +1,7 @@
|
|||||||
use crate::namespace::Namespace;
|
use crate::namespace::Namespace;
|
||||||
use crate::propfind::{generate_multistatus, write_propstat_response};
|
use crate::propfind::{
|
||||||
|
generate_mkcol_response, generate_multistatus, write_propstat_element, write_propstat_response,
|
||||||
|
};
|
||||||
use crate::proptypes::write_string_prop;
|
use crate::proptypes::write_string_prop;
|
||||||
use crate::{CalDavContext, Error};
|
use crate::{CalDavContext, Error};
|
||||||
use actix_web::http::header::ContentType;
|
use actix_web::http::header::ContentType;
|
||||||
@@ -167,24 +169,26 @@ pub async fn route_mkcol_calendar<A: CheckAuthentication, C: CalendarStore>(
|
|||||||
_ => return Err(Error::BadRequest),
|
_ => return Err(Error::BadRequest),
|
||||||
}
|
}
|
||||||
|
|
||||||
for set_node in mkcol_node.children() {
|
// TODO: Why does the spec (rfc5689) allow multiple <set/> elements but only one resource? :/
|
||||||
if set_node.tag_name().name() != "set" {
|
// Well, for now just bother with the first one
|
||||||
return Err(Error::BadRequest);
|
let set_node = mkcol_node.first_element_child().ok_or(Error::BadRequest)?;
|
||||||
}
|
match set_node.tag_name().name() {
|
||||||
let prop_node = set_node.first_element_child().ok_or(Error::BadRequest)?;
|
"set" => {}
|
||||||
if prop_node.tag_name().name() != "prop" {
|
_ => return Err(Error::BadRequest),
|
||||||
return Err(Error::BadRequest);
|
|
||||||
}
|
|
||||||
handle_mkcol_calendar_set(
|
|
||||||
&context.store,
|
|
||||||
prop_node,
|
|
||||||
cid.clone(),
|
|
||||||
auth.inner.user_id.clone(),
|
|
||||||
)
|
|
||||||
.await
|
|
||||||
.map_err(|_e| Error::InternalError)?;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
println!("{body}");
|
let prop_node = set_node.first_element_child().ok_or(Error::BadRequest)?;
|
||||||
Err(Error::InternalError)
|
if prop_node.tag_name().name() != "prop" {
|
||||||
|
return Err(Error::BadRequest);
|
||||||
|
}
|
||||||
|
handle_mkcol_calendar_set(
|
||||||
|
&context.store,
|
||||||
|
prop_node,
|
||||||
|
cid.clone(),
|
||||||
|
auth.inner.user_id.clone(),
|
||||||
|
)
|
||||||
|
.await
|
||||||
|
.map_err(|_e| Error::InternalError)?;
|
||||||
|
|
||||||
|
Ok(HttpResponse::Created().body(""))
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user