From 420ca3e22488fec3f81d0487c0bd15afd5ff09d4 Mon Sep 17 00:00:00 2001 From: alemidev Date: Wed, 13 Jul 2022 01:58:34 +0200 Subject: [PATCH] feat: implemented basic session flow on server Co-authored-by: f-tlm --- src/server/main.rs | 127 ++++++++++++++++++++++++++++++++++----------- 1 file changed, 97 insertions(+), 30 deletions(-) diff --git a/src/server/main.rs b/src/server/main.rs index aca16fc..14c76c4 100644 --- a/src/server/main.rs +++ b/src/server/main.rs @@ -1,60 +1,127 @@ +use std::{collections::HashMap, sync::Arc}; + +use state::{StateManager, AlterState}; +use tonic::Streaming; +use tonic::codegen::futures_core::Stream; use tonic::{transport::Server, Request, Response, Status}; -pub mod proto_core { - tonic::include_proto!("core"); +pub mod proto { + tonic::include_proto!("workspace"); } -use proto_core::session_server::{Session, SessionServer}; -use proto_core::{SessionRequest, SessionResponse}; +use tokio::sync::{mpsc, watch}; +use proto::workspace_server::{Workspace, WorkspaceServer}; +use proto::{SessionRequest, SessionResponse}; -#[derive(Debug, Default)] -pub struct TestSession {} +use crate::workspace::Workspace as WorkspaceInstance; // TODO fuck! + +pub mod workspace; +pub mod state; + +#[derive(Debug)] +pub struct WorkspaceService { + tx: mpsc::Sender, + rx: watch::Receiver>> +} #[tonic::async_trait] -impl Session for TestSession { +impl Workspace for WorkspaceService { async fn create( &self, request: Request, ) -> Result, Status> { println!("Got a request: {:?}", request); + let r = request.into_inner(); - let reply = proto_core::SessionResponse { - session_id: request.into_inner().session_id, + let w = WorkspaceInstance::new(r.session_key.clone(), r.content.unwrap_or("".to_string())); + + let reply = proto::SessionResponse { + session_key: r.session_key.clone(), + accepted: true, + content: Some(w.content.clone()), + hash: None, + }; + + self.tx.send(AlterState::ADD{key: r.session_key.clone(), w}).await.unwrap(); + + Ok(Response::new(reply)) + } + + async fn sync( + &self, + request: Request, + ) -> Result, Status> { + println!("Got a request: {:?}", request); + let r = request.into_inner(); + + if let Some(w) = self.rx.borrow().get(&r.session_key) { + let reply = proto::SessionResponse { + session_key: r.session_key, + accepted: true, + content: Some(w.content.clone()), + hash: None, + }; + + Ok(Response::new(reply)) + } else { + Err(Status::out_of_range("fuck you".to_string())) + } + } + + // TODO make it do something + async fn join( + &self, + request: Request, + ) -> Result, Status> { + println!("Got a request: {:?}", request); + + let reply = proto::SessionResponse { + session_key: request.into_inner().session_key, + accepted: true, + content: None, + hash: None, }; Ok(Response::new(reply)) } + + async fn leave( + &self, + request: Request, + ) -> Result, Status> { + println!("Got a request: {:?}", request); + let r = request.into_inner(); + let mut removed = false; + + if self.rx.borrow().get(&r.session_key).is_some() { + self.tx.send(AlterState::REMOVE { key: r.session_key.clone() }).await.unwrap(); + removed = true; // TODO this is a lie! Verify it + } + + let reply = proto::SessionResponse { + session_key: r.session_key, + accepted: removed, + content: None, + hash: None, + }; + + Ok(Response::new(reply)) + } + } #[tokio::main] async fn main() -> Result<(), Box> { let addr = "[::1]:50051".parse()?; - let greeter = TestSession::default(); + + let (tx, rx) = state::run_state_manager(); + let greeter = WorkspaceService { tx, rx }; Server::builder() - .add_service(SessionServer::new(greeter)) + .add_service(WorkspaceServer::new(greeter)) .serve(addr) .await?; Ok(()) } - -/* - -#[tokio::main] -async fn main() -> Result<(), Box> { - let mut client = GreeterClient::connect("http://[::1]:50051").await?; - - let request = tonic::Request::new(HelloRequest { - name: "Tonic".into(), - }); - - let response = client.say_hello(request).await?; - - println!("RESPONSE={:?}", response); - - Ok(()) -} - -*/