twilight_http/request/guild/
update_guild.rs1use crate::{
2 client::Client,
3 error::Error,
4 request::{self, AuditLogReason, Nullable, Request, TryIntoRequest},
5 response::{Response, ResponseFuture},
6 routing::Route,
7};
8use serde::Serialize;
9use std::future::IntoFuture;
10use twilight_model::{
11 guild::{
12 DefaultMessageNotificationLevel, ExplicitContentFilter, PartialGuild, SystemChannelFlags,
13 VerificationLevel,
14 },
15 id::{
16 Id,
17 marker::{ChannelMarker, GuildMarker, UserMarker},
18 },
19};
20use twilight_validate::request::{
21 ValidationError, audit_reason as validate_audit_reason, guild_name as validate_guild_name,
22};
23
24#[derive(Serialize)]
25struct UpdateGuildFields<'a> {
26 #[serde(skip_serializing_if = "Option::is_none")]
27 afk_channel_id: Option<Nullable<Id<ChannelMarker>>>,
28 #[serde(skip_serializing_if = "Option::is_none")]
29 afk_timeout: Option<u64>,
30 #[serde(skip_serializing_if = "Option::is_none")]
31 banner: Option<Nullable<&'a str>>,
32 #[serde(skip_serializing_if = "Option::is_none")]
33 default_message_notifications: Option<Nullable<DefaultMessageNotificationLevel>>,
34 #[serde(skip_serializing_if = "Option::is_none")]
35 discovery_splash: Option<Nullable<&'a str>>,
36 #[serde(skip_serializing_if = "Option::is_none")]
37 explicit_content_filter: Option<Nullable<ExplicitContentFilter>>,
38 #[serde(skip_serializing_if = "Option::is_none")]
39 features: Option<&'a [&'a str]>,
40 #[serde(skip_serializing_if = "Option::is_none")]
41 icon: Option<Nullable<&'a str>>,
42 #[serde(skip_serializing_if = "Option::is_none")]
43 name: Option<&'a str>,
44 #[serde(skip_serializing_if = "Option::is_none")]
45 owner_id: Option<Id<UserMarker>>,
46 #[serde(skip_serializing_if = "Option::is_none")]
47 splash: Option<Nullable<&'a str>>,
48 #[serde(skip_serializing_if = "Option::is_none")]
49 system_channel_id: Option<Nullable<Id<ChannelMarker>>>,
50 #[serde(skip_serializing_if = "Option::is_none")]
51 system_channel_flags: Option<Nullable<SystemChannelFlags>>,
52 #[serde(skip_serializing_if = "Option::is_none")]
53 verification_level: Option<Nullable<VerificationLevel>>,
54 #[serde(skip_serializing_if = "Option::is_none")]
55 rules_channel_id: Option<Nullable<Id<ChannelMarker>>>,
56 #[serde(skip_serializing_if = "Option::is_none")]
57 public_updates_channel_id: Option<Nullable<Id<ChannelMarker>>>,
58 #[serde(skip_serializing_if = "Option::is_none")]
59 preferred_locale: Option<Nullable<&'a str>>,
60 #[serde(skip_serializing_if = "Option::is_none")]
61 premium_progress_bar_enabled: Option<bool>,
62}
63
64#[must_use = "requests must be configured and executed"]
70pub struct UpdateGuild<'a> {
71 fields: Result<UpdateGuildFields<'a>, ValidationError>,
72 guild_id: Id<GuildMarker>,
73 http: &'a Client,
74 reason: Result<Option<&'a str>, ValidationError>,
75}
76
77impl<'a> UpdateGuild<'a> {
78 pub(crate) const fn new(http: &'a Client, guild_id: Id<GuildMarker>) -> Self {
79 Self {
80 fields: Ok(UpdateGuildFields {
81 afk_channel_id: None,
82 afk_timeout: None,
83 banner: None,
84 default_message_notifications: None,
85 discovery_splash: None,
86 explicit_content_filter: None,
87 features: None,
88 icon: None,
89 name: None,
90 owner_id: None,
91 splash: None,
92 system_channel_id: None,
93 system_channel_flags: None,
94 verification_level: None,
95 rules_channel_id: None,
96 public_updates_channel_id: None,
97 preferred_locale: None,
98 premium_progress_bar_enabled: None,
99 }),
100 guild_id,
101 http,
102 reason: Ok(None),
103 }
104 }
105
106 pub const fn afk_channel_id(mut self, afk_channel_id: Option<Id<ChannelMarker>>) -> Self {
108 if let Ok(fields) = self.fields.as_mut() {
109 fields.afk_channel_id = Some(Nullable(afk_channel_id));
110 }
111
112 self
113 }
114
115 pub const fn afk_timeout(mut self, afk_timeout: u64) -> Self {
117 if let Ok(fields) = self.fields.as_mut() {
118 fields.afk_timeout = Some(afk_timeout);
119 }
120
121 self
122 }
123
124 pub const fn banner(mut self, banner: Option<&'a str>) -> Self {
131 if let Ok(fields) = self.fields.as_mut() {
132 fields.banner = Some(Nullable(banner));
133 }
134
135 self
136 }
137
138 pub const fn default_message_notifications(
143 mut self,
144 default_message_notifications: Option<DefaultMessageNotificationLevel>,
145 ) -> Self {
146 if let Ok(fields) = self.fields.as_mut() {
147 fields.default_message_notifications = Some(Nullable(default_message_notifications));
148 }
149
150 self
151 }
152
153 pub const fn discovery_splash(mut self, discovery_splash: Option<&'a str>) -> Self {
157 if let Ok(fields) = self.fields.as_mut() {
158 fields.discovery_splash = Some(Nullable(discovery_splash));
159 }
160
161 self
162 }
163
164 pub const fn explicit_content_filter(
166 mut self,
167 explicit_content_filter: Option<ExplicitContentFilter>,
168 ) -> Self {
169 if let Ok(fields) = self.fields.as_mut() {
170 fields.explicit_content_filter = Some(Nullable(explicit_content_filter));
171 }
172
173 self
174 }
175
176 pub const fn features(mut self, features: &'a [&'a str]) -> Self {
194 if let Ok(fields) = self.fields.as_mut() {
195 fields.features = Some(features);
196 }
197
198 self
199 }
200
201 pub const fn icon(mut self, icon: Option<&'a str>) -> Self {
209 if let Ok(fields) = self.fields.as_mut() {
210 fields.icon = Some(Nullable(icon));
211 }
212
213 self
214 }
215
216 pub fn name(mut self, name: &'a str) -> Self {
228 self.fields = self.fields.and_then(|mut fields| {
229 validate_guild_name(name)?;
230 fields.name.replace(name);
231
232 Ok(fields)
233 });
234
235 self
236 }
237
238 pub const fn owner_id(mut self, owner_id: Id<UserMarker>) -> Self {
242 if let Ok(fields) = self.fields.as_mut() {
243 fields.owner_id = Some(owner_id);
244 }
245
246 self
247 }
248
249 pub const fn splash(mut self, splash: Option<&'a str>) -> Self {
253 if let Ok(fields) = self.fields.as_mut() {
254 fields.splash = Some(Nullable(splash));
255 }
256
257 self
258 }
259
260 pub const fn system_channel(mut self, system_channel_id: Option<Id<ChannelMarker>>) -> Self {
262 if let Ok(fields) = self.fields.as_mut() {
263 fields.system_channel_id = Some(Nullable(system_channel_id));
264 }
265
266 self
267 }
268
269 pub const fn system_channel_flags(
271 mut self,
272 system_channel_flags: Option<SystemChannelFlags>,
273 ) -> Self {
274 if let Ok(fields) = self.fields.as_mut() {
275 fields.system_channel_flags = Some(Nullable(system_channel_flags));
276 }
277
278 self
279 }
280
281 pub const fn rules_channel(mut self, rules_channel_id: Option<Id<ChannelMarker>>) -> Self {
287 if let Ok(fields) = self.fields.as_mut() {
288 fields.rules_channel_id = Some(Nullable(rules_channel_id));
289 }
290
291 self
292 }
293
294 pub const fn public_updates_channel(
298 mut self,
299 public_updates_channel_id: Option<Id<ChannelMarker>>,
300 ) -> Self {
301 if let Ok(fields) = self.fields.as_mut() {
302 fields.public_updates_channel_id = Some(Nullable(public_updates_channel_id));
303 }
304
305 self
306 }
307
308 pub const fn preferred_locale(mut self, preferred_locale: Option<&'a str>) -> Self {
312 if let Ok(fields) = self.fields.as_mut() {
313 fields.preferred_locale = Some(Nullable(preferred_locale));
314 }
315
316 self
317 }
318
319 pub const fn verification_level(
325 mut self,
326 verification_level: Option<VerificationLevel>,
327 ) -> Self {
328 if let Ok(fields) = self.fields.as_mut() {
329 fields.verification_level = Some(Nullable(verification_level));
330 }
331
332 self
333 }
334
335 pub const fn premium_progress_bar_enabled(
337 mut self,
338 premium_progress_bar_enabled: bool,
339 ) -> Self {
340 if let Ok(fields) = self.fields.as_mut() {
341 fields.premium_progress_bar_enabled = Some(premium_progress_bar_enabled);
342 }
343
344 self
345 }
346}
347
348impl<'a> AuditLogReason<'a> for UpdateGuild<'a> {
349 fn reason(mut self, reason: &'a str) -> Self {
350 self.reason = validate_audit_reason(reason).and(Ok(Some(reason)));
351
352 self
353 }
354}
355
356impl IntoFuture for UpdateGuild<'_> {
357 type Output = Result<Response<PartialGuild>, Error>;
358
359 type IntoFuture = ResponseFuture<PartialGuild>;
360
361 fn into_future(self) -> Self::IntoFuture {
362 let http = self.http;
363
364 match self.try_into_request() {
365 Ok(request) => http.request(request),
366 Err(source) => ResponseFuture::error(source),
367 }
368 }
369}
370
371impl TryIntoRequest for UpdateGuild<'_> {
372 fn try_into_request(self) -> Result<Request, Error> {
373 let fields = self.fields.map_err(Error::validation)?;
374 let mut request = Request::builder(&Route::UpdateGuild {
375 guild_id: self.guild_id.get(),
376 })
377 .json(&fields);
378
379 if let Some(reason) = self.reason.map_err(Error::validation)? {
380 request = request.headers(request::audit_header(reason)?);
381 }
382
383 request.build()
384 }
385}