Refactor internal ignite sequencing.

This commit is contained in:
Sergio Benitez 2024-04-22 17:26:21 -07:00
parent 3bfc4ca644
commit 85ca2bc01c
2 changed files with 36 additions and 46 deletions

View File

@ -113,7 +113,7 @@ impl Client {
let rocket = self.rocket; let rocket = self.rocket;
rocket.shutdown().notify(); rocket.shutdown().notify();
rocket.fairings.handle_shutdown(&rocket).await; rocket.fairings.handle_shutdown(&rocket).await;
rocket.into_ignite() rocket.deorbit()
} }
// Generates the public API methods, which call the private methods above. // Generates the public API methods, which call the private methods above.

View File

@ -3,11 +3,12 @@ use std::ops::{Deref, DerefMut};
use std::sync::Arc; use std::sync::Arc;
use std::time::Duration; use std::time::Duration;
use std::any::Any; use std::any::Any;
use std::future::Future;
use futures::{Future, TryFutureExt};
use yansi::Paint; use yansi::Paint;
use either::Either; use either::Either;
use figment::{Figment, Provider}; use figment::{Figment, Provider};
use futures::TryFutureExt;
use crate::shutdown::{Stages, Shutdown}; use crate::shutdown::{Stages, Shutdown};
use crate::{sentinel, shield::Shield, Catcher, Config, Route}; use crate::{sentinel, shield::Shield, Catcher, Config, Route};
@ -682,31 +683,7 @@ impl Rocket<Ignite> {
rocket rocket
} }
async fn _launch_with<B: Bind>(self) -> Result<Rocket<Ignite>, Error> { async fn _launch<L: Listener + 'static>(self, listener: L) -> Result<Rocket<Ignite>, Error> {
let bind_endpoint = B::bind_endpoint(&&self).ok();
let listener: B = B::bind(&self).await
.map_err(|e| ErrorKind::Bind(bind_endpoint, Box::new(e)))?;
let any: Box<dyn Any + Send + Sync> = Box::new(listener);
match any.downcast::<DefaultListener>() {
Ok(listener) => {
let listener = *listener;
crate::util::for_both!(listener, listener => {
crate::util::for_both!(listener, listener => {
self._launch_on(listener).await
})
})
}
Err(any) => {
let listener = *any.downcast::<B>().unwrap();
self._launch_on(listener).await
}
}
}
async fn _launch_on<L>(self, listener: L) -> Result<Rocket<Ignite>, Error>
where L: Listener + 'static,
{
let rocket = self.listen_and_serve(listener, |rocket| async move { let rocket = self.listen_and_serve(listener, |rocket| async move {
let rocket = Arc::new(rocket); let rocket = Arc::new(rocket);
@ -761,7 +738,7 @@ impl Rocket<Orbit> {
match Arc::try_unwrap(self) { match Arc::try_unwrap(self) {
Ok(rocket) => { Ok(rocket) => {
info!("Graceful shutdown completed successfully."); info!("Graceful shutdown completed successfully.");
Ok(rocket.into_ignite()) Ok(rocket.deorbit())
} }
Err(rocket) => { Err(rocket) => {
warn!("Shutdown failed: outstanding background I/O."); warn!("Shutdown failed: outstanding background I/O.");
@ -770,7 +747,7 @@ impl Rocket<Orbit> {
} }
} }
pub(crate) fn into_ignite(self) -> Rocket<Ignite> { pub(crate) fn deorbit(self) -> Rocket<Ignite> {
Rocket(Igniting { Rocket(Igniting {
router: self.0.router, router: self.0.router,
fairings: self.0.fairings, fairings: self.0.fairings,
@ -955,14 +932,16 @@ impl<P: Phase> Rocket<P> {
} }
} }
pub(crate) async fn local_launch(self, e: Endpoint) -> Result<Rocket<Orbit>, Error> { async fn into_ignite(self) -> Result<Rocket<Ignite>, Error> {
let rocket = match self.0.into_state() { match self.0.into_state() {
State::Build(s) => Rocket::from(s).ignite().await?._local_launch(e).await, State::Build(s) => Rocket::from(s).ignite().await,
State::Ignite(s) => Rocket::from(s)._local_launch(e).await, State::Ignite(s) => Ok(Rocket::from(s)),
State::Orbit(s) => Rocket::from(s) State::Orbit(s) => Ok(Rocket::from(s).deorbit()),
}; }
}
Ok(rocket) pub(crate) async fn local_launch(self, e: Endpoint) -> Result<Rocket<Orbit>, Error> {
Ok(self.into_ignite().await?._local_launch(e).await)
} }
/// Returns a `Future` that transitions this instance of `Rocket` from any /// Returns a `Future` that transitions this instance of `Rocket` from any
@ -1014,10 +993,25 @@ impl<P: Phase> Rocket<P> {
} }
pub async fn launch_with<B: Bind>(self) -> Result<Rocket<Ignite>, Error> { pub async fn launch_with<B: Bind>(self) -> Result<Rocket<Ignite>, Error> {
match self.0.into_state() { let rocket = self.into_ignite().await?;
State::Build(s) => Rocket::from(s).ignite().await?._launch_with::<B>().await, let bind_endpoint = B::bind_endpoint(&rocket).ok();
State::Ignite(s) => Rocket::from(s)._launch_with::<B>().await, let listener: B = B::bind(&rocket).await
State::Orbit(s) => Ok(Rocket::from(s).into_ignite()) .map_err(|e| ErrorKind::Bind(bind_endpoint, Box::new(e)))?;
let any: Box<dyn Any + Send + Sync> = Box::new(listener);
match any.downcast::<DefaultListener>() {
Ok(listener) => {
let listener = *listener;
crate::util::for_both!(listener, listener => {
crate::util::for_both!(listener, listener => {
rocket._launch(listener).await
})
})
}
Err(any) => {
let listener = *any.downcast::<B>().unwrap();
rocket._launch(listener).await
}
} }
} }
@ -1027,17 +1021,13 @@ impl<P: Phase> Rocket<P> {
E: std::error::Error + Send + 'static E: std::error::Error + Send + 'static
{ {
let listener = listener.map_err(|e| ErrorKind::Bind(None, Box::new(e))).await?; let listener = listener.map_err(|e| ErrorKind::Bind(None, Box::new(e))).await?;
self.launch_on(listener).await self.into_ignite().await?._launch(listener).await
} }
pub async fn launch_on<L>(self, listener: L) -> Result<Rocket<Ignite>, Error> pub async fn launch_on<L>(self, listener: L) -> Result<Rocket<Ignite>, Error>
where L: Listener + 'static, where L: Listener + 'static,
{ {
match self.0.into_state() { self.into_ignite().await?._launch(listener).await
State::Build(s) => Rocket::from(s).ignite().await?._launch_on(listener).await,
State::Ignite(s) => Rocket::from(s)._launch_on(listener).await,
State::Orbit(s) => Ok(Rocket::from(s).into_ignite())
}
} }
} }