rust/hedgewars-server/src/core/server.rs
author Wuzzy <Wuzzy2@mail.ru>
Sat, 02 Nov 2019 13:01:28 +0100
changeset 15501 5a30396f8fb2
parent 15492 395be40faa51
child 15516 b907b9071ec5
permissions -rw-r--r--
ClimbHome: Change misleading Seed assignment to nil value This was "Seed = ClimbHome", but ClimbHome was a nil value. This code still worked as the engine interpreted the nil value as empty string. But it can be very misleading. This changeset makes the Seed assignment more explicit by assigning the empty string directly. The compability has been tested.
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
13416
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
     1
use super::{
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
     2
    client::HwClient,
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
     3
    indexslab::IndexSlab,
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
     4
    room::HwRoom,
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
     5
    types::{ClientId, RoomId, ServerVar},
13416
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
     6
};
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
     7
use crate::{protocol::messages::HwProtocolMessage::Greeting, utils};
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
     8
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
     9
use crate::core::server::JoinRoomError::WrongProtocol;
14786
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
    10
use bitflags::*;
13805
0463a4221327 cleanup crate imports
alfadur
parents: 13798
diff changeset
    11
use log::*;
14457
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
    12
use slab;
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    13
use std::{borrow::BorrowMut, collections::HashSet, iter, num::NonZeroU16};
12126
4348997e502b Refactor code to add more structure to it
unc0rr
parents:
diff changeset
    14
12852
bd35cb2302b3 Quick dirty fix for building
unc0rr
parents: 12148
diff changeset
    15
type Slab<T> = slab::Slab<T>;
12127
36ac9c075d0d - Use netbuf buffers for client connection stream
unc0rr
parents: 12126
diff changeset
    16
15441
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
    17
#[derive(Debug)]
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    18
pub enum CreateRoomError {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    19
    InvalidName,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    20
    AlreadyExists,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    21
}
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    22
15441
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
    23
#[derive(Debug)]
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    24
pub enum JoinRoomError {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    25
    DoesntExist,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    26
    WrongProtocol,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    27
    Full,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    28
    Restricted,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    29
}
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    30
15482
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    31
pub enum LeaveRoomResult {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    32
    RoomRemoved,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    33
    RoomRemains {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    34
        is_empty: bool,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    35
        was_master: bool,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    36
        was_in_game: bool,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    37
        new_master: Option<ClientId>,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    38
        removed_teams: Vec<String>,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    39
    },
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    40
}
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    41
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    42
#[derive(Debug)]
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    43
pub enum LeaveRoomError {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    44
    NoRoom,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    45
}
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
    46
15441
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
    47
#[derive(Debug)]
15487
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    48
pub struct ChangeMasterResult {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    49
    pub old_master_id: Option<ClientId>,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    50
    pub new_master_id: ClientId,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    51
}
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    52
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    53
#[derive(Debug)]
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    54
pub enum ChangeMasterError {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    55
    NoAccess,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    56
    AlreadyMaster,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    57
    NoClient,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    58
    ClientNotInRoom,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    59
}
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    60
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
    61
#[derive(Debug)]
15492
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
    62
pub enum StartGameError {
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
    63
    NotEnoughClans,
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
    64
    NotEnoughTeams,
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
    65
    NotReady,
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
    66
    AlreadyInGame,
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
    67
}
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
    68
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
    69
#[derive(Debug)]
15441
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
    70
pub struct UninitializedError();
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
    71
#[derive(Debug)]
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    72
pub struct AccessError();
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
    73
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
    74
pub struct HwAnteClient {
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    75
    pub nick: Option<String>,
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    76
    pub protocol_number: Option<NonZeroU16>,
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    77
    pub server_salt: String,
14781
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
    78
    pub is_checker: bool,
15176
f6115638aa92 enable local admins for non-official servers
alfadur
parents: 15075
diff changeset
    79
    pub is_local_admin: bool,
15441
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
    80
    pub is_registered: bool,
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
    81
    pub is_admin: bool,
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
    82
    pub is_contributor: bool,
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    83
}
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    84
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
    85
pub struct HwAnteroom {
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
    86
    pub clients: IndexSlab<HwAnteClient>,
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    87
}
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    88
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
    89
impl HwAnteroom {
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    90
    pub fn new(clients_limit: usize) -> Self {
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    91
        let clients = IndexSlab::with_capacity(clients_limit);
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
    92
        HwAnteroom { clients }
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    93
    }
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    94
15176
f6115638aa92 enable local admins for non-official servers
alfadur
parents: 15075
diff changeset
    95
    pub fn add_client(&mut self, client_id: ClientId, salt: String, is_local_admin: bool) {
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
    96
        let client = HwAnteClient {
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    97
            nick: None,
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    98
            protocol_number: None,
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
    99
            server_salt: salt,
14781
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   100
            is_checker: false,
15176
f6115638aa92 enable local admins for non-official servers
alfadur
parents: 15075
diff changeset
   101
            is_local_admin,
15441
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   102
            is_registered: false,
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   103
            is_admin: false,
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   104
            is_contributor: false,
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   105
        };
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   106
        self.clients.insert(client_id, client);
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   107
    }
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   108
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   109
    pub fn remove_client(&mut self, client_id: ClientId) -> Option<HwAnteClient> {
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   110
        let client = self.clients.remove(client_id);
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   111
        client
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   112
    }
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   113
}
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   114
14783
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   115
pub struct ServerGreetings {
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   116
    pub for_latest_protocol: String,
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   117
    pub for_old_protocols: String,
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   118
}
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   119
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   120
impl ServerGreetings {
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   121
    fn new() -> Self {
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   122
        Self {
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   123
            for_latest_protocol: "\u{1f994} is watching".to_string(),
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   124
            for_old_protocols: "\u{1f994} is watching".to_string(),
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   125
        }
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   126
    }
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   127
}
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   128
14786
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   129
bitflags! {
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   130
    pub struct ServerFlags: u8 {
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   131
        const REGISTERED_ONLY = 0b0000_1000;
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   132
    }
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   133
}
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   134
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   135
pub struct HwServer {
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   136
    pub clients: IndexSlab<HwClient>,
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   137
    pub rooms: Slab<HwRoom>,
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   138
    pub anteroom: HwAnteroom,
14783
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   139
    pub latest_protocol: u16,
14786
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   140
    pub flags: ServerFlags,
14783
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   141
    pub greetings: ServerGreetings,
12126
4348997e502b Refactor code to add more structure to it
unc0rr
parents:
diff changeset
   142
}
4348997e502b Refactor code to add more structure to it
unc0rr
parents:
diff changeset
   143
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   144
impl HwServer {
14780
65861ba8b4e8 move room saves to IO thread
alfadur
parents: 14779
diff changeset
   145
    pub fn new(clients_limit: usize, rooms_limit: usize) -> Self {
13119
1e39b8749072 separated the server logic from all the async io mess.
alfadur
parents: 12852
diff changeset
   146
        let rooms = Slab::with_capacity(rooms_limit);
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   147
        let clients = IndexSlab::with_capacity(clients_limit);
14694
25c564f77b7d remove lobby room
alfadur <mail@none>
parents: 14693
diff changeset
   148
        Self {
14457
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   149
            clients,
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   150
            rooms,
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   151
            anteroom: HwAnteroom::new(clients_limit),
14783
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   152
            greetings: ServerGreetings::new(),
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   153
            latest_protocol: 58,
14786
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   154
            flags: ServerFlags::empty(),
14694
25c564f77b7d remove lobby room
alfadur <mail@none>
parents: 14693
diff changeset
   155
        }
12126
4348997e502b Refactor code to add more structure to it
unc0rr
parents:
diff changeset
   156
    }
4348997e502b Refactor code to add more structure to it
unc0rr
parents:
diff changeset
   157
15441
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   158
    #[inline]
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   159
    pub fn client(&self, client_id: ClientId) -> &HwClient {
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   160
        &self.clients[client_id]
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   161
    }
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   162
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   163
    #[inline]
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   164
    pub fn client_mut(&mut self, client_id: ClientId) -> &mut HwClient {
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   165
        &mut self.clients[client_id]
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   166
    }
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   167
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   168
    #[inline]
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   169
    pub fn room(&self, room_id: RoomId) -> &HwRoom {
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   170
        &self.rooms[room_id]
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   171
    }
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   172
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   173
    #[inline]
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   174
    pub fn room_mut(&mut self, room_id: RoomId) -> &mut HwRoom {
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   175
        &mut self.rooms[room_id]
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   176
    }
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   177
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   178
    #[inline]
15482
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   179
    pub fn client_and_room(&self, client_id: ClientId, room_id: RoomId) -> (&HwClient, &HwRoom) {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   180
        (&self.clients[client_id], &self.rooms[room_id])
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   181
    }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   182
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   183
    #[inline]
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   184
    pub fn client_and_room_mut(
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   185
        &mut self,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   186
        client_id: ClientId,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   187
        room_id: RoomId,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   188
    ) -> (&mut HwClient, &mut HwRoom) {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   189
        (&mut self.clients[client_id], &mut self.rooms[room_id])
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   190
    }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   191
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   192
    #[inline]
15441
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   193
    pub fn is_admin(&self, client_id: ClientId) -> bool {
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   194
        self.clients
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   195
            .get(client_id)
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   196
            .map(|c| c.is_admin())
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   197
            .unwrap_or(false)
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   198
    }
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   199
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   200
    pub fn add_client(&mut self, client_id: ClientId, data: HwAnteClient) {
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   201
        if let (Some(protocol), Some(nick)) = (data.protocol_number, data.nick) {
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   202
            let mut client = HwClient::new(client_id, protocol.get(), nick);
14781
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   203
            client.set_is_checker(data.is_checker);
15176
f6115638aa92 enable local admins for non-official servers
alfadur
parents: 15075
diff changeset
   204
            #[cfg(not(feature = "official-server"))]
f6115638aa92 enable local admins for non-official servers
alfadur
parents: 15075
diff changeset
   205
            client.set_is_admin(data.is_local_admin);
f6115638aa92 enable local admins for non-official servers
alfadur
parents: 15075
diff changeset
   206
15441
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   207
            #[cfg(feature = "official-server")]
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   208
            {
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   209
                client.set_is_registered(info.is_registered);
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   210
                client.set_is_admin(info.is_admin);
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   211
                client.set_is_contributor(info.is_contributor);
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   212
            }
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   213
14693
6a2e13e36b7f add server anteroom
alfadur <mail@none>
parents: 14686
diff changeset
   214
            self.clients.insert(client_id, client);
13119
1e39b8749072 separated the server logic from all the async io mess.
alfadur
parents: 12852
diff changeset
   215
        }
12126
4348997e502b Refactor code to add more structure to it
unc0rr
parents:
diff changeset
   216
    }
12127
36ac9c075d0d - Use netbuf buffers for client connection stream
unc0rr
parents: 12126
diff changeset
   217
14673
08a8605bafaf Server action refactoring part 4 of N
alfadur <mail@none>
parents: 14672
diff changeset
   218
    pub fn remove_client(&mut self, client_id: ClientId) {
14696
8a45c90f4580 fix client removal
alfadur
parents: 14695
diff changeset
   219
        self.clients.remove(client_id);
12127
36ac9c075d0d - Use netbuf buffers for client connection stream
unc0rr
parents: 12126
diff changeset
   220
    }
36ac9c075d0d - Use netbuf buffers for client connection stream
unc0rr
parents: 12126
diff changeset
   221
15441
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   222
    pub fn get_greetings(&self, client: &HwClient) -> &str {
61a0bd0bb021 refactor root handler
alfadur
parents: 15439
diff changeset
   223
        if client.protocol_number < self.latest_protocol {
14783
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   224
            &self.greetings.for_old_protocols
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   225
        } else {
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   226
            &self.greetings.for_latest_protocol
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   227
        }
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   228
    }
b3adc030104b implement server vars
alfadur
parents: 14781
diff changeset
   229
14504
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   230
    #[inline]
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   231
    pub fn get_client_nick(&self, client_id: ClientId) -> &str {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   232
        &self.clients[client_id].nick
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   233
    }
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   234
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   235
    #[inline]
14504
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   236
    pub fn create_room(
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   237
        &mut self,
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   238
        creator_id: ClientId,
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   239
        name: String,
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   240
        password: Option<String>,
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   241
    ) -> Result<(&HwClient, &HwRoom), CreateRoomError> {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   242
        use CreateRoomError::*;
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   243
        if utils::is_name_illegal(&name) {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   244
            Err(InvalidName)
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   245
        } else if self.has_room(&name) {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   246
            Err(AlreadyExists)
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   247
        } else {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   248
            Ok(create_room(
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   249
                &mut self.clients[creator_id],
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   250
                &mut self.rooms,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   251
                name,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   252
                password,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   253
            ))
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   254
        }
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   255
    }
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   256
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   257
    pub fn join_room(
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   258
        &mut self,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   259
        client_id: ClientId,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   260
        room_id: RoomId,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   261
    ) -> Result<(&HwClient, &HwRoom, impl Iterator<Item = &HwClient> + Clone), JoinRoomError> {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   262
        use JoinRoomError::*;
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   263
        let room = &mut self.rooms[room_id];
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   264
        let client = &mut self.clients[client_id];
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   265
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   266
        if client.protocol_number != room.protocol_number {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   267
            Err(WrongProtocol)
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   268
        } else if room.is_join_restricted() {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   269
            Err(Restricted)
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   270
        } else if room.players_number == u8::max_value() {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   271
            Err(Full)
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   272
        } else {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   273
            move_to_room(client, room);
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   274
            let room_id = room.id;
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   275
            Ok((
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   276
                &self.clients[client_id],
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   277
                &self.rooms[room_id],
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   278
                self.clients.iter().map(|(_, c)| c),
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   279
            ))
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   280
        }
14504
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   281
    }
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   282
14671
455865ccd36c Server action refactoring part 2 of N
alfadur <mail@none>
parents: 14504
diff changeset
   283
    #[inline]
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   284
    pub fn join_room_by_name(
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   285
        &mut self,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   286
        client_id: ClientId,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   287
        room_name: &str,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   288
    ) -> Result<(&HwClient, &HwRoom, impl Iterator<Item = &HwClient> + Clone), JoinRoomError> {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   289
        use JoinRoomError::*;
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   290
        let room = self.rooms.iter().find(|(_, r)| r.name == room_name);
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   291
        if let Some((_, room)) = room {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   292
            let room_id = room.id;
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   293
            self.join_room(client_id, room_id)
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   294
        } else {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   295
            Err(DoesntExist)
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   296
        }
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   297
    }
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   298
15482
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   299
    pub fn leave_room(&mut self, client_id: ClientId) -> Result<LeaveRoomResult, LeaveRoomError> {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   300
        let client = &mut self.clients[client_id];
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   301
        if let Some(room_id) = client.room_id {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   302
            let room = &mut self.rooms[room_id];
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   303
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   304
            room.players_number -= 1;
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   305
            client.room_id = None;
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   306
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   307
            let is_empty = room.players_number == 0;
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   308
            let is_fixed = room.is_fixed();
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   309
            let was_master = room.master_id == Some(client_id);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   310
            let was_in_game = client.is_in_game();
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   311
            let mut removed_teams = vec![];
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   312
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   313
            if is_empty && !is_fixed {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   314
                if client.is_ready() && room.ready_players_number > 0 {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   315
                    room.ready_players_number -= 1;
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   316
                }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   317
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   318
                removed_teams = room
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   319
                    .client_teams(client.id)
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   320
                    .map(|t| t.name.clone())
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   321
                    .collect();
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   322
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   323
                for team_name in &removed_teams {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   324
                    room.remove_team(team_name);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   325
                }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   326
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   327
                if client.is_master() && !is_fixed {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   328
                    client.set_is_master(false);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   329
                    room.master_id = None;
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   330
                }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   331
            }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   332
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   333
            client.set_is_ready(false);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   334
            client.set_is_in_game(false);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   335
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   336
            if !is_fixed {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   337
                if room.players_number == 0 {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   338
                    self.rooms.remove(room_id);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   339
                } else if room.master_id == None {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   340
                    let new_master_id = self.room_clients(room_id).next();
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   341
                    if let Some(new_master_id) = new_master_id {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   342
                        let room = &mut self.rooms[room_id];
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   343
                        room.master_id = Some(new_master_id);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   344
                        let new_master = &mut self.clients[new_master_id];
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   345
                        new_master.set_is_master(true);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   346
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   347
                        if room.protocol_number < 42 {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   348
                            room.name = new_master.nick.clone();
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   349
                        }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   350
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   351
                        room.set_join_restriction(false);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   352
                        room.set_team_add_restriction(false);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   353
                        room.set_unregistered_players_restriction(true);
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   354
                    }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   355
                }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   356
            }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   357
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   358
            if is_empty && !is_fixed {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   359
                Ok(LeaveRoomResult::RoomRemoved)
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   360
            } else {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   361
                Ok(LeaveRoomResult::RoomRemains {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   362
                    is_empty,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   363
                    was_master,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   364
                    was_in_game,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   365
                    new_master: self.rooms[room_id].master_id,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   366
                    removed_teams,
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   367
                })
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   368
            }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   369
        } else {
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   370
            Err(LeaveRoomError::NoRoom)
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   371
        }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   372
    }
4cc9ec732392 refactor some of the room handler
alfadur
parents: 15441
diff changeset
   373
15487
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   374
    pub fn change_master(
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   375
        &mut self,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   376
        client_id: ClientId,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   377
        room_id: RoomId,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   378
        new_master_nick: String,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   379
    ) -> Result<ChangeMasterResult, ChangeMasterError> {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   380
        let client = &mut self.clients[client_id];
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   381
        let room = &mut self.rooms[room_id];
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   382
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   383
        if client.is_admin() || room.master_id == Some(client_id) {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   384
            let new_master_id = self
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   385
                .clients
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   386
                .iter()
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   387
                .find(|(_, c)| c.nick == new_master_nick)
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   388
                .map(|(id, _)| id);
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   389
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   390
            match new_master_id {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   391
                Some(new_master_id) if new_master_id == client_id => {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   392
                    Err(ChangeMasterError::AlreadyMaster)
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   393
                }
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   394
                Some(new_master_id) => {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   395
                    let new_master = &mut self.clients[new_master_id];
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   396
                    if new_master.room_id == Some(room_id) {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   397
                        self.clients[new_master_id].set_is_master(true);
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   398
                        let old_master_id = room.master_id;
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   399
                        if let Some(master_id) = old_master_id {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   400
                            self.clients[master_id].set_is_master(false);
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   401
                        }
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   402
                        room.master_id = Some(new_master_id);
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   403
                        Ok(ChangeMasterResult {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   404
                            old_master_id,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   405
                            new_master_id,
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   406
                        })
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   407
                    } else {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   408
                        Err(ChangeMasterError::ClientNotInRoom)
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   409
                    }
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   410
                }
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   411
                None => Err(ChangeMasterError::NoClient),
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   412
            }
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   413
        } else {
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   414
            Err(ChangeMasterError::NoAccess)
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   415
        }
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   416
    }
91f0c5ec37b5 move change_master into the server
alfadur
parents: 15482
diff changeset
   417
15492
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   418
    pub fn start_game(&mut self, room_id: RoomId) -> Result<Vec<String>, StartGameError> {
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   419
        let (room_clients, room_nicks): (Vec<_>, Vec<_>) = self
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   420
            .clients
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   421
            .iter()
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   422
            .map(|(id, c)| (id, c.nick.clone()))
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   423
            .unzip();
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   424
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   425
        let room = &mut self.rooms[room_id];
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   426
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   427
        if !room.has_multiple_clans() {
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   428
            Err(StartGameError::NotEnoughClans)
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   429
        } else if room.protocol_number <= 43 && room.players_number != room.ready_players_number {
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   430
            Err(StartGameError::NotReady)
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   431
        } else if room.game_info.is_some() {
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   432
            Err(StartGameError::AlreadyInGame)
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   433
        } else {
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   434
            room.start_round();
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   435
            for id in room_clients {
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   436
                let c = &mut self.clients[id];
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   437
                c.set_is_in_game(true);
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   438
                c.team_indices = room.client_team_indices(c.id);
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   439
            }
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   440
            Ok(room_nicks)
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   441
        }
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   442
    }
395be40faa51 move start_game into the server
alfadur
parents: 15487
diff changeset
   443
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   444
    #[inline]
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   445
    pub fn set_var(&mut self, client_id: ClientId, var: ServerVar) -> Result<(), AccessError> {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   446
        if self.clients[client_id].is_admin() {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   447
            match var {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   448
                ServerVar::MOTDNew(msg) => self.greetings.for_latest_protocol = msg,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   449
                ServerVar::MOTDOld(msg) => self.greetings.for_old_protocols = msg,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   450
                ServerVar::LatestProto(n) => self.latest_protocol = n,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   451
            }
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   452
            Ok(())
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   453
        } else {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   454
            Err(AccessError())
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   455
        }
14671
455865ccd36c Server action refactoring part 2 of N
alfadur <mail@none>
parents: 14504
diff changeset
   456
    }
455865ccd36c Server action refactoring part 2 of N
alfadur <mail@none>
parents: 14504
diff changeset
   457
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   458
    #[inline]
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   459
    pub fn get_vars(&self, client_id: ClientId) -> Result<[ServerVar; 3], AccessError> {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   460
        if self.clients[client_id].is_admin() {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   461
            Ok([
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   462
                ServerVar::MOTDNew(self.greetings.for_latest_protocol.clone()),
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   463
                ServerVar::MOTDOld(self.greetings.for_old_protocols.clone()),
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   464
                ServerVar::LatestProto(self.latest_protocol),
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   465
            ])
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   466
        } else {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   467
            Err(AccessError())
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   468
        }
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   469
    }
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   470
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   471
    pub fn get_used_protocols(&self, client_id: ClientId) -> Result<Vec<u16>, AccessError> {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   472
        if self.clients[client_id].is_admin() {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   473
            let mut protocols: HashSet<_> = self
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   474
                .clients
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   475
                .iter()
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   476
                .map(|(_, c)| c.protocol_number)
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   477
                .chain(self.rooms.iter().map(|(_, r)| r.protocol_number))
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   478
                .collect();
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   479
            let mut protocols: Vec<_> = protocols.drain().collect();
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   480
            protocols.sort();
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   481
            Ok(protocols)
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   482
        } else {
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   483
            Err(AccessError())
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   484
        }
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   485
    }
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   486
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   487
    #[inline]
13416
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   488
    pub fn has_room(&self, name: &str) -> bool {
14697
f64e21f164a5 fix some warnings
alfadur
parents: 14696
diff changeset
   489
        self.find_room(name).is_some()
13416
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   490
    }
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   491
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   492
    #[inline]
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   493
    pub fn find_room(&self, name: &str) -> Option<&HwRoom> {
14457
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   494
        self.rooms
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   495
            .iter()
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   496
            .find_map(|(_, r)| Some(r).filter(|r| r.name == name))
13416
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   497
    }
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   498
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   499
    pub fn find_room_mut(&mut self, name: &str) -> Option<&mut HwRoom> {
14457
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   500
        self.rooms
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   501
            .iter_mut()
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   502
            .find_map(|(_, r)| Some(r).filter(|r| r.name == name))
13416
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   503
    }
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   504
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   505
    pub fn find_client(&self, nick: &str) -> Option<&HwClient> {
14457
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   506
        self.clients
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   507
            .iter()
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   508
            .find_map(|(_, c)| Some(c).filter(|c| c.nick == nick))
13478
d79795acaa73 Mostly implement voting
alfadur
parents: 13445
diff changeset
   509
    }
d79795acaa73 Mostly implement voting
alfadur
parents: 13445
diff changeset
   510
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   511
    pub fn find_client_mut(&mut self, nick: &str) -> Option<&mut HwClient> {
14457
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   512
        self.clients
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   513
            .iter_mut()
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   514
            .find_map(|(_, c)| Some(c).filter(|c| c.nick == nick))
13478
d79795acaa73 Mostly implement voting
alfadur
parents: 13445
diff changeset
   515
    }
d79795acaa73 Mostly implement voting
alfadur
parents: 13445
diff changeset
   516
14789
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   517
    pub fn all_clients(&self) -> impl Iterator<Item = ClientId> + '_ {
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   518
        self.clients.iter().map(|(id, _)| id)
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   519
    }
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   520
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   521
    pub fn filter_clients<'a, F>(&'a self, f: F) -> impl Iterator<Item = ClientId> + 'a
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   522
    where
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   523
        F: Fn(&(usize, &HwClient)) -> bool + 'a,
14789
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   524
    {
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   525
        self.clients.iter().filter(f).map(|(_, c)| c.id)
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   526
    }
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   527
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   528
    pub fn filter_rooms<'a, F>(&'a self, f: F) -> impl Iterator<Item = RoomId> + 'a
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   529
    where
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   530
        F: Fn(&(usize, &HwRoom)) -> bool + 'a,
14789
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   531
    {
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   532
        self.rooms.iter().filter(f).map(|(_, c)| c.id)
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   533
    }
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   534
14781
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   535
    pub fn collect_clients<F>(&self, f: F) -> Vec<ClientId>
14457
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   536
    where
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   537
        F: Fn(&(usize, &HwClient)) -> bool,
14457
98ef2913ec73 Apply rustfmt to all files
unc0rr
parents: 14415
diff changeset
   538
    {
14789
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   539
        self.filter_clients(f).collect()
13416
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   540
    }
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   541
14781
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   542
    pub fn collect_nicks<F>(&self, f: F) -> Vec<String>
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   543
    where
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   544
        F: Fn(&(usize, &HwClient)) -> bool,
14781
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   545
    {
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   546
        self.clients
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   547
            .iter()
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   548
            .filter(f)
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   549
            .map(|(_, c)| c.nick.clone())
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   550
            .collect()
14694
25c564f77b7d remove lobby room
alfadur <mail@none>
parents: 14693
diff changeset
   551
    }
25c564f77b7d remove lobby room
alfadur <mail@none>
parents: 14693
diff changeset
   552
14789
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   553
    pub fn lobby_clients(&self) -> impl Iterator<Item = ClientId> + '_ {
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   554
        self.filter_clients(|(_, c)| c.room_id == None)
14781
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   555
    }
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   556
14789
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   557
    pub fn room_clients(&self, room_id: RoomId) -> impl Iterator<Item = ClientId> + '_ {
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   558
        self.filter_clients(move |(_, c)| c.room_id == Some(room_id))
13416
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   559
    }
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   560
14789
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   561
    pub fn protocol_clients(&self, protocol: u16) -> impl Iterator<Item = ClientId> + '_ {
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   562
        self.filter_clients(move |(_, c)| c.protocol_number == protocol)
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   563
    }
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   564
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   565
    pub fn protocol_rooms(&self, protocol: u16) -> impl Iterator<Item = RoomId> + '_ {
18240b308505 implement stats message
alfadur
parents: 14786
diff changeset
   566
        self.filter_rooms(move |(_, r)| r.protocol_number == protocol)
13416
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   567
    }
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   568
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   569
    pub fn other_clients_in_room(&self, self_id: ClientId) -> Vec<ClientId> {
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   570
        let room_id = self.clients[self_id].room_id;
14781
01f8ab45f806 fix lobby joining
alfadur
parents: 14780
diff changeset
   571
        self.collect_clients(|(id, c)| *id != self_id && c.room_id == room_id)
13416
cdf69667593b partial room implementation
alfadur
parents: 13119
diff changeset
   572
    }
14786
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   573
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   574
    pub fn is_registered_only(&self) -> bool {
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   575
        self.flags.contains(ServerFlags::REGISTERED_ONLY)
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   576
    }
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   577
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   578
    pub fn set_is_registered_only(&mut self, value: bool) {
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   579
        self.flags.set(ServerFlags::REGISTERED_ONLY, value)
8ecdb5c6bb2a implement info, registered only & super power messages
alfadur
parents: 14783
diff changeset
   580
    }
13445
d3c86ade3d4d Send the rnd reply to the room only.
Marcin Mielniczuk <marmistrz.dev@zoho.eu>
parents: 13442
diff changeset
   581
}
14504
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   582
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   583
fn allocate_room(rooms: &mut Slab<HwRoom>) -> &mut HwRoom {
14504
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   584
    let entry = rooms.vacant_entry();
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   585
    let room = HwRoom::new(entry.key());
14504
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   586
    entry.insert(room)
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   587
}
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   588
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   589
fn create_room<'a, 'b>(
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   590
    client: &'a mut HwClient,
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   591
    rooms: &'b mut Slab<HwRoom>,
14504
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   592
    name: String,
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   593
    password: Option<String>,
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   594
) -> (&'a HwClient, &'b HwRoom) {
14504
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   595
    let room = allocate_room(rooms);
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   596
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   597
    room.master_id = Some(client.id);
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   598
    room.name = name;
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   599
    room.password = password;
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   600
    room.protocol_number = client.protocol_number;
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   601
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   602
    room.players_number = 1;
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   603
    room.ready_players_number = 1;
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   604
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   605
    client.room_id = Some(room.id);
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   606
    client.set_is_master(true);
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   607
    client.set_is_ready(true);
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   608
    client.set_is_joined_mid_game(false);
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   609
15439
a158ff8f84ef refactor the lobby handler
alfadur
parents: 15176
diff changeset
   610
    (client, room)
14504
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   611
}
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   612
15075
e935b1ad23f3 normalize type names
alfadur
parents: 15074
diff changeset
   613
fn move_to_room(client: &mut HwClient, room: &mut HwRoom) {
14504
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   614
    debug_assert!(client.room_id != Some(room.id));
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   615
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   616
    room.players_number += 1;
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   617
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   618
    client.room_id = Some(room.id);
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   619
    client.set_is_joined_mid_game(room.game_info.is_some());
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   620
    client.set_is_in_game(room.game_info.is_some());
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   621
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   622
    if let Some(ref mut info) = room.game_info {
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   623
        let teams = info.client_teams(client.id);
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   624
        client.teams_in_game = teams.clone().count() as u8;
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   625
        client.clan = teams.clone().next().map(|t| t.color);
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   626
        let team_names: Vec<_> = teams.map(|t| t.name.clone()).collect();
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   627
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   628
        if !team_names.is_empty() {
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   629
            info.left_teams.retain(|name| !team_names.contains(&name));
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   630
            info.teams_in_game += team_names.len() as u8;
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   631
            room.teams = info
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   632
                .teams_at_start
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   633
                .iter()
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   634
                .filter(|(_, t)| !team_names.contains(&t.name))
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   635
                .cloned()
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   636
                .collect();
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   637
        }
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   638
    }
6cc0fce249f9 Server action refactoring part 1 of N
alfadur <mail@none>
parents: 14457
diff changeset
   639
}