team04_server/messages/
error.rs

1use super::*;
2
3pub mod error_code {
4    pub const CHARACTER_TAKEN: &str = "CHARACTER_TAKEN";
5    pub const GAME_ALREADY_STARTED: &str = "GAME_ALREADY_STARTED";
6    pub const LOBBY_FULL: &str = "LOBBY_FULL";
7    pub const NAME_IN_USE: &str = "NAME_IN_USE";
8    pub const NO_LOBBY_WITH_ID: &str = "NO_LOBBY_WITH_ID";
9    pub const NAME_TOO_LONG: &str = "NAME_TOO_LONG";
10    pub const MESSAGE_AT_WRONG_TIME_LIGHTSABER_CHOSEN: &str = "MSG_AT_WRONG_TIME_LIGHTSABER_CHOSEN";
11    pub const MESSAGE_AT_WRONG_TIME_UNIT_CHOSEN: &str = "MSG_AT_WRONG_TIME_UNIT_CHOSEN";
12    pub const MESSAGE_AT_WRONG_TIME_PLACEMENT_COMPLETE: &str =
13        "MSG_AT_WRONG_TIME_PLACEMENT_COMPLETE";
14    pub const UNIT_CHOSEN_NOT_IN_OPTIONS: &str = "UNIT_CHOSEN_NOT_IN_OPTIONS";
15    pub const INVALID_PLACEMENT_UNITS: &str = "INVALID_PLACEMENT_UNITS";
16    pub const INVALID_PLACEMENT_UNIT_ON_ROCK: &str = "INVALID_PLACEMENT_UNITS";
17    pub const INVALID_PLACEMENT_COORD_OUT_OF_BOUNDS: &str = "INVALID_PLACEMENT_COORD_OUT_OF_BOUNDS";
18    pub const INVALID_PLACEMENT_UNIT_WRONG_BOARD_HALF: &str =
19        "INVALID_PLACEMENT_UNIT_WRONG_BOARD_HALF";
20    pub const INVALID_PLACEMENT_TWO_UNITS_ON_ONE_FIELD: &str =
21        "INVALID_PLACEMENT_TWO_UNITS_ON_ONE_FIELD";
22    pub const NO_PLAYER_WITH_ID: &str = "NO_PLAYER_WITH_ID";
23    pub const WRONG_RECONNECT_TOKEN: &str = "WRONG_RECONNECT_TOKEN";
24    pub const GAME_NOT_STARTED: &str = "GAME_NOT_STARTED";
25}
26
27pub struct ErrorMessage<'a> {
28    /// This should be a human readable description of the error.
29    pub reason: &'a str,
30
31    /// This field does not appear in the spec, but something similar is required for
32    /// letting the client handle error conditions. This should be a machine readable
33    /// identifier, like `"CHARACTER_TAKEN"`.
34    /// It **is** serialized in `#[cfg(test)]`, so that
35    /// tests can ensure the correct error case was triggered.
36    pub code: &'static str,
37}
38
39impl<'a> MessageTx for ErrorMessage<'a> {
40    fn serialize(&self) -> String {
41        #[derive(Serialize)]
42        #[serde(rename_all = "camelCase")]
43        struct ErrorJson<'b> {
44            message_type: &'static str,
45            reason: &'b str,
46            #[cfg(test)]
47            code: &'b str,
48        }
49
50        let message = ErrorJson {
51            message_type: "ERROR",
52            reason: self.reason,
53            #[cfg(test)]
54            code: self.code,
55        };
56
57        serialize(&message)
58    }
59}
60
61pub struct ErrorInvalid<'a> {
62    pub original_message: &'a str,
63}
64
65impl<'a> MessageTx for ErrorInvalid<'a> {
66    fn serialize(&self) -> String {
67        #[derive(Serialize)]
68        #[serde(rename_all = "camelCase")]
69        struct InvalidJson<'b> {
70            message_type: &'static str,
71            invalid_message: &'b str,
72        }
73
74        let message = InvalidJson {
75            message_type: "INVALID_MESSAGE",
76            invalid_message: self.original_message,
77        };
78
79        serialize(&message)
80    }
81}