add tests
This commit is contained in:
@@ -159,14 +159,13 @@ impl<Arguments> ValidationContext<Arguments> {
|
|||||||
|
|
||||||
/// # Arguments
|
/// # Arguments
|
||||||
///
|
///
|
||||||
/// `T`: data type to validate
|
/// * `T`: The data type to validate using arguments
|
||||||
/// `Self::A`: dependent arguments
|
|
||||||
///
|
///
|
||||||
pub trait Arguments<'a, T>
|
pub trait Arguments<'a, T>
|
||||||
where
|
where
|
||||||
T: ValidateArgs<'a>,
|
T: ValidateArgs<'a>,
|
||||||
{
|
{
|
||||||
/// Get dependent arguments
|
/// Get arguments from `self`
|
||||||
fn get(&'a self) -> T::Args;
|
fn get(&'a self) -> T::Args;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
388
src/test.rs
388
src/test.rs
@@ -1,3 +1,4 @@
|
|||||||
|
use crate::test::extra_typed_path::TypedPathParamExValidationArguments;
|
||||||
use crate::tests::{ValidTest, ValidTestParameter};
|
use crate::tests::{ValidTest, ValidTestParameter};
|
||||||
use crate::{Arguments, HasValidate, Valid, ValidEx, ValidationContext, VALIDATION_ERROR_STATUS};
|
use crate::{Arguments, HasValidate, Valid, ValidEx, ValidationContext, VALIDATION_ERROR_STATUS};
|
||||||
use axum::extract::{FromRef, Path, Query};
|
use axum::extract::{FromRef, Path, Query};
|
||||||
@@ -109,32 +110,37 @@ impl HasValidate for Parameters {
|
|||||||
|
|
||||||
#[derive(Debug, Clone, FromRef)]
|
#[derive(Debug, Clone, FromRef)]
|
||||||
struct MyState {
|
struct MyState {
|
||||||
validation_ctx: ValidationContext<ParametersExValidationArguments>,
|
param_validation_ctx: ValidationContext<ParametersExValidationArguments>,
|
||||||
|
typed_path_validation_ctx: ValidationContext<TypedPathParamExValidationArguments>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[tokio::test]
|
#[tokio::test]
|
||||||
async fn test_main() -> anyhow::Result<()> {
|
async fn test_main() -> anyhow::Result<()> {
|
||||||
|
let state = MyState {
|
||||||
|
param_validation_ctx: ValidationContext::<ParametersExValidationArguments>::default(),
|
||||||
|
typed_path_validation_ctx:
|
||||||
|
ValidationContext::<TypedPathParamExValidationArguments>::default(),
|
||||||
|
};
|
||||||
|
|
||||||
let router = Router::new()
|
let router = Router::new()
|
||||||
.route(route::PATH, get(extract_path))
|
.route(route::PATH, get(extract_path))
|
||||||
.route(route::QUERY, get(extract_query))
|
.route(route::QUERY, get(extract_query))
|
||||||
.route(route::FORM, post(extract_form))
|
.route(route::FORM, post(extract_form))
|
||||||
.route(route::JSON, post(extract_json));
|
.route(route::JSON, post(extract_json))
|
||||||
|
|
||||||
let router_ex = Router::new()
|
|
||||||
.route(route::QUERY_EX, get(extract_query_ex))
|
.route(route::QUERY_EX, get(extract_query_ex))
|
||||||
.route(route::FORM_EX, post(extract_form_ex))
|
.route(route::FORM_EX, post(extract_form_ex))
|
||||||
.route(route::JSON_EX, post(extract_json_ex))
|
.route(route::JSON_EX, post(extract_json_ex));
|
||||||
.with_state(MyState {
|
|
||||||
validation_ctx: ValidationContext::<ParametersExValidationArguments>::default(),
|
|
||||||
});
|
|
||||||
|
|
||||||
let router = router.merge(router_ex);
|
|
||||||
|
|
||||||
#[cfg(feature = "typed_header")]
|
#[cfg(feature = "typed_header")]
|
||||||
let router = router.route(
|
let router = router
|
||||||
typed_header::route::TYPED_HEADER,
|
.route(
|
||||||
post(typed_header::extract_typed_header),
|
typed_header::route::TYPED_HEADER,
|
||||||
);
|
post(typed_header::extract_typed_header),
|
||||||
|
)
|
||||||
|
.route(
|
||||||
|
typed_header::route::TYPED_HEADER_EX,
|
||||||
|
post(typed_header::extract_typed_header_ex),
|
||||||
|
);
|
||||||
|
|
||||||
#[cfg(feature = "typed_multipart")]
|
#[cfg(feature = "typed_multipart")]
|
||||||
let router = router
|
let router = router
|
||||||
@@ -142,9 +148,17 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
typed_multipart::route::TYPED_MULTIPART,
|
typed_multipart::route::TYPED_MULTIPART,
|
||||||
post(typed_multipart::extract_typed_multipart),
|
post(typed_multipart::extract_typed_multipart),
|
||||||
)
|
)
|
||||||
|
.route(
|
||||||
|
typed_multipart::route::TYPED_MULTIPART_EX,
|
||||||
|
post(typed_multipart::extract_typed_multipart_ex),
|
||||||
|
)
|
||||||
.route(
|
.route(
|
||||||
typed_multipart::route::BASE_MULTIPART,
|
typed_multipart::route::BASE_MULTIPART,
|
||||||
post(typed_multipart::extract_base_multipart),
|
post(typed_multipart::extract_base_multipart),
|
||||||
|
)
|
||||||
|
.route(
|
||||||
|
typed_multipart::route::BASE_MULTIPART_EX,
|
||||||
|
post(typed_multipart::extract_base_multipart_ex),
|
||||||
);
|
);
|
||||||
|
|
||||||
#[cfg(feature = "extra")]
|
#[cfg(feature = "extra")]
|
||||||
@@ -160,40 +174,72 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
);
|
);
|
||||||
|
|
||||||
#[cfg(feature = "extra_typed_path")]
|
#[cfg(feature = "extra_typed_path")]
|
||||||
let router = router.route(
|
let router = router
|
||||||
extra_typed_path::route::EXTRA_TYPED_PATH,
|
.route(
|
||||||
get(extra_typed_path::extract_extra_typed_path),
|
extra_typed_path::route::EXTRA_TYPED_PATH,
|
||||||
);
|
get(extra_typed_path::extract_extra_typed_path),
|
||||||
|
)
|
||||||
|
.route(
|
||||||
|
extra_typed_path::route::EXTRA_TYPED_PATH_EX,
|
||||||
|
get(extra_typed_path::extract_extra_typed_path_ex),
|
||||||
|
);
|
||||||
|
|
||||||
#[cfg(feature = "extra_query")]
|
#[cfg(feature = "extra_query")]
|
||||||
let router = router.route(
|
let router = router
|
||||||
extra_query::route::EXTRA_QUERY,
|
.route(
|
||||||
post(extra_query::extract_extra_query),
|
extra_query::route::EXTRA_QUERY,
|
||||||
);
|
post(extra_query::extract_extra_query),
|
||||||
|
)
|
||||||
|
.route(
|
||||||
|
extra_query::route::EXTRA_QUERY_EX,
|
||||||
|
post(extra_query::extract_extra_query_ex),
|
||||||
|
);
|
||||||
|
|
||||||
#[cfg(feature = "extra_form")]
|
#[cfg(feature = "extra_form")]
|
||||||
let router = router.route(
|
let router = router
|
||||||
extra_form::route::EXTRA_FORM,
|
.route(
|
||||||
post(extra_form::extract_extra_form),
|
extra_form::route::EXTRA_FORM,
|
||||||
);
|
post(extra_form::extract_extra_form),
|
||||||
|
)
|
||||||
|
.route(
|
||||||
|
extra_form::route::EXTRA_FORM_EX,
|
||||||
|
post(extra_form::extract_extra_form_ex),
|
||||||
|
);
|
||||||
|
|
||||||
#[cfg(feature = "extra_protobuf")]
|
#[cfg(feature = "extra_protobuf")]
|
||||||
let router = router.route(
|
let router = router
|
||||||
extra_protobuf::route::EXTRA_PROTOBUF,
|
.route(
|
||||||
post(extra_protobuf::extract_extra_protobuf),
|
extra_protobuf::route::EXTRA_PROTOBUF,
|
||||||
);
|
post(extra_protobuf::extract_extra_protobuf),
|
||||||
|
)
|
||||||
|
.route(
|
||||||
|
extra_protobuf::route::EXTRA_PROTOBUF_EX,
|
||||||
|
post(extra_protobuf::extract_extra_protobuf_ex),
|
||||||
|
);
|
||||||
|
|
||||||
#[cfg(feature = "yaml")]
|
#[cfg(feature = "yaml")]
|
||||||
let router = router.route(yaml::route::YAML, post(yaml::extract_yaml));
|
let router = router
|
||||||
|
.route(yaml::route::YAML, post(yaml::extract_yaml))
|
||||||
|
.route(yaml::route::YAML_EX, post(yaml::extract_yaml_ex));
|
||||||
|
|
||||||
#[cfg(feature = "msgpack")]
|
#[cfg(feature = "msgpack")]
|
||||||
let router = router
|
let router = router
|
||||||
.route(msgpack::route::MSGPACK, post(msgpack::extract_msgpack))
|
.route(msgpack::route::MSGPACK, post(msgpack::extract_msgpack))
|
||||||
|
.route(
|
||||||
|
msgpack::route::MSGPACK_EX,
|
||||||
|
post(msgpack::extract_msgpack_ex),
|
||||||
|
)
|
||||||
.route(
|
.route(
|
||||||
msgpack::route::MSGPACK_RAW,
|
msgpack::route::MSGPACK_RAW,
|
||||||
post(msgpack::extract_msgpack_raw),
|
post(msgpack::extract_msgpack_raw),
|
||||||
|
)
|
||||||
|
.route(
|
||||||
|
msgpack::route::MSGPACK_RAW_EX,
|
||||||
|
post(msgpack::extract_msgpack_raw_ex),
|
||||||
);
|
);
|
||||||
|
|
||||||
|
let router = router.with_state(state);
|
||||||
|
|
||||||
let server = axum::Server::bind(&SocketAddr::from(([0u8, 0, 0, 0], 0u16)))
|
let server = axum::Server::bind(&SocketAddr::from(([0u8, 0, 0, 0], 0u16)))
|
||||||
.serve(router.into_make_service());
|
.serve(router.into_make_service());
|
||||||
let server_addr = server.local_addr();
|
let server_addr = server.local_addr();
|
||||||
@@ -288,26 +334,52 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
#[cfg(feature = "typed_header")]
|
#[cfg(feature = "typed_header")]
|
||||||
{
|
{
|
||||||
use axum::TypedHeader;
|
use axum::TypedHeader;
|
||||||
|
// Valid
|
||||||
test_executor
|
test_executor
|
||||||
.execute::<TypedHeader<Parameters>>(Method::POST, typed_header::route::TYPED_HEADER)
|
.execute::<TypedHeader<Parameters>>(Method::POST, typed_header::route::TYPED_HEADER)
|
||||||
.await?;
|
.await?;
|
||||||
|
|
||||||
|
// ValidEx
|
||||||
|
test_executor
|
||||||
|
.execute::<TypedHeader<Parameters>>(Method::POST, typed_header::route::TYPED_HEADER_EX)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "typed_multipart")]
|
#[cfg(feature = "typed_multipart")]
|
||||||
{
|
{
|
||||||
use axum_typed_multipart::{BaseMultipart, TypedMultipart, TypedMultipartError};
|
use axum_typed_multipart::{BaseMultipart, TypedMultipart, TypedMultipartError};
|
||||||
|
|
||||||
|
// Valid
|
||||||
test_executor
|
test_executor
|
||||||
.execute::<BaseMultipart<Parameters, TypedMultipartError>>(
|
.execute::<BaseMultipart<Parameters, TypedMultipartError>>(
|
||||||
Method::POST,
|
Method::POST,
|
||||||
typed_multipart::route::BASE_MULTIPART,
|
typed_multipart::route::BASE_MULTIPART,
|
||||||
)
|
)
|
||||||
.await?;
|
.await?;
|
||||||
|
|
||||||
|
// ValidEx
|
||||||
|
test_executor
|
||||||
|
.execute::<BaseMultipart<Parameters, TypedMultipartError>>(
|
||||||
|
Method::POST,
|
||||||
|
typed_multipart::route::BASE_MULTIPART_EX,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
|
// Valid
|
||||||
test_executor
|
test_executor
|
||||||
.execute::<TypedMultipart<Parameters>>(
|
.execute::<TypedMultipart<Parameters>>(
|
||||||
Method::POST,
|
Method::POST,
|
||||||
typed_multipart::route::TYPED_MULTIPART,
|
typed_multipart::route::TYPED_MULTIPART,
|
||||||
)
|
)
|
||||||
.await?;
|
.await?;
|
||||||
|
|
||||||
|
// ValidEx
|
||||||
|
test_executor
|
||||||
|
.execute::<TypedMultipart<Parameters>>(
|
||||||
|
Method::POST,
|
||||||
|
typed_multipart::route::TYPED_MULTIPART_EX,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "extra")]
|
#[cfg(feature = "extra")]
|
||||||
@@ -335,12 +407,16 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
|
|
||||||
#[cfg(feature = "extra_typed_path")]
|
#[cfg(feature = "extra_typed_path")]
|
||||||
{
|
{
|
||||||
{
|
async fn test_extra_typed_path(
|
||||||
|
test_executor: &TestExecutor,
|
||||||
|
route: &str,
|
||||||
|
server_url: &str,
|
||||||
|
) -> anyhow::Result<()> {
|
||||||
let extra_typed_path_type_name = "T: TypedPath";
|
let extra_typed_path_type_name = "T: TypedPath";
|
||||||
let valid_extra_typed_path_response = test_executor
|
let valid_extra_typed_path_response = test_executor
|
||||||
.client()
|
.client()
|
||||||
.get(format!(
|
.get(format!(
|
||||||
"{}/extra_typed_path/{}/{}",
|
"{}/{route}/{}/{}",
|
||||||
server_url, VALID_PARAMETERS.v0, VALID_PARAMETERS.v1
|
server_url, VALID_PARAMETERS.v0, VALID_PARAMETERS.v1
|
||||||
))
|
))
|
||||||
.send()
|
.send()
|
||||||
@@ -354,7 +430,7 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
|
|
||||||
let error_extra_typed_path_response = test_executor
|
let error_extra_typed_path_response = test_executor
|
||||||
.client()
|
.client()
|
||||||
.get(format!("{}/extra_typed_path/not_i32/path", server_url))
|
.get(format!("{}/{route}/not_i32/path", server_url))
|
||||||
.send()
|
.send()
|
||||||
.await?;
|
.await?;
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
@@ -367,7 +443,7 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
let invalid_extra_typed_path_response = test_executor
|
let invalid_extra_typed_path_response = test_executor
|
||||||
.client()
|
.client()
|
||||||
.get(format!(
|
.get(format!(
|
||||||
"{}/extra_typed_path/{}/{}",
|
"{}/{route}/{}/{}",
|
||||||
server_url, INVALID_PARAMETERS.v0, INVALID_PARAMETERS.v1
|
server_url, INVALID_PARAMETERS.v0, INVALID_PARAMETERS.v1
|
||||||
))
|
))
|
||||||
.send()
|
.send()
|
||||||
@@ -385,7 +461,11 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
)
|
)
|
||||||
.await;
|
.await;
|
||||||
println!("All {} tests passed.", extra_typed_path_type_name);
|
println!("All {} tests passed.", extra_typed_path_type_name);
|
||||||
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
test_extra_typed_path(&test_executor, "extra_typed_path", &server_url).await?;
|
||||||
|
test_extra_typed_path(&test_executor, "extra_typed_path_ex", &server_url).await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "extra_query")]
|
#[cfg(feature = "extra_query")]
|
||||||
@@ -394,6 +474,9 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
test_executor
|
test_executor
|
||||||
.execute::<Query<Parameters>>(Method::POST, extra_query::route::EXTRA_QUERY)
|
.execute::<Query<Parameters>>(Method::POST, extra_query::route::EXTRA_QUERY)
|
||||||
.await?;
|
.await?;
|
||||||
|
test_executor
|
||||||
|
.execute::<Query<Parameters>>(Method::POST, extra_query::route::EXTRA_QUERY_EX)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "extra_form")]
|
#[cfg(feature = "extra_form")]
|
||||||
@@ -402,6 +485,9 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
test_executor
|
test_executor
|
||||||
.execute::<Form<Parameters>>(Method::POST, extra_form::route::EXTRA_FORM)
|
.execute::<Form<Parameters>>(Method::POST, extra_form::route::EXTRA_FORM)
|
||||||
.await?;
|
.await?;
|
||||||
|
test_executor
|
||||||
|
.execute::<Form<Parameters>>(Method::POST, extra_form::route::EXTRA_FORM_EX)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "extra_protobuf")]
|
#[cfg(feature = "extra_protobuf")]
|
||||||
@@ -410,6 +496,9 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
test_executor
|
test_executor
|
||||||
.execute::<Protobuf<Parameters>>(Method::POST, extra_protobuf::route::EXTRA_PROTOBUF)
|
.execute::<Protobuf<Parameters>>(Method::POST, extra_protobuf::route::EXTRA_PROTOBUF)
|
||||||
.await?;
|
.await?;
|
||||||
|
test_executor
|
||||||
|
.execute::<Protobuf<Parameters>>(Method::POST, extra_protobuf::route::EXTRA_PROTOBUF_EX)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "yaml")]
|
#[cfg(feature = "yaml")]
|
||||||
@@ -418,6 +507,9 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
test_executor
|
test_executor
|
||||||
.execute::<Yaml<Parameters>>(Method::POST, yaml::route::YAML)
|
.execute::<Yaml<Parameters>>(Method::POST, yaml::route::YAML)
|
||||||
.await?;
|
.await?;
|
||||||
|
test_executor
|
||||||
|
.execute::<Yaml<Parameters>>(Method::POST, yaml::route::YAML_EX)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "msgpack")]
|
#[cfg(feature = "msgpack")]
|
||||||
@@ -426,9 +518,15 @@ async fn test_main() -> anyhow::Result<()> {
|
|||||||
test_executor
|
test_executor
|
||||||
.execute::<MsgPack<Parameters>>(Method::POST, msgpack::route::MSGPACK)
|
.execute::<MsgPack<Parameters>>(Method::POST, msgpack::route::MSGPACK)
|
||||||
.await?;
|
.await?;
|
||||||
|
test_executor
|
||||||
|
.execute::<MsgPack<Parameters>>(Method::POST, msgpack::route::MSGPACK_EX)
|
||||||
|
.await?;
|
||||||
test_executor
|
test_executor
|
||||||
.execute::<MsgPackRaw<Parameters>>(Method::POST, msgpack::route::MSGPACK_RAW)
|
.execute::<MsgPackRaw<Parameters>>(Method::POST, msgpack::route::MSGPACK_RAW)
|
||||||
.await?;
|
.await?;
|
||||||
|
test_executor
|
||||||
|
.execute::<MsgPackRaw<Parameters>>(Method::POST, msgpack::route::MSGPACK_RAW_EX)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
drop(server_guard);
|
drop(server_guard);
|
||||||
@@ -589,10 +687,12 @@ mod typed_header {
|
|||||||
|
|
||||||
pub(crate) mod route {
|
pub(crate) mod route {
|
||||||
pub const TYPED_HEADER: &str = "/typed_header";
|
pub const TYPED_HEADER: &str = "/typed_header";
|
||||||
|
pub const TYPED_HEADER_EX: &str = "/typed_header_ex";
|
||||||
}
|
}
|
||||||
|
|
||||||
use super::{validate_again, Parameters};
|
use super::{validate_again, Parameters};
|
||||||
use crate::Valid;
|
use crate::test::{validate_again_ex, ParametersEx, ParametersExValidationArguments};
|
||||||
|
use crate::{Arguments, Valid, ValidEx};
|
||||||
use axum::headers::{Error, Header, HeaderName, HeaderValue};
|
use axum::headers::{Error, Header, HeaderName, HeaderValue};
|
||||||
use axum::http::StatusCode;
|
use axum::http::StatusCode;
|
||||||
use axum::TypedHeader;
|
use axum::TypedHeader;
|
||||||
@@ -605,6 +705,15 @@ mod typed_header {
|
|||||||
validate_again(parameters)
|
validate_again(parameters)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub(super) async fn extract_typed_header_ex(
|
||||||
|
ValidEx(TypedHeader(parameters), args): ValidEx<
|
||||||
|
TypedHeader<ParametersEx>,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
>,
|
||||||
|
) -> StatusCode {
|
||||||
|
validate_again_ex(parameters, args.get())
|
||||||
|
}
|
||||||
|
|
||||||
impl Header for Parameters {
|
impl Header for Parameters {
|
||||||
fn name() -> &'static HeaderName {
|
fn name() -> &'static HeaderName {
|
||||||
&AXUM_VALID_PARAMETERS
|
&AXUM_VALID_PARAMETERS
|
||||||
@@ -638,6 +747,39 @@ mod typed_header {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Header for ParametersEx {
|
||||||
|
fn name() -> &'static HeaderName {
|
||||||
|
&AXUM_VALID_PARAMETERS
|
||||||
|
}
|
||||||
|
|
||||||
|
fn decode<'i, I>(values: &mut I) -> Result<Self, Error>
|
||||||
|
where
|
||||||
|
Self: Sized,
|
||||||
|
I: Iterator<Item = &'i HeaderValue>,
|
||||||
|
{
|
||||||
|
let value = values.next().ok_or_else(Error::invalid)?;
|
||||||
|
let src = std::str::from_utf8(value.as_bytes()).map_err(|_| Error::invalid())?;
|
||||||
|
let split = src.split(',').collect::<Vec<_>>();
|
||||||
|
match split.as_slice() {
|
||||||
|
[v0, v1] => Ok(ParametersEx {
|
||||||
|
v0: v0.parse().map_err(|_| Error::invalid())?,
|
||||||
|
v1: v1.to_string(),
|
||||||
|
}),
|
||||||
|
_ => Err(Error::invalid()),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn encode<E: Extend<HeaderValue>>(&self, values: &mut E) {
|
||||||
|
let v0 = self.v0.to_string();
|
||||||
|
let mut vec = Vec::with_capacity(v0.len() + 1 + self.v1.len());
|
||||||
|
vec.extend_from_slice(v0.as_bytes());
|
||||||
|
vec.push(b',');
|
||||||
|
vec.extend_from_slice(self.v1.as_bytes());
|
||||||
|
let value = HeaderValue::from_bytes(&vec).expect("Failed to build header");
|
||||||
|
values.extend(::std::iter::once(value));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn parameter_is_header() -> anyhow::Result<()> {
|
fn parameter_is_header() -> anyhow::Result<()> {
|
||||||
let parameter = Parameters {
|
let parameter = Parameters {
|
||||||
@@ -654,14 +796,19 @@ mod typed_header {
|
|||||||
|
|
||||||
#[cfg(feature = "typed_multipart")]
|
#[cfg(feature = "typed_multipart")]
|
||||||
mod typed_multipart {
|
mod typed_multipart {
|
||||||
use crate::test::{validate_again, Parameters};
|
use crate::test::{
|
||||||
use crate::Valid;
|
validate_again, validate_again_ex, Parameters, ParametersEx,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
};
|
||||||
|
use crate::{Arguments, Valid, ValidEx};
|
||||||
use axum::http::StatusCode;
|
use axum::http::StatusCode;
|
||||||
use axum_typed_multipart::{BaseMultipart, TypedMultipart, TypedMultipartError};
|
use axum_typed_multipart::{BaseMultipart, TypedMultipart, TypedMultipartError};
|
||||||
|
|
||||||
pub mod route {
|
pub mod route {
|
||||||
pub const TYPED_MULTIPART: &str = "/typed_multipart";
|
pub const TYPED_MULTIPART: &str = "/typed_multipart";
|
||||||
|
pub const TYPED_MULTIPART_EX: &str = "/typed_multipart_ex";
|
||||||
pub const BASE_MULTIPART: &str = "/base_multipart";
|
pub const BASE_MULTIPART: &str = "/base_multipart";
|
||||||
|
pub const BASE_MULTIPART_EX: &str = "/base_multipart_ex";
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<&Parameters> for reqwest::multipart::Form {
|
impl From<&Parameters> for reqwest::multipart::Form {
|
||||||
@@ -678,11 +825,29 @@ mod typed_multipart {
|
|||||||
validate_again(parameters)
|
validate_again(parameters)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub(super) async fn extract_typed_multipart_ex(
|
||||||
|
ValidEx(TypedMultipart(parameters), args): ValidEx<
|
||||||
|
TypedMultipart<ParametersEx>,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
>,
|
||||||
|
) -> StatusCode {
|
||||||
|
validate_again_ex(parameters, args.get())
|
||||||
|
}
|
||||||
|
|
||||||
pub(super) async fn extract_base_multipart(
|
pub(super) async fn extract_base_multipart(
|
||||||
Valid(BaseMultipart { data, .. }): Valid<BaseMultipart<Parameters, TypedMultipartError>>,
|
Valid(BaseMultipart { data, .. }): Valid<BaseMultipart<Parameters, TypedMultipartError>>,
|
||||||
) -> StatusCode {
|
) -> StatusCode {
|
||||||
validate_again(data)
|
validate_again(data)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub(super) async fn extract_base_multipart_ex(
|
||||||
|
ValidEx(BaseMultipart { data, .. }, args): ValidEx<
|
||||||
|
BaseMultipart<ParametersEx, TypedMultipartError>,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
>,
|
||||||
|
) -> StatusCode {
|
||||||
|
validate_again_ex(data, args.get())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "extra")]
|
#[cfg(feature = "extra")]
|
||||||
@@ -837,15 +1002,17 @@ mod extra {
|
|||||||
|
|
||||||
#[cfg(feature = "extra_typed_path")]
|
#[cfg(feature = "extra_typed_path")]
|
||||||
mod extra_typed_path {
|
mod extra_typed_path {
|
||||||
use crate::test::validate_again;
|
use crate::test::{validate_again, validate_again_ex};
|
||||||
use crate::{HasValidate, Valid};
|
use crate::{Arguments, HasValidate, HasValidateArgs, Valid, ValidEx};
|
||||||
use axum::http::StatusCode;
|
use axum::http::StatusCode;
|
||||||
use axum_extra::routing::TypedPath;
|
use axum_extra::routing::TypedPath;
|
||||||
use serde::Deserialize;
|
use serde::Deserialize;
|
||||||
use validator::Validate;
|
use std::ops::RangeInclusive;
|
||||||
|
use validator::{Validate, ValidateArgs};
|
||||||
|
|
||||||
pub mod route {
|
pub mod route {
|
||||||
pub const EXTRA_TYPED_PATH: &str = "/extra_typed_path/:v0/:v1";
|
pub const EXTRA_TYPED_PATH: &str = "/extra_typed_path/:v0/:v1";
|
||||||
|
pub const EXTRA_TYPED_PATH_EX: &str = "/extra_typed_path_ex/:v0/:v1";
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Validate, TypedPath, Deserialize)]
|
#[derive(Validate, TypedPath, Deserialize)]
|
||||||
@@ -868,17 +1035,65 @@ mod extra_typed_path {
|
|||||||
pub async fn extract_extra_typed_path(Valid(param): Valid<TypedPathParam>) -> StatusCode {
|
pub async fn extract_extra_typed_path(Valid(param): Valid<TypedPathParam>) -> StatusCode {
|
||||||
validate_again(param)
|
validate_again(param)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Validate, TypedPath, Deserialize)]
|
||||||
|
#[typed_path("/extra_typed_path_ex/:v0/:v1")]
|
||||||
|
pub struct TypedPathParamEx {
|
||||||
|
#[validate(custom(function = "super::validate_v0", arg = "&'v_a RangeInclusive<i32>"))]
|
||||||
|
v0: i32,
|
||||||
|
#[validate(custom(function = "super::validate_v1", arg = "&'v_a RangeInclusive<usize>"))]
|
||||||
|
v1: String,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'v> HasValidateArgs<'v> for TypedPathParamEx {
|
||||||
|
type ValidateArgs = Self;
|
||||||
|
|
||||||
|
fn get_validate_args(&self) -> &Self::ValidateArgs {
|
||||||
|
self
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
pub struct TypedPathParamExValidationArguments {
|
||||||
|
v0_range: RangeInclusive<i32>,
|
||||||
|
v1_length_range: RangeInclusive<usize>,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Default for TypedPathParamExValidationArguments {
|
||||||
|
fn default() -> Self {
|
||||||
|
Self {
|
||||||
|
v0_range: 5..=10,
|
||||||
|
v1_length_range: 1..=10,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> Arguments<'a, TypedPathParamEx> for TypedPathParamExValidationArguments {
|
||||||
|
fn get(&'a self) -> <TypedPathParamEx as ValidateArgs<'a>>::Args {
|
||||||
|
(&self.v0_range, &self.v1_length_range)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub async fn extract_extra_typed_path_ex(
|
||||||
|
ValidEx(param, args): ValidEx<TypedPathParamEx, TypedPathParamExValidationArguments>,
|
||||||
|
) -> StatusCode {
|
||||||
|
validate_again_ex(param, args.get())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "extra_query")]
|
#[cfg(feature = "extra_query")]
|
||||||
mod extra_query {
|
mod extra_query {
|
||||||
use crate::test::{validate_again, Parameters};
|
use crate::test::{
|
||||||
use crate::Valid;
|
validate_again, validate_again_ex, Parameters, ParametersEx,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
};
|
||||||
|
use crate::{Arguments, Valid, ValidEx};
|
||||||
use axum::http::StatusCode;
|
use axum::http::StatusCode;
|
||||||
use axum_extra::extract::Query;
|
use axum_extra::extract::Query;
|
||||||
|
|
||||||
pub mod route {
|
pub mod route {
|
||||||
pub const EXTRA_QUERY: &str = "/extra_query";
|
pub const EXTRA_QUERY: &str = "/extra_query";
|
||||||
|
pub const EXTRA_QUERY_EX: &str = "/extra_query_ex";
|
||||||
}
|
}
|
||||||
|
|
||||||
pub async fn extract_extra_query(
|
pub async fn extract_extra_query(
|
||||||
@@ -886,17 +1101,30 @@ mod extra_query {
|
|||||||
) -> StatusCode {
|
) -> StatusCode {
|
||||||
validate_again(parameters)
|
validate_again(parameters)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub async fn extract_extra_query_ex(
|
||||||
|
ValidEx(Query(parameters), args): ValidEx<
|
||||||
|
Query<ParametersEx>,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
>,
|
||||||
|
) -> StatusCode {
|
||||||
|
validate_again_ex(parameters, args.get())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "extra_form")]
|
#[cfg(feature = "extra_form")]
|
||||||
mod extra_form {
|
mod extra_form {
|
||||||
use crate::test::{validate_again, Parameters};
|
use crate::test::{
|
||||||
use crate::Valid;
|
validate_again, validate_again_ex, Parameters, ParametersEx,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
};
|
||||||
|
use crate::{Arguments, Valid, ValidEx};
|
||||||
use axum::http::StatusCode;
|
use axum::http::StatusCode;
|
||||||
use axum_extra::extract::Form;
|
use axum_extra::extract::Form;
|
||||||
|
|
||||||
pub mod route {
|
pub mod route {
|
||||||
pub const EXTRA_FORM: &str = "/extra_form";
|
pub const EXTRA_FORM: &str = "/extra_form";
|
||||||
|
pub const EXTRA_FORM_EX: &str = "/extra_form_ex";
|
||||||
}
|
}
|
||||||
|
|
||||||
pub async fn extract_extra_form(
|
pub async fn extract_extra_form(
|
||||||
@@ -904,17 +1132,30 @@ mod extra_form {
|
|||||||
) -> StatusCode {
|
) -> StatusCode {
|
||||||
validate_again(parameters)
|
validate_again(parameters)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub async fn extract_extra_form_ex(
|
||||||
|
ValidEx(Form(parameters), args): ValidEx<
|
||||||
|
Form<ParametersEx>,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
>,
|
||||||
|
) -> StatusCode {
|
||||||
|
validate_again_ex(parameters, args.get())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "extra_protobuf")]
|
#[cfg(feature = "extra_protobuf")]
|
||||||
mod extra_protobuf {
|
mod extra_protobuf {
|
||||||
use crate::test::{validate_again, Parameters};
|
use crate::test::{
|
||||||
use crate::Valid;
|
validate_again, validate_again_ex, Parameters, ParametersEx,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
};
|
||||||
|
use crate::{Arguments, Valid, ValidEx};
|
||||||
use axum::http::StatusCode;
|
use axum::http::StatusCode;
|
||||||
use axum_extra::protobuf::Protobuf;
|
use axum_extra::protobuf::Protobuf;
|
||||||
|
|
||||||
pub mod route {
|
pub mod route {
|
||||||
pub const EXTRA_PROTOBUF: &str = "/extra_protobuf";
|
pub const EXTRA_PROTOBUF: &str = "/extra_protobuf";
|
||||||
|
pub const EXTRA_PROTOBUF_EX: &str = "/extra_protobuf_ex";
|
||||||
}
|
}
|
||||||
|
|
||||||
pub async fn extract_extra_protobuf(
|
pub async fn extract_extra_protobuf(
|
||||||
@@ -922,34 +1163,61 @@ mod extra_protobuf {
|
|||||||
) -> StatusCode {
|
) -> StatusCode {
|
||||||
validate_again(parameters)
|
validate_again(parameters)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub async fn extract_extra_protobuf_ex(
|
||||||
|
ValidEx(Protobuf(parameters), args): ValidEx<
|
||||||
|
Protobuf<ParametersEx>,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
>,
|
||||||
|
) -> StatusCode {
|
||||||
|
validate_again_ex(parameters, args.get())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "yaml")]
|
#[cfg(feature = "yaml")]
|
||||||
mod yaml {
|
mod yaml {
|
||||||
use crate::test::{validate_again, Parameters};
|
use crate::test::{
|
||||||
use crate::Valid;
|
validate_again, validate_again_ex, Parameters, ParametersEx,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
};
|
||||||
|
use crate::{Arguments, Valid, ValidEx};
|
||||||
use axum::http::StatusCode;
|
use axum::http::StatusCode;
|
||||||
use axum_yaml::Yaml;
|
use axum_yaml::Yaml;
|
||||||
|
|
||||||
pub mod route {
|
pub mod route {
|
||||||
pub const YAML: &str = "/yaml";
|
pub const YAML: &str = "/yaml";
|
||||||
|
pub const YAML_EX: &str = "/yaml_ex";
|
||||||
}
|
}
|
||||||
|
|
||||||
pub async fn extract_yaml(Valid(Yaml(parameters)): Valid<Yaml<Parameters>>) -> StatusCode {
|
pub async fn extract_yaml(Valid(Yaml(parameters)): Valid<Yaml<Parameters>>) -> StatusCode {
|
||||||
validate_again(parameters)
|
validate_again(parameters)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub async fn extract_yaml_ex(
|
||||||
|
ValidEx(Yaml(parameters), args): ValidEx<
|
||||||
|
Yaml<ParametersEx>,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
>,
|
||||||
|
) -> StatusCode {
|
||||||
|
validate_again_ex(parameters, args.get())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "msgpack")]
|
#[cfg(feature = "msgpack")]
|
||||||
mod msgpack {
|
mod msgpack {
|
||||||
use crate::test::{validate_again, Parameters};
|
use crate::test::{
|
||||||
use crate::Valid;
|
validate_again, validate_again_ex, Parameters, ParametersEx,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
};
|
||||||
|
use crate::{Arguments, Valid, ValidEx};
|
||||||
use axum::http::StatusCode;
|
use axum::http::StatusCode;
|
||||||
use axum_msgpack::{MsgPack, MsgPackRaw};
|
use axum_msgpack::{MsgPack, MsgPackRaw};
|
||||||
|
|
||||||
pub mod route {
|
pub mod route {
|
||||||
pub const MSGPACK: &str = "/msgpack";
|
pub const MSGPACK: &str = "/msgpack";
|
||||||
|
pub const MSGPACK_EX: &str = "/msgpack_ex";
|
||||||
pub const MSGPACK_RAW: &str = "/msgpack_raw";
|
pub const MSGPACK_RAW: &str = "/msgpack_raw";
|
||||||
|
pub const MSGPACK_RAW_EX: &str = "/msgpack_raw_ex";
|
||||||
}
|
}
|
||||||
|
|
||||||
pub async fn extract_msgpack(
|
pub async fn extract_msgpack(
|
||||||
@@ -958,9 +1226,27 @@ mod msgpack {
|
|||||||
validate_again(parameters)
|
validate_again(parameters)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub async fn extract_msgpack_ex(
|
||||||
|
ValidEx(MsgPack(parameters), args): ValidEx<
|
||||||
|
MsgPack<ParametersEx>,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
>,
|
||||||
|
) -> StatusCode {
|
||||||
|
validate_again_ex(parameters, args.get())
|
||||||
|
}
|
||||||
|
|
||||||
pub async fn extract_msgpack_raw(
|
pub async fn extract_msgpack_raw(
|
||||||
Valid(MsgPackRaw(parameters)): Valid<MsgPackRaw<Parameters>>,
|
Valid(MsgPackRaw(parameters)): Valid<MsgPackRaw<Parameters>>,
|
||||||
) -> StatusCode {
|
) -> StatusCode {
|
||||||
validate_again(parameters)
|
validate_again(parameters)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub async fn extract_msgpack_raw_ex(
|
||||||
|
ValidEx(MsgPackRaw(parameters), args): ValidEx<
|
||||||
|
MsgPackRaw<ParametersEx>,
|
||||||
|
ParametersExValidationArguments,
|
||||||
|
>,
|
||||||
|
) -> StatusCode {
|
||||||
|
validate_again_ex(parameters, args.get())
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user