Server action refactoring part 1 of N
authoralfadur <mail@none>
Fri, 28 Dec 2018 03:10:05 +0300
changeset 14504 6cc0fce249f9
parent 14503 831ecafd74c6
child 14505 ba29aa03db87
Server action refactoring part 1 of N
rust/hedgewars-server/src/server/actions.rs
rust/hedgewars-server/src/server/core.rs
rust/hedgewars-server/src/server/handlers/lobby.rs
--- a/rust/hedgewars-server/src/server/actions.rs	Thu Dec 27 23:43:54 2018 +0100
+++ b/rust/hedgewars-server/src/server/actions.rs	Fri Dec 28 03:10:05 2018 +0300
@@ -118,7 +118,6 @@
     ReactProtocolMessage(HWProtocolMessage),
     CheckRegistered,
     JoinLobby,
-    AddRoom(String, Option<String>),
     RemoveRoom(RoomId),
     MoveToRoom(RoomId),
     MoveToLobby(String),
@@ -240,26 +239,6 @@
                 ],
             );
         }
-        AddRoom(name, password) => {
-            let room_id = server.add_room();;
-
-            let r = &mut server.rooms[room_id];
-            let c = &mut server.clients[client_id];
-            r.master_id = Some(c.id);
-            r.name = name;
-            r.password = password;
-            r.protocol_number = c.protocol_number;
-
-            let actions = vec![
-                RoomAdd(r.info(Some(&c)))
-                    .send_all()
-                    .with_protocol(r.protocol_number)
-                    .action(),
-                MoveToRoom(room_id),
-            ];
-
-            server.react(client_id, actions);
-        }
         RemoveRoom(room_id) => {
             let r = &mut server.rooms[room_id];
             let actions = vec![RoomRemove(r.name.clone())
--- a/rust/hedgewars-server/src/server/core.rs	Thu Dec 27 23:43:54 2018 +0100
+++ b/rust/hedgewars-server/src/server/core.rs	Fri Dec 28 03:10:05 2018 +0300
@@ -13,6 +13,7 @@
 use log::*;
 use rand::{thread_rng, RngCore};
 use slab;
+use std::borrow::BorrowMut;
 
 type Slab<T> = slab::Slab<T>;
 
@@ -37,7 +38,7 @@
             removed_clients: vec![],
             io,
         };
-        server.lobby_id = server.add_room();
+        server.lobby_id = server.add_room().id;
         server
     }
 
@@ -68,12 +69,8 @@
         );
     }
 
-    pub fn add_room(&mut self) -> RoomId {
-        let entry = self.rooms.vacant_entry();
-        let key = entry.key();
-        let room = HWRoom::new(entry.key());
-        entry.insert(room);
-        key
+    pub fn add_room(&mut self) -> &mut HWRoom {
+        allocate_room(&mut self.rooms)
     }
 
     pub fn handle_msg(&mut self, client_id: ClientId, msg: HWProtocolMessage) {
@@ -83,6 +80,21 @@
         }
     }
 
+    #[inline]
+    pub fn create_room(
+        &mut self,
+        creator_id: ClientId,
+        name: String,
+        password: Option<String>,
+    ) -> RoomId {
+        create_room(
+            &mut self.clients[creator_id],
+            &mut self.rooms,
+            name,
+            password,
+        )
+    }
+
     fn get_recipients(&self, client_id: ClientId, destination: &Destination) -> Vec<ClientId> {
         let mut ids = match *destination {
             Destination::ToSelf => vec![client_id],
@@ -188,3 +200,62 @@
         self.client_and_room(client_id).1
     }
 }
+
+fn allocate_room(rooms: &mut Slab<HWRoom>) -> &mut HWRoom {
+    let entry = rooms.vacant_entry();
+    let key = entry.key();
+    let room = HWRoom::new(entry.key());
+    entry.insert(room)
+}
+
+fn create_room(
+    client: &mut HWClient,
+    rooms: &mut Slab<HWRoom>,
+    name: String,
+    password: Option<String>,
+) -> RoomId {
+    let room = allocate_room(rooms);
+
+    room.master_id = Some(client.id);
+    room.name = name;
+    room.password = password;
+    room.protocol_number = client.protocol_number;
+
+    room.players_number = 1;
+    room.ready_players_number = 1;
+
+    client.room_id = Some(room.id);
+    client.set_is_master(true);
+    client.set_is_ready(true);
+    client.set_is_joined_mid_game(false);
+
+    room.id
+}
+
+fn move_to_room(client: &mut HWClient, room: &mut HWRoom) {
+    debug_assert!(client.room_id != Some(room.id));
+
+    room.players_number += 1;
+
+    client.room_id = Some(room.id);
+    client.set_is_joined_mid_game(room.game_info.is_some());
+    client.set_is_in_game(room.game_info.is_some());
+
+    if let Some(ref mut info) = room.game_info {
+        let teams = info.client_teams(client.id);
+        client.teams_in_game = teams.clone().count() as u8;
+        client.clan = teams.clone().next().map(|t| t.color);
+        let team_names: Vec<_> = teams.map(|t| t.name.clone()).collect();
+
+        if !team_names.is_empty() {
+            info.left_teams.retain(|name| !team_names.contains(&name));
+            info.teams_in_game += team_names.len() as u8;
+            room.teams = info
+                .teams_at_start
+                .iter()
+                .filter(|(_, t)| !team_names.contains(&t.name))
+                .cloned()
+                .collect();
+        }
+    }
+}
--- a/rust/hedgewars-server/src/server/handlers/lobby.rs	Thu Dec 27 23:43:54 2018 +0100
+++ b/rust/hedgewars-server/src/server/handlers/lobby.rs	Fri Dec 28 03:10:05 2018 +0300
@@ -27,9 +27,20 @@
                     "+hr".to_string(),
                     vec![server.clients[client_id].nick.clone()],
                 );
-                vec![AddRoom(name, password), flags_msg.send_self().action()]
+
+                let room_id = server.create_room(client_id, name, password);
+                let room = &server.rooms[room_id];
+                let client = &server.clients[client_id];
+
+                vec![
+                    RoomAdd(room.info(Some(&client)))
+                        .send_all()
+                        .with_protocol(room.protocol_number)
+                        .action(),
+                    flags_msg.send_self().action(),
+                ]
             };
-            server.react(client_id, actions);
+            server.react(client_id, actions)
         }
         Chat(msg) => {
             let actions = vec![ChatMsg {