diff options
author | Kjetil Orbekk <kj@orbekk.com> | 2022-12-23 16:41:50 -0500 |
---|---|---|
committer | Kjetil Orbekk <kj@orbekk.com> | 2022-12-23 16:41:50 -0500 |
commit | b62be3482bc8a69d59744964ec4f6d3574d8b918 (patch) | |
tree | c8bc8d42cbfcbb5fe8f075ec99d48d8ffd4b5ce4 | |
parent | 45ce66a29b3d1c49ef8e86b125701e89d58e8a4a (diff) |
Add ability to request the next deal when results are displayed
-rw-r--r-- | server/src/main.rs | 13 | ||||
-rw-r--r-- | server/src/play.rs | 9 | ||||
-rw-r--r-- | webapp/src/components/table.rs | 19 | ||||
-rw-r--r-- | webapp/src/services.rs | 9 |
4 files changed, 48 insertions, 2 deletions
diff --git a/server/src/main.rs b/server/src/main.rs index a9e8f69..c0ec4cb 100644 --- a/server/src/main.rs +++ b/server/src/main.rs @@ -117,6 +117,7 @@ async fn main() { .route("/api/table/:id", get(get_table_view)) .route("/api/table/:id/bid", post(post_bid)) .route("/api/table/:id/play", post(post_play)) + .route("/api/table/:id/admin/deal", post(table_new_deal)) .route("/api/login", get(login)) .route(auth::LOGIN_CALLBACK, get(login_callback)) .layer(CookieManagerLayer::new()) @@ -169,6 +170,18 @@ async fn get_table_view( Ok(response) } +async fn table_new_deal( + _session: AuthenticatedSession, + State(state): ServerState, + Path(id): Path<Uuid>, +) -> Result<Json<()>, BridgeError> { + info!("Getting table state for {id:}"); + let jnl = DbJournal::new(state.db.clone(), id); + let mut table = play::Table::replay(jnl).await?; + table.new_deal().await?; + Ok(Json(())) +} + async fn post_bid( _session: AuthenticatedSession, State(state): ServerState, diff --git a/server/src/play.rs b/server/src/play.rs index e0d4733..68ea94b 100644 --- a/server/src/play.rs +++ b/server/src/play.rs @@ -179,6 +179,15 @@ impl<J: Journal<TableUpdate>> Table<J> { self.insert_and_apply(TableUpdate::Play(card)).await } + pub async fn new_deal(&mut self) -> Result<(), BridgeError> { + let dealer = match &self.state { + TableState::Unknown => random(), + TableState::Game(g) => g.dealer(), + TableState::Result(_) => random(), // TODO: We should know the dealer here. + }; + self.insert_and_apply(TableUpdate::NewDeal { deal: random(), dealer: dealer.next() }).await + } + async fn insert_and_apply( &mut self, update: TableUpdate, diff --git a/webapp/src/components/table.rs b/webapp/src/components/table.rs index 9702793..3bc52a3 100644 --- a/webapp/src/components/table.rs +++ b/webapp/src/components/table.rs @@ -35,6 +35,7 @@ struct OnlineTableInner { pub enum Msg { TableStateUpdated(Result<TableStatePlayerView, anyhow::Error>), + RequestNewDeal, Bid(Bid), Play(Card), } @@ -136,6 +137,15 @@ impl Component for OnlineTableInner { ctx.props().app_ctx.set_error(error); false } + Msg::RequestNewDeal => { + let table = ctx.props().table.clone(); + ctx.link().send_future( + async move { + services::new_deal(table.clone()).await?; + services::get_table_player_view(table).await + }.map(Msg::TableStateUpdated)); + false + }, } } @@ -146,8 +156,13 @@ impl Component for OnlineTableInner { <p>{"An error occurred."}</p> }, Some(TableStatePlayerView::Game(game)) => self.view_game(ctx, game), - Some(TableStatePlayerView::Result(result)) => html! { - <p>{"A beautiful result."}</p> + Some(TableStatePlayerView::Result(_)) => html! { + <> + <p>{"A beautiful result."}</p> + <button onclick={ctx.link().callback(|_| Msg::RequestNewDeal)}> + {"New deal"} + </button> + </> }, } } diff --git a/webapp/src/services.rs b/webapp/src/services.rs index 43b1698..668530f 100644 --- a/webapp/src/services.rs +++ b/webapp/src/services.rs @@ -34,3 +34,12 @@ pub async fn play(table: Table, card: Card) -> Result<(), anyhow::Error> { .context("submitting play")?; ok_json(response).await } + +pub async fn new_deal(table: Table) -> Result<(), anyhow::Error> { + let response = + Request::post(&format!("/api/table/{}/admin/deal", table.id)) + .send() + .await + .context("requesting new deal")?; + ok_json(response).await +} |