f1ab857c6e
This declutters the main `xso` namespace. In addition, if (when) we introduce more complex generic implementations, we might want to have tests for these, and those can then live there, too, without making the main `lib.rs` file gigantic (or moving the tests too far away from the tested code).
822 lines
27 KiB
Rust
822 lines
27 KiB
Rust
// Copyright (c) 2024 Jonas Schäfer <jonas@zombofant.net>
|
|
//
|
|
// This Source Code Form is subject to the terms of the Mozilla Public
|
|
// License, v. 2.0. If a copy of the MPL was not distributed with this
|
|
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
|
|
|
//! Module with specific [`syn::Type`] constructors.
|
|
|
|
use proc_macro2::Span;
|
|
use syn::{spanned::Spanned, *};
|
|
|
|
/// Construct a [`syn::Type`] referring to `::xso::exports::rxml::Namespace`.
|
|
pub(crate) fn namespace_ty(span: Span) -> Type {
|
|
Type::Path(TypePath {
|
|
qself: None,
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("exports", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("rxml", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("Namespace", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to `::xso::exports::rxml::NcNameStr`.
|
|
pub(crate) fn ncnamestr_ty(span: Span) -> Type {
|
|
Type::Path(TypePath {
|
|
qself: None,
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("exports", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("rxml", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("NcNameStr", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to `Cow<#lifetime, #ty>`.
|
|
pub(crate) fn cow_ty(ty: Type, lifetime: Lifetime) -> Type {
|
|
let span = ty.span();
|
|
Type::Path(TypePath {
|
|
qself: None,
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("std", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("borrow", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("Cow", span),
|
|
arguments: PathArguments::AngleBracketed(AngleBracketedGenericArguments {
|
|
colon2_token: None,
|
|
lt_token: token::Lt { spans: [span] },
|
|
args: [
|
|
GenericArgument::Lifetime(lifetime),
|
|
GenericArgument::Type(ty),
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
gt_token: token::Gt { spans: [span] },
|
|
}),
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to
|
|
/// `Cow<#lifetime, ::rxml::NcNameStr>`.
|
|
pub(crate) fn ncnamestr_cow_ty(ty_span: Span, lifetime: Lifetime) -> Type {
|
|
cow_ty(ncnamestr_ty(ty_span), lifetime)
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `<#ty as ::xso::FromXmlText>::from_xml_text`.
|
|
pub(crate) fn from_xml_text_fn(ty: Type) -> Expr {
|
|
let span = ty.span();
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: Some(QSelf {
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
ty: Box::new(ty),
|
|
position: 2,
|
|
as_token: Some(syn::token::As { span }),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("FromXmlText", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("from_xml_text", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `<#ty as ::xso::AsOptionalXmlText>::as_optional_xml_text`.
|
|
pub(crate) fn as_optional_xml_text_fn(ty: Type) -> Expr {
|
|
let span = ty.span();
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: Some(QSelf {
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
ty: Box::new(ty),
|
|
position: 2,
|
|
as_token: Some(syn::token::As { span }),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("AsOptionalXmlText", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("as_optional_xml_text", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `<#of_ty as ::core::default::Default>::default`.
|
|
pub(crate) fn default_fn(of_ty: Type) -> Expr {
|
|
let span = of_ty.span();
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: Some(QSelf {
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
ty: Box::new(of_ty),
|
|
position: 3,
|
|
as_token: Some(syn::token::As { span }),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("core", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("default", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("Default", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("default", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to `::std::string::String`.
|
|
pub(crate) fn string_ty(span: Span) -> Type {
|
|
Type::Path(TypePath {
|
|
qself: None,
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("std", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("string", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("String", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `<#ty as ::xso::AsXmlText>::as_xml_text`.
|
|
pub(crate) fn as_xml_text_fn(ty: Type) -> Expr {
|
|
let span = ty.span();
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: Some(QSelf {
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
ty: Box::new(ty),
|
|
position: 2,
|
|
as_token: Some(syn::token::As { span }),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("AsXmlText", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("as_xml_text", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Path`] referring to `::xso::TextCodec::<#for_ty>`,
|
|
/// returing the span of `for_ty` alongside it.
|
|
fn text_codec_of(for_ty: Type) -> (Span, Path) {
|
|
let span = for_ty.span();
|
|
(
|
|
span,
|
|
Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("TextCodec", span),
|
|
arguments: PathArguments::AngleBracketed(AngleBracketedGenericArguments {
|
|
colon2_token: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
args: [GenericArgument::Type(for_ty)].into_iter().collect(),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
)
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `::xso::TextCodec::<#for_ty>::encode`.
|
|
pub(crate) fn text_codec_encode_fn(for_ty: Type) -> Expr {
|
|
let (span, mut path) = text_codec_of(for_ty);
|
|
path.segments.push(PathSegment {
|
|
ident: Ident::new("encode", span),
|
|
arguments: PathArguments::None,
|
|
});
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: None,
|
|
path: path,
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `::xso::TextCodec::<#for_ty>::decode`.
|
|
pub(crate) fn text_codec_decode_fn(for_ty: Type) -> Expr {
|
|
let (span, mut path) = text_codec_of(for_ty);
|
|
path.segments.push(PathSegment {
|
|
ident: Ident::new("decode", span),
|
|
arguments: PathArguments::None,
|
|
});
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: None,
|
|
path: path,
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] for `&#lifetime #ty`.
|
|
pub(crate) fn ref_ty(ty: Type, lifetime: Lifetime) -> Type {
|
|
let span = ty.span();
|
|
Type::Reference(TypeReference {
|
|
and_token: token::And { spans: [span] },
|
|
lifetime: Some(lifetime),
|
|
mutability: None,
|
|
elem: Box::new(ty),
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to
|
|
/// `::core::marker::PhantomData<&#lifetime ()>`.
|
|
pub(crate) fn phantom_lifetime_ty(lifetime: Lifetime) -> Type {
|
|
let span = lifetime.span();
|
|
let dummy = Type::Tuple(TypeTuple {
|
|
paren_token: token::Paren::default(),
|
|
elems: punctuated::Punctuated::default(),
|
|
});
|
|
Type::Path(TypePath {
|
|
qself: None,
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("core", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("marker", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("PhantomData", span),
|
|
arguments: PathArguments::AngleBracketed(AngleBracketedGenericArguments {
|
|
colon2_token: None,
|
|
lt_token: token::Lt { spans: [span] },
|
|
args: [GenericArgument::Type(ref_ty(dummy, lifetime))]
|
|
.into_iter()
|
|
.collect(),
|
|
gt_token: token::Gt { spans: [span] },
|
|
}),
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::TypePath`] referring to
|
|
/// `<#of_ty as ::xso::FromXml>`.
|
|
fn from_xml_of(of_ty: Type) -> (Span, TypePath) {
|
|
let span = of_ty.span();
|
|
(
|
|
span,
|
|
TypePath {
|
|
qself: Some(QSelf {
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
ty: Box::new(of_ty),
|
|
position: 2,
|
|
as_token: Some(syn::token::As { span }),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("FromXml", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
},
|
|
)
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to
|
|
/// `<#of_ty as ::xso::FromXml>::Builder`.
|
|
pub(crate) fn from_xml_builder_ty(of_ty: Type) -> Type {
|
|
let (span, mut ty) = from_xml_of(of_ty);
|
|
ty.path.segments.push(PathSegment {
|
|
ident: Ident::new("Builder", span),
|
|
arguments: PathArguments::None,
|
|
});
|
|
Type::Path(ty)
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `<#of_ty as ::xso::FromXml>::from_events`.
|
|
pub(crate) fn from_events_fn(of_ty: Type) -> Expr {
|
|
let (span, mut ty) = from_xml_of(of_ty);
|
|
ty.path.segments.push(PathSegment {
|
|
ident: Ident::new("from_events", span),
|
|
arguments: PathArguments::None,
|
|
});
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: ty.qself,
|
|
path: ty.path,
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] which wraps the given `ty` in
|
|
/// `::core::option::Option<_>`.
|
|
pub(crate) fn option_ty(ty: Type) -> Type {
|
|
let span = ty.span();
|
|
Type::Path(TypePath {
|
|
qself: None,
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("core", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("option", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("Option", span),
|
|
arguments: PathArguments::AngleBracketed(AngleBracketedGenericArguments {
|
|
colon2_token: None,
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
args: [GenericArgument::Type(ty)].into_iter().collect(),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::TypePath`] referring to
|
|
/// `<#of_ty as ::xso::FromEventsBuilder>`.
|
|
fn from_events_builder_of(of_ty: Type) -> (Span, TypePath) {
|
|
let span = of_ty.span();
|
|
(
|
|
span,
|
|
TypePath {
|
|
qself: Some(QSelf {
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
ty: Box::new(of_ty),
|
|
position: 2,
|
|
as_token: Some(syn::token::As { span }),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("FromEventsBuilder", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
},
|
|
)
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `<#of_ty as ::xso::FromEventsBuilder>::feed`.
|
|
pub(crate) fn feed_fn(of_ty: Type) -> Expr {
|
|
let (span, mut ty) = from_events_builder_of(of_ty);
|
|
ty.path.segments.push(PathSegment {
|
|
ident: Ident::new("feed", span),
|
|
arguments: PathArguments::None,
|
|
});
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: ty.qself,
|
|
path: ty.path,
|
|
})
|
|
}
|
|
|
|
fn as_xml_of(of_ty: Type) -> (Span, TypePath) {
|
|
let span = of_ty.span();
|
|
(
|
|
span,
|
|
TypePath {
|
|
qself: Some(QSelf {
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
ty: Box::new(of_ty),
|
|
position: 2,
|
|
as_token: Some(syn::token::As { span }),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("AsXml", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
},
|
|
)
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `<#of_ty as ::xso::AsXml>::as_xml_iter`.
|
|
pub(crate) fn as_xml_iter_fn(of_ty: Type) -> Expr {
|
|
let (span, mut ty) = as_xml_of(of_ty);
|
|
ty.path.segments.push(PathSegment {
|
|
ident: Ident::new("as_xml_iter", span),
|
|
arguments: PathArguments::None,
|
|
});
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: ty.qself,
|
|
path: ty.path,
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to
|
|
/// `<#of_ty as ::xso::AsXml>::ItemIter`.
|
|
pub(crate) fn item_iter_ty(of_ty: Type, lifetime: Lifetime) -> Type {
|
|
let (span, mut ty) = as_xml_of(of_ty);
|
|
ty.path.segments.push(PathSegment {
|
|
ident: Ident::new("ItemIter", span),
|
|
arguments: PathArguments::AngleBracketed(AngleBracketedGenericArguments {
|
|
colon2_token: None,
|
|
lt_token: token::Lt { spans: [span] },
|
|
args: [GenericArgument::Lifetime(lifetime)].into_iter().collect(),
|
|
gt_token: token::Gt { spans: [span] },
|
|
}),
|
|
});
|
|
Type::Path(ty)
|
|
}
|
|
|
|
/// Construct a [`syn::TypePath`] referring to `<#of_ty as IntoIterator>`.
|
|
fn into_iterator_of(of_ty: Type) -> (Span, TypePath) {
|
|
let span = of_ty.span();
|
|
(
|
|
span,
|
|
TypePath {
|
|
qself: Some(QSelf {
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
ty: Box::new(of_ty),
|
|
position: 3,
|
|
as_token: Some(syn::token::As { span }),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("core", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("iter", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("IntoIterator", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
},
|
|
)
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to
|
|
/// `<#of_ty as IntoIterator>::IntoIter`.
|
|
pub(crate) fn into_iterator_iter_ty(of_ty: Type) -> Type {
|
|
let (span, mut ty) = into_iterator_of(of_ty);
|
|
ty.path.segments.push(PathSegment {
|
|
ident: Ident::new("IntoIter", span),
|
|
arguments: PathArguments::None,
|
|
});
|
|
Type::Path(ty)
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to
|
|
/// `<#of_ty as IntoIterator>::Item`.
|
|
pub(crate) fn into_iterator_item_ty(of_ty: Type) -> Type {
|
|
let (span, mut ty) = into_iterator_of(of_ty);
|
|
ty.path.segments.push(PathSegment {
|
|
ident: Ident::new("Item", span),
|
|
arguments: PathArguments::None,
|
|
});
|
|
Type::Path(ty)
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `<#of_ty as IntoIterator>::into_iter`.
|
|
pub(crate) fn into_iterator_into_iter_fn(of_ty: Type) -> Expr {
|
|
let (span, mut ty) = into_iterator_of(of_ty);
|
|
ty.path.segments.push(PathSegment {
|
|
ident: Ident::new("into_iter", span),
|
|
arguments: PathArguments::None,
|
|
});
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: ty.qself,
|
|
path: ty.path,
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Expr`] referring to
|
|
/// `<#of_ty as ::core::iter::Extend>::extend`.
|
|
pub(crate) fn extend_fn(of_ty: Type, item_ty: Type) -> Expr {
|
|
let span = of_ty.span();
|
|
Expr::Path(ExprPath {
|
|
attrs: Vec::new(),
|
|
qself: Some(QSelf {
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
ty: Box::new(of_ty),
|
|
position: 3,
|
|
as_token: Some(syn::token::As { span }),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("core", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("iter", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("Extend", span),
|
|
arguments: PathArguments::AngleBracketed(AngleBracketedGenericArguments {
|
|
colon2_token: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
lt_token: syn::token::Lt { spans: [span] },
|
|
args: [GenericArgument::Type(item_ty)].into_iter().collect(),
|
|
gt_token: syn::token::Gt { spans: [span] },
|
|
}),
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("extend", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::TypePath`] which references the given type name.
|
|
pub(crate) fn ty_from_ident(ident: Ident) -> TypePath {
|
|
TypePath {
|
|
qself: None,
|
|
path: ident.into(),
|
|
}
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to `xso::OptionAsXml<#inner_ty>`.
|
|
pub(crate) fn option_as_xml_ty(inner_ty: Type) -> Type {
|
|
let span = inner_ty.span();
|
|
Type::Path(TypePath {
|
|
qself: None,
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("asxml", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("OptionAsXml", span),
|
|
arguments: PathArguments::AngleBracketed(AngleBracketedGenericArguments {
|
|
colon2_token: None,
|
|
lt_token: token::Lt { spans: [span] },
|
|
args: [GenericArgument::Type(inner_ty)].into_iter().collect(),
|
|
gt_token: token::Gt { spans: [span] },
|
|
}),
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|
|
|
|
/// Construct a [`syn::Type`] referring to `::xso::exports::minidom::Element`.
|
|
#[cfg(feature = "minidom")]
|
|
pub(crate) fn element_ty(span: Span) -> Type {
|
|
Type::Path(TypePath {
|
|
qself: None,
|
|
path: Path {
|
|
leading_colon: Some(syn::token::PathSep {
|
|
spans: [span, span],
|
|
}),
|
|
segments: [
|
|
PathSegment {
|
|
ident: Ident::new("xso", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("exports", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("minidom", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
PathSegment {
|
|
ident: Ident::new("Element", span),
|
|
arguments: PathArguments::None,
|
|
},
|
|
]
|
|
.into_iter()
|
|
.collect(),
|
|
},
|
|
})
|
|
}
|