use crate::{
listener::ServerListener, virtual_host::VirtualHostImpl, VetisRwLock, VetisVirtualHosts,
};
use http::{HeaderMap, Version};
use hyper_body_utils::HttpBody;
use std::{collections::HashMap, sync::Arc};
use vetis::{
listener::Listener,
server::{Server, ServerConfig},
VetisResult,
};
pub use vetis::{Request, Response};
pub struct HttpServer {
config: ServerConfig,
listeners: Vec<ServerListener>,
virtual_hosts: VetisVirtualHosts<VirtualHostImpl>,
}
impl Server for HttpServer {
type VirtualHost = VirtualHostImpl;
fn new(config: ServerConfig) -> Self {
Self {
config,
listeners: Vec::new(),
virtual_hosts: Arc::new(VetisRwLock::new(HashMap::new())),
}
}
fn set_virtual_hosts(&mut self, virtual_hosts: VetisVirtualHosts<VirtualHostImpl>) {
self.virtual_hosts = virtual_hosts;
}
async fn start(&mut self) -> VetisResult<()> {
let mut listeners: Vec<ServerListener> = self
.config
.listeners()
.iter()
.map(|listener_config| match listener_config.protocol_version() {
#[cfg(feature = "http1")]
&Version::HTTP_11 => {
let mut listener = ServerListener::new(listener_config.clone());
listener.set_virtual_hosts(
self.virtual_hosts
.clone(),
);
listener
}
#[cfg(feature = "http2")]
&Version::HTTP_2 => {
let mut listener = ServerListener::new(listener_config.clone());
listener.set_virtual_hosts(
self.virtual_hosts
.clone(),
);
listener
}
#[cfg(feature = "http3")]
&Version::HTTP_3 => {
let mut listener = ServerListener::new(listener_config.clone());
listener.set_virtual_hosts(
self.virtual_hosts
.clone(),
);
listener
}
_ => {
panic!("Unsupported protocol");
}
})
.collect();
for listener in listeners.iter_mut() {
listener
.listen()
.await?;
}
self.listeners = listeners;
Ok(())
}
async fn stop(&mut self) -> VetisResult<()> {
for listener in self
.listeners
.iter_mut()
{
listener
.stop()
.await?;
}
Ok(())
}
}
pub fn static_response(
status: http::StatusCode,
headers: Option<HeaderMap>,
body: String,
) -> http::Response<HttpBody> {
let mut response = http::Response::builder()
.status(status)
.body(HttpBody::from_bytes(body.as_bytes()))
.unwrap();
if let Some(headers) = headers {
*response.headers_mut() = headers;
}
response
}