use crate::operations::ServerOperation; use anyhow::anyhow; use bytes::BytesMut; use log::{error, info}; use tokio::io::AsyncReadExt; use tokio::net::{TcpListener, TcpStream}; use tokio_stream::{wrappers::TcpListenerStream, StreamExt}; mod operations; pub(crate) type Result = std::result::Result; #[tokio::main] async fn main() -> Result<()> { simple_logger::SimpleLogger::default().init()?; let mut listener_stream = TcpListener::bind("localhost:8080") .await .map(TcpListenerStream::new)?; info!("Successfully bound to port"); while let Some(Ok(stream)) = listener_stream.next().await { tokio::task::spawn(async { match handle_stream(stream).await { Ok(_) => (), Err(e) => error!("{}", e), } }); } info!("Cleanly shut down. Goodbye!"); Ok(()) } async fn handle_stream(mut socket: TcpStream) -> Result<()> { // only accept data that can fit in 256 bytes let mut buffer = BytesMut::with_capacity(256); loop { let bytes_read = socket.read_buf(&mut buffer).await?; match bytes_read { 0 => return Err(anyhow!("Failed to read bytes, assuming socket is closed.")), n => { let data = buffer.split_to(n); // O(1) let parsed = serde_json::from_slice::(&data)?; match parsed { ServerOperation::Query(op) => { dbg!(op); } ServerOperation::Meta(op) => { dbg!(op); } } buffer.unsplit(data); // O(1) } } buffer.clear(); } }