api: Add stable_path
, r0_path
and unstable_path
metadata fields
This commit is contained in:
parent
0dcdb57c29
commit
1e900ab58c
@ -48,6 +48,9 @@ impl Api {
|
|||||||
let method = &metadata.method;
|
let method = &metadata.method;
|
||||||
let name = &metadata.name;
|
let name = &metadata.name;
|
||||||
let path = &metadata.path;
|
let path = &metadata.path;
|
||||||
|
let unstable_path = util::map_option_literal(&metadata.unstable_path);
|
||||||
|
let r0_path = util::map_option_literal(&metadata.r0_path);
|
||||||
|
let stable_path = util::map_option_literal(&metadata.stable_path);
|
||||||
let rate_limited: TokenStream = metadata
|
let rate_limited: TokenStream = metadata
|
||||||
.rate_limited
|
.rate_limited
|
||||||
.iter()
|
.iter()
|
||||||
@ -92,6 +95,9 @@ impl Api {
|
|||||||
method: #http::Method::#method,
|
method: #http::Method::#method,
|
||||||
name: #name,
|
name: #name,
|
||||||
path: #path,
|
path: #path,
|
||||||
|
unstable_path: #unstable_path,
|
||||||
|
r0_path: #r0_path,
|
||||||
|
stable_path: #stable_path,
|
||||||
added: #added,
|
added: #added,
|
||||||
deprecated: #deprecated,
|
deprecated: #deprecated,
|
||||||
removed: #removed,
|
removed: #removed,
|
||||||
|
@ -15,6 +15,9 @@ mod kw {
|
|||||||
syn::custom_keyword!(method);
|
syn::custom_keyword!(method);
|
||||||
syn::custom_keyword!(name);
|
syn::custom_keyword!(name);
|
||||||
syn::custom_keyword!(path);
|
syn::custom_keyword!(path);
|
||||||
|
syn::custom_keyword!(unstable);
|
||||||
|
syn::custom_keyword!(r0);
|
||||||
|
syn::custom_keyword!(stable);
|
||||||
syn::custom_keyword!(rate_limited);
|
syn::custom_keyword!(rate_limited);
|
||||||
syn::custom_keyword!(authentication);
|
syn::custom_keyword!(authentication);
|
||||||
syn::custom_keyword!(added);
|
syn::custom_keyword!(added);
|
||||||
@ -42,8 +45,17 @@ pub struct Metadata {
|
|||||||
/// The name field.
|
/// The name field.
|
||||||
pub name: LitStr,
|
pub name: LitStr,
|
||||||
|
|
||||||
/// The path field.
|
/// The path field. (deprecated)
|
||||||
pub path: LitStr,
|
pub path: EndpointPath,
|
||||||
|
|
||||||
|
/// The unstable path field.
|
||||||
|
pub unstable_path: Option<EndpointPath>,
|
||||||
|
|
||||||
|
/// The pre-v1.1 path field.
|
||||||
|
pub r0_path: Option<EndpointPath>,
|
||||||
|
|
||||||
|
/// The stable path field.
|
||||||
|
pub stable_path: Option<EndpointPath>,
|
||||||
|
|
||||||
/// The rate_limited field.
|
/// The rate_limited field.
|
||||||
pub rate_limited: Vec<MetadataField<LitBool>>,
|
pub rate_limited: Vec<MetadataField<LitBool>>,
|
||||||
@ -90,6 +102,9 @@ impl Parse for Metadata {
|
|||||||
let mut method = None;
|
let mut method = None;
|
||||||
let mut name = None;
|
let mut name = None;
|
||||||
let mut path = None;
|
let mut path = None;
|
||||||
|
let mut unstable_path = None;
|
||||||
|
let mut r0_path = None;
|
||||||
|
let mut stable_path = None;
|
||||||
let mut rate_limited = vec![];
|
let mut rate_limited = vec![];
|
||||||
let mut authentication = vec![];
|
let mut authentication = vec![];
|
||||||
let mut added = None;
|
let mut added = None;
|
||||||
@ -102,6 +117,9 @@ impl Parse for Metadata {
|
|||||||
FieldValue::Method(m) => set_field(&mut method, m)?,
|
FieldValue::Method(m) => set_field(&mut method, m)?,
|
||||||
FieldValue::Name(n) => set_field(&mut name, n)?,
|
FieldValue::Name(n) => set_field(&mut name, n)?,
|
||||||
FieldValue::Path(p) => set_field(&mut path, p)?,
|
FieldValue::Path(p) => set_field(&mut path, p)?,
|
||||||
|
FieldValue::Unstable(p) => set_field(&mut unstable_path, p)?,
|
||||||
|
FieldValue::R0(p) => set_field(&mut r0_path, p)?,
|
||||||
|
FieldValue::Stable(p) => set_field(&mut stable_path, p)?,
|
||||||
FieldValue::RateLimited(value, attrs) => {
|
FieldValue::RateLimited(value, attrs) => {
|
||||||
rate_limited.push(MetadataField { attrs, value });
|
rate_limited.push(MetadataField { attrs, value });
|
||||||
}
|
}
|
||||||
@ -141,11 +159,29 @@ impl Parse for Metadata {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if let Some(added) = &added {
|
||||||
|
if stable_path.is_none() {
|
||||||
|
return Err(syn::Error::new_spanned(
|
||||||
|
added,
|
||||||
|
"added version is defined, but no stable path exists",
|
||||||
|
));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if unstable_path.is_none() && r0_path.is_none() && stable_path.is_none() {
|
||||||
|
// TODO replace with error
|
||||||
|
// return Err(syn::Error::new_spanned(metadata_kw, "no path is defined"));
|
||||||
|
r0_path = path.clone();
|
||||||
|
}
|
||||||
|
|
||||||
Ok(Self {
|
Ok(Self {
|
||||||
description: description.ok_or_else(|| missing_field("description"))?,
|
description: description.ok_or_else(|| missing_field("description"))?,
|
||||||
method: method.ok_or_else(|| missing_field("method"))?,
|
method: method.ok_or_else(|| missing_field("method"))?,
|
||||||
name: name.ok_or_else(|| missing_field("name"))?,
|
name: name.ok_or_else(|| missing_field("name"))?,
|
||||||
path: path.ok_or_else(|| missing_field("path"))?,
|
path: path.ok_or_else(|| missing_field("path"))?,
|
||||||
|
unstable_path,
|
||||||
|
r0_path,
|
||||||
|
stable_path,
|
||||||
rate_limited: if rate_limited.is_empty() {
|
rate_limited: if rate_limited.is_empty() {
|
||||||
return Err(missing_field("rate_limited"));
|
return Err(missing_field("rate_limited"));
|
||||||
} else {
|
} else {
|
||||||
@ -168,6 +204,9 @@ enum Field {
|
|||||||
Method,
|
Method,
|
||||||
Name,
|
Name,
|
||||||
Path,
|
Path,
|
||||||
|
Unstable,
|
||||||
|
R0,
|
||||||
|
Stable,
|
||||||
RateLimited,
|
RateLimited,
|
||||||
Authentication,
|
Authentication,
|
||||||
Added,
|
Added,
|
||||||
@ -191,6 +230,15 @@ impl Parse for Field {
|
|||||||
} else if lookahead.peek(kw::path) {
|
} else if lookahead.peek(kw::path) {
|
||||||
let _: kw::path = input.parse()?;
|
let _: kw::path = input.parse()?;
|
||||||
Ok(Self::Path)
|
Ok(Self::Path)
|
||||||
|
} else if lookahead.peek(kw::unstable) {
|
||||||
|
let _: kw::unstable = input.parse()?;
|
||||||
|
Ok(Self::Unstable)
|
||||||
|
} else if lookahead.peek(kw::r0) {
|
||||||
|
let _: kw::r0 = input.parse()?;
|
||||||
|
Ok(Self::R0)
|
||||||
|
} else if lookahead.peek(kw::stable) {
|
||||||
|
let _: kw::stable = input.parse()?;
|
||||||
|
Ok(Self::Stable)
|
||||||
} else if lookahead.peek(kw::rate_limited) {
|
} else if lookahead.peek(kw::rate_limited) {
|
||||||
let _: kw::rate_limited = input.parse()?;
|
let _: kw::rate_limited = input.parse()?;
|
||||||
Ok(Self::RateLimited)
|
Ok(Self::RateLimited)
|
||||||
@ -216,7 +264,10 @@ enum FieldValue {
|
|||||||
Description(LitStr),
|
Description(LitStr),
|
||||||
Method(Ident),
|
Method(Ident),
|
||||||
Name(LitStr),
|
Name(LitStr),
|
||||||
Path(LitStr),
|
Path(EndpointPath),
|
||||||
|
Unstable(EndpointPath),
|
||||||
|
R0(EndpointPath),
|
||||||
|
Stable(EndpointPath),
|
||||||
RateLimited(LitBool, Vec<Attribute>),
|
RateLimited(LitBool, Vec<Attribute>),
|
||||||
Authentication(AuthScheme, Vec<Attribute>),
|
Authentication(AuthScheme, Vec<Attribute>),
|
||||||
Added(MatrixVersionLiteral),
|
Added(MatrixVersionLiteral),
|
||||||
@ -242,18 +293,10 @@ impl Parse for FieldValue {
|
|||||||
Field::Description => Self::Description(input.parse()?),
|
Field::Description => Self::Description(input.parse()?),
|
||||||
Field::Method => Self::Method(input.parse()?),
|
Field::Method => Self::Method(input.parse()?),
|
||||||
Field::Name => Self::Name(input.parse()?),
|
Field::Name => Self::Name(input.parse()?),
|
||||||
Field::Path => {
|
Field::Path => Self::Path(input.parse()?),
|
||||||
let path: LitStr = input.parse()?;
|
Field::Unstable => Self::Unstable(input.parse()?),
|
||||||
|
Field::R0 => Self::R0(input.parse()?),
|
||||||
if !util::is_valid_endpoint_path(&path.value()) {
|
Field::Stable => Self::Stable(input.parse()?),
|
||||||
return Err(syn::Error::new_spanned(
|
|
||||||
&path,
|
|
||||||
"path may only contain printable ASCII characters with no spaces",
|
|
||||||
));
|
|
||||||
}
|
|
||||||
|
|
||||||
Self::Path(path)
|
|
||||||
}
|
|
||||||
Field::RateLimited => Self::RateLimited(input.parse()?, attrs),
|
Field::RateLimited => Self::RateLimited(input.parse()?, attrs),
|
||||||
Field::Authentication => Self::Authentication(input.parse()?, attrs),
|
Field::Authentication => Self::Authentication(input.parse()?, attrs),
|
||||||
Field::Added => Self::Added(input.parse()?),
|
Field::Added => Self::Added(input.parse()?),
|
||||||
@ -262,3 +305,27 @@ impl Parse for FieldValue {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Clone)]
|
||||||
|
pub struct EndpointPath(LitStr);
|
||||||
|
|
||||||
|
impl Parse for EndpointPath {
|
||||||
|
fn parse(input: ParseStream<'_>) -> syn::Result<Self> {
|
||||||
|
let path: LitStr = input.parse()?;
|
||||||
|
|
||||||
|
if util::is_valid_endpoint_path(&path.value()) {
|
||||||
|
Ok(Self(path))
|
||||||
|
} else {
|
||||||
|
Err(syn::Error::new_spanned(
|
||||||
|
&path,
|
||||||
|
"path may only contain printable ASCII characters with no spaces",
|
||||||
|
))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl ToTokens for EndpointPath {
|
||||||
|
fn to_tokens(&self, tokens: &mut proc_macro2::TokenStream) {
|
||||||
|
self.0.to_tokens(tokens)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -415,9 +415,19 @@ pub struct Metadata {
|
|||||||
/// A unique identifier for this endpoint.
|
/// A unique identifier for this endpoint.
|
||||||
pub name: &'static str,
|
pub name: &'static str,
|
||||||
|
|
||||||
|
/// (DEPRECATED)
|
||||||
|
pub path: &'static str,
|
||||||
|
|
||||||
|
/// The unstable path of this endpoint's URL, often `None`, used for developmental purposes.
|
||||||
|
pub unstable_path: Option<&'static str>,
|
||||||
|
|
||||||
|
/// The pre-v1.1 version of this endpoint's URL, `None` for post-v1.1 endpoints, supplemental
|
||||||
|
/// to `stable_path`.
|
||||||
|
pub r0_path: Option<&'static str>,
|
||||||
|
|
||||||
/// The path of this endpoint's URL, with variable names where path parameters should be filled
|
/// The path of this endpoint's URL, with variable names where path parameters should be filled
|
||||||
/// in during a request.
|
/// in during a request.
|
||||||
pub path: &'static str,
|
pub stable_path: Option<&'static str>,
|
||||||
|
|
||||||
/// Whether or not this endpoint is rate limited by the server.
|
/// Whether or not this endpoint is rate limited by the server.
|
||||||
pub rate_limited: bool,
|
pub rate_limited: bool,
|
||||||
|
@ -29,6 +29,9 @@ const METADATA: Metadata = Metadata {
|
|||||||
method: Method::PUT,
|
method: Method::PUT,
|
||||||
name: "create_alias",
|
name: "create_alias",
|
||||||
path: "/_matrix/client/r0/directory/room/:room_alias",
|
path: "/_matrix/client/r0/directory/room/:room_alias",
|
||||||
|
unstable_path: None,
|
||||||
|
r0_path: None,
|
||||||
|
stable_path: None,
|
||||||
rate_limited: false,
|
rate_limited: false,
|
||||||
authentication: AuthScheme::None,
|
authentication: AuthScheme::None,
|
||||||
added: None,
|
added: None,
|
||||||
|
@ -8,6 +8,9 @@ ruma_api! {
|
|||||||
method: POST, // An `http::Method` constant. No imports required.
|
method: POST, // An `http::Method` constant. No imports required.
|
||||||
name: "some_endpoint",
|
name: "some_endpoint",
|
||||||
path: "/_matrix/some/endpoint/:baz",
|
path: "/_matrix/some/endpoint/:baz",
|
||||||
|
unstable: "/_matrix/some/msc1234/endpoint/:baz",
|
||||||
|
r0: "/_matrix/some/r0/endpoint/:baz",
|
||||||
|
stable: "/_matrix/some/v1/endpoint/:baz",
|
||||||
rate_limited: false,
|
rate_limited: false,
|
||||||
authentication: None,
|
authentication: None,
|
||||||
added: 1.0,
|
added: 1.0,
|
||||||
@ -56,6 +59,10 @@ ruma_api! {
|
|||||||
fn main() {
|
fn main() {
|
||||||
use ruma_api::MatrixVersion;
|
use ruma_api::MatrixVersion;
|
||||||
|
|
||||||
|
assert_eq!(METADATA.unstable_path, Some("/_matrix/some/msc1234/endpoint/:baz"));
|
||||||
|
assert_eq!(METADATA.r0_path, Some("/_matrix/some/r0/endpoint/:baz"));
|
||||||
|
assert_eq!(METADATA.stable_path, Some("/_matrix/some/v1/endpoint/:baz"));
|
||||||
|
|
||||||
assert_eq!(METADATA.added, Some(MatrixVersion::V1_0));
|
assert_eq!(METADATA.added, Some(MatrixVersion::V1_0));
|
||||||
assert_eq!(METADATA.deprecated, Some(MatrixVersion::V1_1));
|
assert_eq!(METADATA.deprecated, Some(MatrixVersion::V1_1));
|
||||||
assert_eq!(METADATA.removed, Some(MatrixVersion::V1_2));
|
assert_eq!(METADATA.removed, Some(MatrixVersion::V1_2));
|
||||||
|
Loading…
x
Reference in New Issue
Block a user