Vendor dependencies

This commit is contained in:
2026-08-01 16:11:49 +03:00
parent 7f139a0241
commit 6b5e7f0f8b
29706 changed files with 9575646 additions and 0 deletions
+97
View File
@@ -0,0 +1,97 @@
use crate::util::BoxService;
use std::{fmt, sync::Arc};
use tower_layer::{layer_fn, Layer};
use tower_service::Service;
/// A boxed [`Layer`] trait object.
///
/// [`BoxLayer`] turns a layer into a trait object, allowing both the [`Layer`] itself
/// and the output [`Service`] to be dynamic, while having consistent types.
///
/// This [`Layer`] produces [`BoxService`] instances erasing the type of the
/// [`Service`] produced by the wrapped [`Layer`].
///
/// # Example
///
/// `BoxLayer` can, for example, be useful to create layers dynamically that otherwise wouldn't have
/// the same types. In this example, we include a [`Timeout`] layer
/// only if an environment variable is set. We can use `BoxLayer`
/// to return a consistent type regardless of runtime configuration:
///
/// ```
/// use std::time::Duration;
/// use tower::{Service, ServiceBuilder, BoxError, util::BoxLayer};
///
/// fn common_layer<S, T>() -> BoxLayer<S, T, S::Response, BoxError>
/// where
/// S: Service<T> + Send + 'static,
/// S::Future: Send + 'static,
/// S::Error: Into<BoxError> + 'static,
/// {
/// let builder = ServiceBuilder::new()
/// .concurrency_limit(100);
///
/// if std::env::var("SET_TIMEOUT").is_ok() {
/// let layer = builder
/// .timeout(Duration::from_secs(30))
/// .into_inner();
///
/// BoxLayer::new(layer)
/// } else {
/// let layer = builder
/// .map_err(Into::into)
/// .into_inner();
///
/// BoxLayer::new(layer)
/// }
/// }
/// ```
///
/// [`Layer`]: tower_layer::Layer
/// [`Service`]: tower_service::Service
/// [`BoxService`]: super::BoxService
/// [`Timeout`]: crate::timeout
pub struct BoxLayer<In, T, U, E> {
boxed: Arc<dyn Layer<In, Service = BoxService<T, U, E>> + Send + Sync + 'static>,
}
impl<In, T, U, E> BoxLayer<In, T, U, E> {
/// Create a new [`BoxLayer`].
pub fn new<L>(inner_layer: L) -> Self
where
L: Layer<In> + Send + Sync + 'static,
L::Service: Service<T, Response = U, Error = E> + Send + 'static,
<L::Service as Service<T>>::Future: Send + 'static,
{
let layer = layer_fn(move |inner: In| {
let out = inner_layer.layer(inner);
BoxService::new(out)
});
Self {
boxed: Arc::new(layer),
}
}
}
impl<In, T, U, E> Layer<In> for BoxLayer<In, T, U, E> {
type Service = BoxService<T, U, E>;
fn layer(&self, inner: In) -> Self::Service {
self.boxed.layer(inner)
}
}
impl<In, T, U, E> Clone for BoxLayer<In, T, U, E> {
fn clone(&self) -> Self {
Self {
boxed: Arc::clone(&self.boxed),
}
}
}
impl<In, T, U, E> fmt::Debug for BoxLayer<In, T, U, E> {
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
fmt.debug_struct("BoxLayer").finish()
}
}
+128
View File
@@ -0,0 +1,128 @@
use crate::util::BoxCloneService;
use std::{fmt, sync::Arc};
use tower_layer::{layer_fn, Layer};
use tower_service::Service;
/// A [`Clone`] + [`Send`] boxed [`Layer`].
///
/// [`BoxCloneServiceLayer`] turns a layer into a trait object, allowing both the [`Layer`] itself
/// and the output [`Service`] to be dynamic, while having consistent types.
///
/// This [`Layer`] produces [`BoxCloneService`] instances erasing the type of the
/// [`Service`] produced by the wrapped [`Layer`].
///
/// This is similar to [`BoxLayer`](super::BoxLayer) except the layer and resulting
/// service implements [`Clone`].
///
/// # Example
///
/// `BoxCloneServiceLayer` can, for example, be useful to create layers dynamically that otherwise wouldn't have
/// the same types, when the underlying service must be clone (for example, when building a MakeService)
/// In this example, we include a [`Timeout`] layer only if an environment variable is set. We can use
/// `BoxCloneService` to return a consistent type regardless of runtime configuration:
///
/// ```
/// use std::time::Duration;
/// use tower::{Service, ServiceBuilder, BoxError};
/// use tower::util::{BoxCloneServiceLayer, BoxCloneService};
///
/// #
/// # struct Request;
/// # struct Response;
/// # impl Response {
/// # fn new() -> Self { Self }
/// # }
///
/// fn common_layer<S, T>() -> BoxCloneServiceLayer<S, T, S::Response, BoxError>
/// where
/// S: Service<T> + Clone + Send + 'static,
/// S::Future: Send + 'static,
/// S::Error: Into<BoxError> + 'static,
/// {
/// let builder = ServiceBuilder::new()
/// .concurrency_limit(100);
///
/// if std::env::var("SET_TIMEOUT").is_ok() {
/// let layer = builder
/// .timeout(Duration::from_secs(30))
/// .into_inner();
///
/// BoxCloneServiceLayer::new(layer)
/// } else {
/// let layer = builder
/// .map_err(Into::into)
/// .into_inner();
///
/// BoxCloneServiceLayer::new(layer)
/// }
/// }
///
/// // We can clone the layer (this is true of BoxLayer as well)
/// let boxed_clone_layer = common_layer();
///
/// let cloned_layer = boxed_clone_layer.clone();
///
/// // Using the `BoxCloneServiceLayer` we can create a `BoxCloneService`
/// let service: BoxCloneService<Request, Response, BoxError> = ServiceBuilder::new().layer(boxed_clone_layer)
/// .service_fn(|req: Request| async {
/// Ok::<_, BoxError>(Response::new())
/// });
///
/// # let service = assert_service(service);
///
/// // And we can still clone the service
/// let cloned_service = service.clone();
/// #
/// # fn assert_service<S, R>(svc: S) -> S
/// # where S: Service<R> { svc }
///
/// ```
///
/// [`Layer`]: tower_layer::Layer
/// [`Service`]: tower_service::Service
/// [`BoxService`]: super::BoxService
/// [`Timeout`]: crate::timeout
pub struct BoxCloneServiceLayer<In, T, U, E> {
boxed: Arc<dyn Layer<In, Service = BoxCloneService<T, U, E>> + Send + Sync + 'static>,
}
impl<In, T, U, E> BoxCloneServiceLayer<In, T, U, E> {
/// Create a new [`BoxCloneServiceLayer`].
pub fn new<L>(inner_layer: L) -> Self
where
L: Layer<In> + Send + Sync + 'static,
L::Service: Service<T, Response = U, Error = E> + Send + Clone + 'static,
<L::Service as Service<T>>::Future: Send + 'static,
{
let layer = layer_fn(move |inner: In| {
let out = inner_layer.layer(inner);
BoxCloneService::new(out)
});
Self {
boxed: Arc::new(layer),
}
}
}
impl<In, T, U, E> Layer<In> for BoxCloneServiceLayer<In, T, U, E> {
type Service = BoxCloneService<T, U, E>;
fn layer(&self, inner: In) -> Self::Service {
self.boxed.layer(inner)
}
}
impl<In, T, U, E> Clone for BoxCloneServiceLayer<In, T, U, E> {
fn clone(&self) -> Self {
Self {
boxed: Arc::clone(&self.boxed),
}
}
}
impl<In, T, U, E> fmt::Debug for BoxCloneServiceLayer<In, T, U, E> {
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
fmt.debug_struct("BoxCloneServiceLayer").finish()
}
}
@@ -0,0 +1,129 @@
use std::{fmt, sync::Arc};
use tower_layer::{layer_fn, Layer};
use tower_service::Service;
use crate::util::BoxCloneSyncService;
/// A [`Clone`] + [`Send`] + [`Sync`] boxed [`Layer`].
///
/// [`BoxCloneSyncServiceLayer`] turns a layer into a trait object, allowing both the [`Layer`] itself
/// and the output [`Service`] to be dynamic, while having consistent types.
///
/// This [`Layer`] produces [`BoxCloneSyncService`] instances erasing the type of the
/// [`Service`] produced by the wrapped [`Layer`].
///
/// This is similar to [`BoxCloneServiceLayer`](super::BoxCloneServiceLayer) except the layer and resulting
/// service implements [`Sync`].
///
/// # Example
///
/// `BoxCloneSyncServiceLayer` can, for example, be useful to create layers dynamically that otherwise wouldn't have
/// the same types, when the underlying service must be clone and sync (for example, when building a Hyper connector).
/// In this example, we include a [`Timeout`] layer only if an environment variable is set. We can use
/// `BoxCloneSyncServiceLayer` to return a consistent type regardless of runtime configuration:
///
/// ```
/// use std::time::Duration;
/// use tower::{Service, ServiceBuilder, BoxError};
/// use tower::util::{BoxCloneSyncServiceLayer, BoxCloneSyncService};
///
/// #
/// # struct Request;
/// # struct Response;
/// # impl Response {
/// # fn new() -> Self { Self }
/// # }
///
/// fn common_layer<S, T>() -> BoxCloneSyncServiceLayer<S, T, S::Response, BoxError>
/// where
/// S: Service<T> + Clone + Send + Sync + 'static,
/// S::Future: Send + 'static,
/// S::Error: Into<BoxError> + 'static,
/// {
/// let builder = ServiceBuilder::new()
/// .concurrency_limit(100);
///
/// if std::env::var("SET_TIMEOUT").is_ok() {
/// let layer = builder
/// .timeout(Duration::from_secs(30))
/// .into_inner();
///
/// BoxCloneSyncServiceLayer::new(layer)
/// } else {
/// let layer = builder
/// .map_err(Into::into)
/// .into_inner();
///
/// BoxCloneSyncServiceLayer::new(layer)
/// }
/// }
///
/// // We can clone the layer (this is true of BoxLayer as well)
/// let boxed_clone_sync_layer = common_layer();
///
/// let cloned_sync_layer = boxed_clone_sync_layer.clone();
///
/// // Using the `BoxCloneSyncServiceLayer` we can create a `BoxCloneSyncService`
/// let service: BoxCloneSyncService<Request, Response, BoxError> = ServiceBuilder::new().layer(cloned_sync_layer)
/// .service_fn(|req: Request| async {
/// Ok::<_, BoxError>(Response::new())
/// });
///
/// # let service = assert_service(service);
///
/// // And we can still clone the service
/// let cloned_service = service.clone();
/// #
/// # fn assert_service<S, R>(svc: S) -> S
/// # where S: Service<R> { svc }
///
/// ```
///
/// [`Layer`]: tower_layer::Layer
/// [`Service`]: tower_service::Service
/// [`BoxService`]: super::BoxService
/// [`Timeout`]: crate::timeout
pub struct BoxCloneSyncServiceLayer<In, T, U, E> {
boxed: Arc<dyn Layer<In, Service = BoxCloneSyncService<T, U, E>> + Send + Sync + 'static>,
}
impl<In, T, U, E> BoxCloneSyncServiceLayer<In, T, U, E> {
/// Create a new [`BoxCloneSyncServiceLayer`].
pub fn new<L>(inner_layer: L) -> Self
where
L: Layer<In> + Send + Sync + 'static,
L::Service: Service<T, Response = U, Error = E> + Send + Sync + Clone + 'static,
<L::Service as Service<T>>::Future: Send + 'static,
{
let layer = layer_fn(move |inner: In| {
let out = inner_layer.layer(inner);
BoxCloneSyncService::new(out)
});
Self {
boxed: Arc::new(layer),
}
}
}
impl<In, T, U, E> Layer<In> for BoxCloneSyncServiceLayer<In, T, U, E> {
type Service = BoxCloneSyncService<T, U, E>;
fn layer(&self, inner: In) -> Self::Service {
self.boxed.layer(inner)
}
}
impl<In, T, U, E> Clone for BoxCloneSyncServiceLayer<In, T, U, E> {
fn clone(&self) -> Self {
Self {
boxed: Arc::clone(&self.boxed),
}
}
}
impl<In, T, U, E> fmt::Debug for BoxCloneSyncServiceLayer<In, T, U, E> {
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
fmt.debug_struct("BoxCloneSyncServiceLayer").finish()
}
}
+11
View File
@@ -0,0 +1,11 @@
mod layer;
mod layer_clone;
mod layer_clone_sync;
mod sync;
mod unsync;
#[allow(unreachable_pub)] // https://github.com/rust-lang/rust/issues/57411
pub use self::{
layer::BoxLayer, layer_clone::BoxCloneServiceLayer, layer_clone_sync::BoxCloneSyncServiceLayer,
sync::BoxService, unsync::UnsyncBoxService,
};
+111
View File
@@ -0,0 +1,111 @@
use crate::ServiceExt;
use tower_layer::{layer_fn, LayerFn};
use tower_service::Service;
use sync_wrapper::SyncWrapper;
use std::fmt;
use std::{
future::Future,
pin::Pin,
task::{Context, Poll},
};
/// A boxed `Service + Send` trait object.
///
/// [`BoxService`] turns a service into a trait object, allowing the response
/// future type to be dynamic. This type requires both the service and the
/// response future to be [`Send`].
///
/// If you need a boxed [`Service`] that implements [`Clone`] consider using
/// [`BoxCloneService`](crate::util::BoxCloneService).
///
/// Dynamically dispatched [`Service`] objects allow for erasing the underlying
/// [`Service`] type and using the `Service` instances as opaque handles. This can
/// be useful when the service instance cannot be explicitly named for whatever
/// reason.
///
/// # Examples
///
/// ```
/// use std::future::ready;
/// # use tower_service::Service;
/// # use tower::util::{BoxService, service_fn};
/// // Respond to requests using a closure, but closures cannot be named...
/// # pub fn main() {
/// let svc = service_fn(|mut request: String| {
/// request.push_str(" response");
/// ready(Ok(request))
/// });
///
/// let service: BoxService<String, String, ()> = BoxService::new(svc);
/// # drop(service);
/// }
/// ```
///
/// [`Service`]: crate::Service
/// [`Rc`]: std::rc::Rc
pub struct BoxService<T, U, E> {
inner:
SyncWrapper<Box<dyn Service<T, Response = U, Error = E, Future = BoxFuture<U, E>> + Send>>,
}
/// A boxed `Future + Send` trait object.
///
/// This type alias represents a boxed future that is [`Send`] and can be moved
/// across threads.
type BoxFuture<T, E> = Pin<Box<dyn Future<Output = Result<T, E>> + Send>>;
impl<T, U, E> BoxService<T, U, E> {
#[allow(missing_docs)]
pub fn new<S>(inner: S) -> Self
where
S: Service<T, Response = U, Error = E> + Send + 'static,
S::Future: Send + 'static,
{
// rust can't infer the type
let inner: Box<dyn Service<T, Response = U, Error = E, Future = BoxFuture<U, E>> + Send> =
Box::new(inner.map_future(|f: S::Future| Box::pin(f) as _));
let inner = SyncWrapper::new(inner);
BoxService { inner }
}
/// Returns a [`Layer`] for wrapping a [`Service`] in a [`BoxService`]
/// middleware.
///
/// [`Layer`]: crate::Layer
pub fn layer<S>() -> LayerFn<fn(S) -> Self>
where
S: Service<T, Response = U, Error = E> + Send + 'static,
S::Future: Send + 'static,
{
layer_fn(Self::new)
}
}
impl<T, U, E> Service<T> for BoxService<T, U, E> {
type Response = U;
type Error = E;
type Future = BoxFuture<U, E>;
fn poll_ready(&mut self, cx: &mut Context<'_>) -> Poll<Result<(), E>> {
self.inner.get_mut().poll_ready(cx)
}
fn call(&mut self, request: T) -> BoxFuture<U, E> {
self.inner.get_mut().call(request)
}
}
impl<T, U, E> fmt::Debug for BoxService<T, U, E> {
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
fmt.debug_struct("BoxService").finish()
}
}
#[test]
fn is_sync() {
fn assert_sync<T: Sync>() {}
assert_sync::<BoxService<(), (), ()>>();
}
+86
View File
@@ -0,0 +1,86 @@
use tower_layer::{layer_fn, LayerFn};
use tower_service::Service;
use std::fmt;
use std::{
future::Future,
pin::Pin,
task::{Context, Poll},
};
/// A boxed [`Service`] trait object.
pub struct UnsyncBoxService<T, U, E> {
inner: Box<dyn Service<T, Response = U, Error = E, Future = UnsyncBoxFuture<U, E>>>,
}
/// A boxed [`Future`] trait object.
///
/// This type alias represents a boxed future that is *not* [`Send`] and must
/// remain on the current thread.
type UnsyncBoxFuture<T, E> = Pin<Box<dyn Future<Output = Result<T, E>>>>;
#[derive(Debug)]
struct UnsyncBoxed<S> {
inner: S,
}
impl<T, U, E> UnsyncBoxService<T, U, E> {
#[allow(missing_docs)]
pub fn new<S>(inner: S) -> Self
where
S: Service<T, Response = U, Error = E> + 'static,
S::Future: 'static,
{
let inner = Box::new(UnsyncBoxed { inner });
UnsyncBoxService { inner }
}
/// Returns a [`Layer`] for wrapping a [`Service`] in an [`UnsyncBoxService`] middleware.
///
/// [`Layer`]: crate::Layer
pub fn layer<S>() -> LayerFn<fn(S) -> Self>
where
S: Service<T, Response = U, Error = E> + 'static,
S::Future: 'static,
{
layer_fn(Self::new)
}
}
impl<T, U, E> Service<T> for UnsyncBoxService<T, U, E> {
type Response = U;
type Error = E;
type Future = UnsyncBoxFuture<U, E>;
fn poll_ready(&mut self, cx: &mut Context<'_>) -> Poll<Result<(), E>> {
self.inner.poll_ready(cx)
}
fn call(&mut self, request: T) -> UnsyncBoxFuture<U, E> {
self.inner.call(request)
}
}
impl<T, U, E> fmt::Debug for UnsyncBoxService<T, U, E> {
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
fmt.debug_struct("UnsyncBoxService").finish()
}
}
impl<S, Request> Service<Request> for UnsyncBoxed<S>
where
S: Service<Request> + 'static,
S::Future: 'static,
{
type Response = S::Response;
type Error = S::Error;
type Future = Pin<Box<dyn Future<Output = Result<S::Response, S::Error>>>>;
fn poll_ready(&mut self, cx: &mut Context<'_>) -> Poll<Result<(), Self::Error>> {
self.inner.poll_ready(cx)
}
fn call(&mut self, request: Request) -> Self::Future {
Box::pin(self.inner.call(request))
}
}