WIP encoder
This commit is contained in:
parent
fadadffc92
commit
33a02ff695
4 changed files with 101 additions and 84 deletions
|
@ -8,28 +8,6 @@ use quick_xml::writer::{ElementWriter, Writer};
|
||||||
use quick_xml::name::PrefixDeclaration;
|
use quick_xml::name::PrefixDeclaration;
|
||||||
use tokio::io::AsyncWrite;
|
use tokio::io::AsyncWrite;
|
||||||
|
|
||||||
/*pub trait CalWriter<E: Extension>: DavWriter<E> {
|
|
||||||
fn create_cal_element(&mut self, name: &str) -> ElementWriter<impl AsyncWrite + Unpin>;
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<'a, W: AsyncWrite+Unpin> DavWriter<CalExtension> for Writer<'a, W, CalExtension> {
|
|
||||||
fn create_dav_element(&mut self, name: &str) -> ElementWriter<impl AsyncWrite + Unpin> {
|
|
||||||
self.create_ns_element(name, Namespace::Dav)
|
|
||||||
}
|
|
||||||
fn child(w: &'a mut QWriter<W>) -> impl DavWriter<CalExtension> {
|
|
||||||
Self::child(w)
|
|
||||||
}
|
|
||||||
async fn error(&mut self, err: &Violation) -> Result<(), QError> {
|
|
||||||
err.write(self).await
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<'a, W: AsyncWrite+Unpin> CalWriter<CalExtension> for Writer<'a, W, CalExtension> {
|
|
||||||
fn create_cal_element(&mut self, name: &str) -> ElementWriter<impl AsyncWrite + Unpin> {
|
|
||||||
self.create_ns_element(name, Namespace::CalDav)
|
|
||||||
}
|
|
||||||
}*/
|
|
||||||
|
|
||||||
pub struct CalCtx {
|
pub struct CalCtx {
|
||||||
root: bool
|
root: bool
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,25 +1,11 @@
|
||||||
use super::types::*;
|
use super::types::*;
|
||||||
|
|
||||||
pub enum Namespace {
|
|
||||||
Dav,
|
|
||||||
CalDav,
|
|
||||||
}
|
|
||||||
|
|
||||||
pub struct CalExtension {}
|
pub struct CalExtension {}
|
||||||
impl Extension for CalExtension {
|
impl Extension for CalExtension {
|
||||||
type Error = Violation;
|
type Error = Violation;
|
||||||
type Namespace = Namespace;
|
type Property = Property;
|
||||||
|
type PropertyRequest = Property; //@FIXME
|
||||||
fn namespaces() -> &'static [(&'static str, &'static str)] {
|
|
||||||
return &[ ("D", "DAV:"), ("C", "urn:ietf:params:xml:ns:caldav") ][..]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn short_ns(ns: Self::Namespace) -> &'static str {
|
|
||||||
match ns {
|
|
||||||
Namespace::Dav => "D",
|
|
||||||
Namespace::CalDav => "C",
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
pub enum Violation {
|
pub enum Violation {
|
||||||
|
@ -39,3 +25,9 @@ pub enum Violation {
|
||||||
/// param-filter*)>
|
/// param-filter*)>
|
||||||
SupportedFilter,
|
SupportedFilter,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
pub enum Property {
|
||||||
|
CalendarDescription,
|
||||||
|
CalendarTimezone,
|
||||||
|
}
|
||||||
|
|
|
@ -149,16 +149,68 @@ impl<E: Extension, C: Context<E>> QuickWritable<E,C> for ResponseDescription {
|
||||||
|
|
||||||
impl<E: Extension, C: Context<E>> QuickWritable<E,C> for Location {
|
impl<E: Extension, C: Context<E>> QuickWritable<E,C> for Location {
|
||||||
async fn write(&self, xml: &mut Writer<impl AsyncWrite+Unpin>, ctx: C) -> Result<(), QError> {
|
async fn write(&self, xml: &mut Writer<impl AsyncWrite+Unpin>, ctx: C) -> Result<(), QError> {
|
||||||
unimplemented!();
|
let start = ctx.create_dav_element("location");
|
||||||
|
let end = start.to_end();
|
||||||
|
|
||||||
|
xml.write_event_async(Event::Start(start.clone())).await?;
|
||||||
|
self.0.write(xml, ctx.child()).await?;
|
||||||
|
xml.write_event_async(Event::End(end)).await?;
|
||||||
|
|
||||||
|
Ok(())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<E: Extension, C: Context<E>> QuickWritable<E,C> for PropStat<E> {
|
impl<E: Extension, C: Context<E>> QuickWritable<E,C> for PropStat<E> {
|
||||||
async fn write(&self, xml: &mut Writer<impl AsyncWrite+Unpin>, ctx: C) -> Result<(), QError> {
|
async fn write(&self, xml: &mut Writer<impl AsyncWrite+Unpin>, ctx: C) -> Result<(), QError> {
|
||||||
unimplemented!();
|
let start = ctx.create_dav_element("propstat");
|
||||||
|
let end = start.to_end();
|
||||||
|
|
||||||
|
xml.write_event_async(Event::Start(start.clone())).await?;
|
||||||
|
self.prop.write(xml, ctx.child()).await?;
|
||||||
|
self.status.write(xml, ctx.child()).await?;
|
||||||
|
if let Some(error) = &self.error {
|
||||||
|
error.write(xml, ctx.child()).await?;
|
||||||
|
}
|
||||||
|
if let Some(description) = &self.responsedescription {
|
||||||
|
description.write(xml, ctx.child()).await?;
|
||||||
|
}
|
||||||
|
xml.write_event_async(Event::End(end)).await?;
|
||||||
|
|
||||||
|
Ok(())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl<E: Extension, C: Context<E>> QuickWritable<E,C> for Prop<E> {
|
||||||
|
async fn write(&self, xml: &mut Writer<impl AsyncWrite+Unpin>, ctx: C) -> Result<(), QError> {
|
||||||
|
let start = ctx.create_dav_element("prop");
|
||||||
|
let end = start.to_end();
|
||||||
|
|
||||||
|
xml.write_event_async(Event::Start(start.clone())).await?;
|
||||||
|
for property in &self.0 {
|
||||||
|
property.write(xml, ctx.child()).await?;
|
||||||
|
}
|
||||||
|
xml.write_event_async(Event::End(end)).await?;
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
impl<E: Extension, C: Context<E>> QuickWritable<E,C> for Property<E> {
|
||||||
|
async fn write(&self, xml: &mut Writer<impl AsyncWrite+Unpin>, ctx: C) -> Result<(), QError> {
|
||||||
|
use Property::*;
|
||||||
|
match self {
|
||||||
|
CreationDate(date) => unimplemented!(),
|
||||||
|
DisplayName(name) => unimplemented!(),
|
||||||
|
//@FIXME not finished
|
||||||
|
_ => unimplemented!(),
|
||||||
|
};
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
impl<E: Extension, C: Context<E>> QuickWritable<E,C> for Error<E> {
|
impl<E: Extension, C: Context<E>> QuickWritable<E,C> for Error<E> {
|
||||||
async fn write(&self, xml: &mut Writer<impl AsyncWrite+Unpin>, ctx: C) -> Result<(), QError> {
|
async fn write(&self, xml: &mut Writer<impl AsyncWrite+Unpin>, ctx: C) -> Result<(), QError> {
|
||||||
let start = ctx.create_dav_element("error");
|
let start = ctx.create_dav_element("error");
|
||||||
|
|
|
@ -6,10 +6,8 @@ use chrono::{DateTime,FixedOffset};
|
||||||
pub struct Disabled(());
|
pub struct Disabled(());
|
||||||
pub trait Extension {
|
pub trait Extension {
|
||||||
type Error;
|
type Error;
|
||||||
type Namespace;
|
type Property;
|
||||||
|
type PropertyRequest;
|
||||||
fn namespaces() -> &'static [(&'static str, &'static str)];
|
|
||||||
fn short_ns(ns: Self::Namespace) -> &'static str;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// No extension
|
/// No extension
|
||||||
|
@ -19,16 +17,9 @@ pub enum Namespace {
|
||||||
}
|
}
|
||||||
impl Extension for NoExtension {
|
impl Extension for NoExtension {
|
||||||
type Error = Disabled;
|
type Error = Disabled;
|
||||||
type Namespace = Namespace;
|
type Property = Disabled;
|
||||||
|
type PropertyRequest = Disabled;
|
||||||
fn namespaces() -> &'static [(&'static str, &'static str)] {
|
}
|
||||||
return &[ ("D", "DAV:") ][..]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn short_ns(ns: Self::Namespace) -> &'static str {
|
|
||||||
"D"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// 14.1. activelock XML Element
|
/// 14.1. activelock XML Element
|
||||||
///
|
///
|
||||||
|
@ -38,11 +29,11 @@ impl Extension for NoExtension {
|
||||||
/// <!ELEMENT activelock (lockscope, locktype, depth, owner?, timeout?,
|
/// <!ELEMENT activelock (lockscope, locktype, depth, owner?, timeout?,
|
||||||
/// locktoken?, lockroot)>
|
/// locktoken?, lockroot)>
|
||||||
pub struct ActiveLock {
|
pub struct ActiveLock {
|
||||||
lockscope: LockScope,
|
pub lockscope: LockScope,
|
||||||
locktype: LockType,
|
pub locktype: LockType,
|
||||||
depth: Depth,
|
pub depth: Depth,
|
||||||
owner: Option<Owner>,
|
pub owner: Option<Owner>,
|
||||||
timeout: Option<Timeout>,
|
pub timeout: Option<Timeout>,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// 14.2 allprop XML Element
|
/// 14.2 allprop XML Element
|
||||||
|
@ -225,7 +216,7 @@ pub struct Href(pub String);
|
||||||
/// standards. This element MUST NOT contain text or mixed content.
|
/// standards. This element MUST NOT contain text or mixed content.
|
||||||
///
|
///
|
||||||
/// <!ELEMENT include ANY >
|
/// <!ELEMENT include ANY >
|
||||||
pub struct Include(Vec<Property>);
|
pub struct Include<T: Extension>(pub Vec<Property<T>>);
|
||||||
|
|
||||||
/// 14.9. location XML Element
|
/// 14.9. location XML Element
|
||||||
///
|
///
|
||||||
|
@ -241,7 +232,7 @@ pub struct Include(Vec<Property>);
|
||||||
/// that would be used in a Location header.
|
/// that would be used in a Location header.
|
||||||
///
|
///
|
||||||
/// <!ELEMENT location (href)>
|
/// <!ELEMENT location (href)>
|
||||||
pub struct Location(Href);
|
pub struct Location(pub Href);
|
||||||
|
|
||||||
/// 14.10. lockentry XML Element
|
/// 14.10. lockentry XML Element
|
||||||
///
|
///
|
||||||
|
@ -252,8 +243,8 @@ pub struct Location(Href);
|
||||||
///
|
///
|
||||||
/// <!ELEMENT lockentry (lockscope, locktype) >
|
/// <!ELEMENT lockentry (lockscope, locktype) >
|
||||||
pub struct LockEntry {
|
pub struct LockEntry {
|
||||||
lokscope: LockScope,
|
pub lokscope: LockScope,
|
||||||
locktype: LockType,
|
pub locktype: LockType,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// 14.11. lockinfo XML Element
|
/// 14.11. lockinfo XML Element
|
||||||
|
@ -265,9 +256,9 @@ pub struct LockEntry {
|
||||||
///
|
///
|
||||||
/// <!ELEMENT lockinfo (lockscope, locktype, owner?) >
|
/// <!ELEMENT lockinfo (lockscope, locktype, owner?) >
|
||||||
pub struct LockInfo {
|
pub struct LockInfo {
|
||||||
lockscope: LockScope,
|
pub lockscope: LockScope,
|
||||||
locktype: LockType,
|
pub locktype: LockType,
|
||||||
owner: Option<Owner>,
|
pub owner: Option<Owner>,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// 14.12. lockroot XML Element
|
/// 14.12. lockroot XML Element
|
||||||
|
@ -282,7 +273,7 @@ pub struct LockInfo {
|
||||||
/// values and the response to LOCK requests.
|
/// values and the response to LOCK requests.
|
||||||
///
|
///
|
||||||
/// <!ELEMENT lockroot (href) >
|
/// <!ELEMENT lockroot (href) >
|
||||||
pub struct LockRoot(Href);
|
pub struct LockRoot(pub Href);
|
||||||
|
|
||||||
/// 14.13. lockscope XML Element
|
/// 14.13. lockscope XML Element
|
||||||
///
|
///
|
||||||
|
@ -369,7 +360,7 @@ pub struct Multistatus<T: Extension> {
|
||||||
/// text content or attributes.
|
/// text content or attributes.
|
||||||
///
|
///
|
||||||
/// <!ELEMENT owner ANY >
|
/// <!ELEMENT owner ANY >
|
||||||
pub struct Owner(String);
|
pub struct Owner(pub String);
|
||||||
|
|
||||||
/// 14.18. prop XML Element
|
/// 14.18. prop XML Element
|
||||||
///
|
///
|
||||||
|
@ -385,7 +376,7 @@ pub struct Owner(String);
|
||||||
/// text or mixed content.
|
/// text or mixed content.
|
||||||
///
|
///
|
||||||
/// <!ELEMENT prop ANY >
|
/// <!ELEMENT prop ANY >
|
||||||
pub struct Prop(Vec<Property>);
|
pub struct Prop<T: Extension>(pub Vec<Property<T>>);
|
||||||
|
|
||||||
/// 14.19. propertyupdate XML Element
|
/// 14.19. propertyupdate XML Element
|
||||||
///
|
///
|
||||||
|
@ -397,10 +388,10 @@ pub struct Prop(Vec<Property>);
|
||||||
/// required to modify the properties on the resource.
|
/// required to modify the properties on the resource.
|
||||||
///
|
///
|
||||||
/// <!ELEMENT propertyupdate (remove | set)+ >
|
/// <!ELEMENT propertyupdate (remove | set)+ >
|
||||||
pub struct PropertyUpdate(Vec<PropertyUpdateItem>);
|
pub struct PropertyUpdate<T: Extension>(Vec<PropertyUpdateItem<T>>);
|
||||||
pub enum PropertyUpdateItem {
|
pub enum PropertyUpdateItem<T: Extension> {
|
||||||
Remove(Remove),
|
Remove(Remove<T>),
|
||||||
Set(Set),
|
Set(Set<T>),
|
||||||
}
|
}
|
||||||
|
|
||||||
/// 14.20. propfind XML Element
|
/// 14.20. propfind XML Element
|
||||||
|
@ -414,10 +405,10 @@ pub enum PropertyUpdateItem {
|
||||||
/// values.
|
/// values.
|
||||||
///
|
///
|
||||||
/// <!ELEMENT propfind ( propname | (allprop, include?) | prop ) >
|
/// <!ELEMENT propfind ( propname | (allprop, include?) | prop ) >
|
||||||
pub enum PropFind {
|
pub enum PropFind<T: Extension> {
|
||||||
PropName(PropName),
|
PropName(PropName),
|
||||||
AllProp(AllProp, Option<Include>),
|
AllProp(AllProp, Option<Include<T>>),
|
||||||
Prop(Prop),
|
Prop(Prop<T>),
|
||||||
}
|
}
|
||||||
|
|
||||||
/// 14.21. propname XML Element
|
/// 14.21. propname XML Element
|
||||||
|
@ -446,10 +437,10 @@ pub struct PropName {}
|
||||||
///
|
///
|
||||||
/// <!ELEMENT propstat (prop, status, error?, responsedescription?) >
|
/// <!ELEMENT propstat (prop, status, error?, responsedescription?) >
|
||||||
pub struct PropStat<T: Extension> {
|
pub struct PropStat<T: Extension> {
|
||||||
prop: Prop,
|
pub prop: Prop<T>,
|
||||||
status: Status,
|
pub status: Status,
|
||||||
error: Option<Error<T>>,
|
pub error: Option<Error<T>>,
|
||||||
responsedescription: Option<ResponseDescription>,
|
pub responsedescription: Option<ResponseDescription>,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// 14.23. remove XML Element
|
/// 14.23. remove XML Element
|
||||||
|
@ -465,7 +456,7 @@ pub struct PropStat<T: Extension> {
|
||||||
/// the names of properties to be removed are required.
|
/// the names of properties to be removed are required.
|
||||||
///
|
///
|
||||||
/// <!ELEMENT remove (prop) >
|
/// <!ELEMENT remove (prop) >
|
||||||
pub struct Remove(Prop);
|
pub struct Remove<T: Extension>(pub Prop<T>);
|
||||||
|
|
||||||
/// 14.24. response XML Element
|
/// 14.24. response XML Element
|
||||||
///
|
///
|
||||||
|
@ -530,7 +521,7 @@ pub struct ResponseDescription(pub String);
|
||||||
/// property, and MUST be subsequently retrievable using PROPFIND.
|
/// property, and MUST be subsequently retrievable using PROPFIND.
|
||||||
///
|
///
|
||||||
/// <!ELEMENT set (prop) >
|
/// <!ELEMENT set (prop) >
|
||||||
pub struct Set(Prop);
|
pub struct Set<T: Extension>(pub Prop<T>);
|
||||||
|
|
||||||
/// 14.27. shared XML Element
|
/// 14.27. shared XML Element
|
||||||
///
|
///
|
||||||
|
@ -595,7 +586,7 @@ pub struct Timeout(u64);
|
||||||
/// the header value could include LWS as defined in [RFC2616], Section
|
/// the header value could include LWS as defined in [RFC2616], Section
|
||||||
/// 4.2. Server implementors SHOULD strip LWS from these values before
|
/// 4.2. Server implementors SHOULD strip LWS from these values before
|
||||||
/// using as WebDAV property values.
|
/// using as WebDAV property values.
|
||||||
pub enum PropertyRequest {
|
pub enum PropertyRequest<T: Extension> {
|
||||||
CreationDate,
|
CreationDate,
|
||||||
DisplayName,
|
DisplayName,
|
||||||
GetContentLanguage,
|
GetContentLanguage,
|
||||||
|
@ -606,8 +597,9 @@ pub enum PropertyRequest {
|
||||||
LockDiscovery,
|
LockDiscovery,
|
||||||
ResourceType,
|
ResourceType,
|
||||||
SupportedLock,
|
SupportedLock,
|
||||||
|
Extension(T::PropertyRequest),
|
||||||
}
|
}
|
||||||
pub enum Property {
|
pub enum Property<T: Extension> {
|
||||||
/// 15.1. creationdate Property
|
/// 15.1. creationdate Property
|
||||||
///
|
///
|
||||||
/// Name: creationdate
|
/// Name: creationdate
|
||||||
|
@ -884,6 +876,9 @@ pub enum Property {
|
||||||
///
|
///
|
||||||
/// <!ELEMENT supportedlock (lockentry)* >
|
/// <!ELEMENT supportedlock (lockentry)* >
|
||||||
SupportedLock(Vec<LockEntry>),
|
SupportedLock(Vec<LockEntry>),
|
||||||
|
|
||||||
|
/// Any extension
|
||||||
|
Extension(T::Property),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue