lichess_api/model/challenges/
mod.rs

1pub mod accept;
2pub mod add_time;
3pub mod ai;
4pub mod cancel;
5pub mod create;
6pub mod decline;
7pub mod list;
8pub mod open;
9pub mod start_clocks;
10
11use crate::model::{Color, Days, GameCompat, Speed, Title, Variant, VariantKey};
12use serde::{Deserialize, Serialize};
13use serde_with::skip_serializing_none;
14
15#[derive(Clone, Debug, Serialize)]
16pub struct OpenChallenge {
17    #[serde(flatten)]
18    pub base: ChallengeBase,
19    pub name: String,
20    pub rules: String,
21    pub users: String,
22}
23
24#[derive(Clone, Debug, Serialize)]
25#[serde(rename_all = "camelCase")]
26pub struct CreateChallenge {
27    #[serde(flatten)]
28    pub base: ChallengeBase,
29    pub rated: bool,
30    pub keep_alive_stream: bool,
31    pub accept_by_token: Option<String>,
32    pub message: Option<String>,
33    pub rules: String,
34}
35
36#[derive(Clone, Debug, PartialEq, Eq, Serialize)]
37#[serde(rename_all = "camelCase")]
38pub enum Rules {
39    NoAbort,
40    NoRematch,
41    NoGiveTime,
42    NoClaimWin,
43}
44
45#[derive(Clone, Debug, Serialize)]
46pub struct AIChallenge {
47    #[serde(flatten)]
48    pub base: ChallengeBase,
49    pub level: u32,
50    pub color: Color,
51}
52
53#[skip_serializing_none]
54#[derive(Clone, Debug, Serialize)]
55pub struct ChallengeBase {
56    #[serde(rename = "clock.limit")]
57    pub clock_limit: Option<u32>,
58    #[serde(rename = "clock.increment")]
59    pub clock_increment: Option<u32>,
60    pub days: Option<Days>,
61    pub variant: VariantKey,
62    pub fen: Option<String>,
63}
64
65#[derive(Clone, Debug, Deserialize, Serialize)]
66#[serde(rename_all = "camelCase")]
67pub struct ChallengeOpenJson {
68    pub id: String,
69    pub url: String,
70    pub status: Status,
71    pub challenger: Option<ChallengeUser>,
72    pub dest_user: Option<ChallengeUser>,
73    pub variant: Variant,
74    pub rated: bool,
75    pub speed: Speed,
76    pub time_control: TimeControl,
77    pub color: Color,
78    pub final_color: Option<Color>,
79    pub perf: Perf,
80    #[serde(skip_serializing_if = "Option::is_none")]
81    pub initial_fen: Option<String>,
82    pub url_white: String,
83    pub url_black: String,
84    pub open: OpenChallengeUsers,
85}
86
87#[derive(Clone, Debug, Deserialize, Serialize, Default)]
88#[serde(rename_all = "camelCase")]
89pub struct OpenChallengeUsers {
90    #[serde(skip_serializing_if = "Option::is_none")]
91    pub user_ids: Option<Vec<String>>,
92}
93
94#[derive(Clone, Debug, Deserialize, Serialize)]
95#[serde(rename_all = "camelCase")]
96pub struct ChallengeDeclinedJson {
97    #[serde(flatten)]
98    pub base: ChallengeJson,
99    pub decline_reason: String,
100    pub decline_reason_key: DeclineReasonKey,
101}
102
103#[derive(Clone, Debug, Deserialize, PartialEq, Eq, Serialize)]
104#[serde(rename_all = "lowercase")]
105pub enum DeclineReasonKey {
106    Generic,
107    Later,
108    #[serde(rename = "toofast")]
109    TooFast,
110    #[serde(rename = "tooslow")]
111    TooSlow,
112    #[serde(rename = "timecontrol")]
113    TimeControl,
114    Rated,
115    Casual,
116    Standard,
117    Variant,
118    #[serde(rename = "nobot")]
119    NoBot,
120    #[serde(rename = "onlybot")]
121    OnlyBot,
122}
123
124#[skip_serializing_none]
125#[derive(Clone, Debug, Deserialize, Serialize)]
126#[serde(rename_all = "camelCase")]
127pub struct ChallengeJson {
128    #[serde(flatten)]
129    pub base: ChallengeJsonBase,
130    pub initial_fen: Option<String>,
131    pub decline_reason: Option<String>,
132}
133
134#[skip_serializing_none]
135#[derive(Clone, Debug, Deserialize, Serialize)]
136#[serde(rename_all = "camelCase")]
137pub struct ChallengeJsonBase {
138    pub id: String,
139    pub url: String,
140    pub color: Color,
141    pub direction: Option<Direction>,
142    pub time_control: TimeControl,
143    pub variant: Variant,
144
145    /// The api docs suggest this is non-nullable,
146    /// this is true only if the user does not accept anonymous challengers.
147    pub challenger: Option<ChallengeUser>,
148    pub dest_user: Option<ChallengeUser>,
149    pub perf: Perf,
150    pub rated: bool,
151    pub speed: Speed,
152    pub status: Status,
153    pub final_color: Option<Color>,
154}
155
156#[derive(Clone, Debug, Deserialize, PartialEq, Eq, Serialize)]
157#[serde(rename_all = "camelCase")]
158pub enum Direction {
159    In,
160    Out,
161}
162
163#[derive(Clone, Debug, Deserialize, Serialize)]
164pub struct Perf {
165    pub icon: String,
166    pub name: String,
167}
168
169#[derive(Clone, Debug, Deserialize, PartialEq, Eq, Serialize)]
170#[serde(rename_all = "camelCase")]
171pub enum Status {
172    Created,
173    Offline,
174    Canceled,
175    Declined,
176    Accepted,
177}
178
179#[derive(Clone, Debug, Deserialize, Serialize)]
180#[serde(rename_all = "camelCase")]
181pub struct ChallengeEvent {
182    #[serde(rename = "type")]
183    pub event_type: String, // Always "challenge"
184    pub challenge: ChallengeJson,
185    pub compat: Option<GameCompat>,
186}
187
188#[derive(Clone, Debug, Deserialize, Serialize)]
189#[serde(rename_all = "camelCase")]
190pub struct ChallengeCanceledEvent {
191    #[serde(rename = "type")]
192    pub event_type: String, // Always "challengeCanceled"
193    pub challenge: ChallengeJson,
194}
195
196#[derive(Clone, Debug, Deserialize, Serialize)]
197#[serde(rename_all = "camelCase")]
198pub struct ChallengeDeclinedEvent {
199    #[serde(rename = "type")]
200    pub event_type: String, // Always "challengeDeclined"
201    pub challenge: ChallengeDeclinedJson,
202}
203
204#[derive(Clone, Debug, Deserialize, Serialize)]
205#[serde(tag = "type")]
206#[serde(rename_all = "camelCase")]
207#[serde(rename_all_fields = "camelCase")]
208pub enum TimeControl {
209    Clock {
210        increment: u32,
211        limit: u32,
212        show: String,
213    },
214    Correspondence {
215        days_per_turn: u32,
216    },
217    Unlimited,
218}
219
220#[derive(Clone, Debug, Deserialize, Serialize)]
221pub struct ChallengeUser {
222    pub id: String,
223    pub name: String,
224    pub rating: u32,
225    pub title: Option<Title>,
226    #[serde(skip_serializing_if = "Option::is_none")]
227    pub flair: Option<String>,
228    #[serde(skip_serializing_if = "Option::is_none")]
229    pub patron: Option<bool>,
230    #[serde(skip_serializing_if = "Option::is_none")]
231    pub provisional: Option<bool>,
232    #[serde(skip_serializing_if = "Option::is_none")]
233    pub online: Option<bool>,
234    #[serde(skip_serializing_if = "Option::is_none")]
235    pub lag: Option<u32>,
236}