serenity/model/guild/guild_id.rs
1use std::fmt;
2
3#[cfg(feature = "model")]
4use futures::stream::Stream;
5
6#[cfg(feature = "model")]
7use crate::builder::{
8 AddMember,
9 Builder,
10 CreateChannel,
11 CreateCommand,
12 CreateScheduledEvent,
13 CreateSoundboard,
14 CreateSticker,
15 EditAutoModRule,
16 EditCommandPermissions,
17 EditGuild,
18 EditGuildIncidentActions,
19 EditGuildWelcomeScreen,
20 EditGuildWidget,
21 EditMember,
22 EditRole,
23 EditScheduledEvent,
24 EditSoundboard,
25 EditSticker,
26};
27#[cfg(all(feature = "cache", feature = "model"))]
28use crate::cache::{Cache, GuildRef};
29#[cfg(feature = "collector")]
30use crate::collector::{MessageCollector, ReactionCollector};
31#[cfg(feature = "collector")]
32use crate::gateway::ShardMessenger;
33#[cfg(feature = "model")]
34use crate::http::{CacheHttp, Http, UserPagination};
35#[cfg(feature = "model")]
36use crate::internal::prelude::*;
37#[cfg(feature = "model")]
38use crate::json::json;
39use crate::model::prelude::*;
40
41#[cfg(feature = "model")]
42impl GuildId {
43 /// Gets all auto moderation [`Rule`]s of this guild via HTTP.
44 ///
45 /// **Note**: Requires the [Manage Guild] permission.
46 ///
47 /// # Errors
48 ///
49 /// Returns an [`Error::Http`] if the guild is unavailable.
50 ///
51 /// [Manage Guild]: Permissions::MANAGE_GUILD
52 #[inline]
53 pub async fn automod_rules(self, http: impl AsRef<Http>) -> Result<Vec<Rule>> {
54 http.as_ref().get_automod_rules(self).await
55 }
56
57 /// Gets an auto moderation [`Rule`] of this guild by its ID via HTTP.
58 ///
59 /// **Note**: Requires the [Manage Guild] permission.
60 ///
61 /// # Errors
62 ///
63 /// Returns an [`Error::Http`] if a rule with the given ID does not exist.
64 ///
65 /// [Manage Guild]: Permissions::MANAGE_GUILD
66 #[inline]
67 pub async fn automod_rule(
68 self,
69 http: impl AsRef<Http>,
70 rule_id: impl Into<RuleId>,
71 ) -> Result<Rule> {
72 http.as_ref().get_automod_rule(self, rule_id.into()).await
73 }
74
75 /// Creates an auto moderation [`Rule`] in the guild.
76 ///
77 /// **Note**: Requires the [Manage Guild] permission.
78 ///
79 /// # Examples
80 ///
81 /// Create a custom keyword filter to block the message and timeout the author.
82 ///
83 /// ```
84 /// use std::time::Duration;
85 ///
86 /// use serenity::builder::EditAutoModRule;
87 /// use serenity::model::guild::automod::{Action, Trigger};
88 /// use serenity::model::id::GuildId;
89 ///
90 /// # async fn run() {
91 /// # use serenity::http::Http;
92 /// # let http: Http = unimplemented!();
93 /// let builder = EditAutoModRule::new()
94 /// .name("foobar filter")
95 /// .trigger(Trigger::Keyword {
96 /// strings: vec!["foo*".to_string(), "*bar".to_string()],
97 /// regex_patterns: vec![],
98 /// allow_list: vec![],
99 /// })
100 /// .actions(vec![
101 /// Action::BlockMessage {
102 /// custom_message: None,
103 /// },
104 /// Action::Timeout(Duration::from_secs(60)),
105 /// ]);
106 /// let _rule = GuildId::new(7).create_automod_rule(&http, builder).await;
107 /// # }
108 /// ```
109 ///
110 /// # Errors
111 ///
112 /// Returns [`Error::Http`] if the current user lacks permission, or if invalid data is given.
113 ///
114 /// [Manage Guild]: Permissions::MANAGE_GUILD
115 #[inline]
116 pub async fn create_automod_rule(
117 self,
118 cache_http: impl CacheHttp,
119 builder: EditAutoModRule<'_>,
120 ) -> Result<Rule> {
121 builder.execute(cache_http, (self, None)).await
122 }
123
124 /// Edit an auto moderation [`Rule`], given its Id.
125 ///
126 /// **Note**: Requires the [Manage Guild] permission.
127 ///
128 /// # Errors
129 ///
130 /// Returns [`Error::Http`] if the current user lacks permission, or if invalid data is given.
131 ///
132 /// [Manage Guild]: Permissions::MANAGE_GUILD
133 #[inline]
134 pub async fn edit_automod_rule(
135 self,
136 cache_http: impl CacheHttp,
137 rule_id: impl Into<RuleId>,
138 builder: EditAutoModRule<'_>,
139 ) -> Result<Rule> {
140 builder.execute(cache_http, (self, Some(rule_id.into()))).await
141 }
142
143 /// Deletes an auto moderation [`Rule`] from the guild.
144 ///
145 /// **Note**: Requires the [Manage Guild] permission.
146 ///
147 /// # Errors
148 ///
149 /// Returns [`Error::Http`] if the current user lacks permission, or if a rule with that Id
150 /// does not exist.
151 ///
152 /// [Manage Guild]: Permissions::MANAGE_GUILD
153 #[inline]
154 pub async fn delete_automod_rule(
155 self,
156 http: impl AsRef<Http>,
157 rule_id: impl Into<RuleId>,
158 ) -> Result<()> {
159 http.as_ref().delete_automod_rule(self, rule_id.into(), None).await
160 }
161
162 /// Adds a [`User`] to this guild with a valid OAuth2 access token.
163 ///
164 /// Returns the created [`Member`] object, or nothing if the user is already a member of the
165 /// guild.
166 ///
167 /// # Errors
168 ///
169 /// Returns [`Error::Http`] if the current user lacks permission, or if invalid data is given.
170 #[inline]
171 pub async fn add_member(
172 self,
173 cache_http: impl CacheHttp,
174 user_id: impl Into<UserId>,
175 builder: AddMember,
176 ) -> Result<Option<Member>> {
177 builder.execute(cache_http, (self, user_id.into())).await
178 }
179
180 /// Ban a [`User`] from the guild, deleting a number of days' worth of messages (`dmd`) between
181 /// the range 0 and 7.
182 ///
183 /// Refer to the documentation for [`Guild::ban`] for more information.
184 ///
185 /// **Note**: Requires the [Ban Members] permission.
186 ///
187 /// # Examples
188 ///
189 /// Ban a member and remove all messages they've sent in the last 4 days:
190 ///
191 /// ```rust,no_run
192 /// use serenity::model::id::{GuildId, UserId};
193 ///
194 /// # async fn run() -> Result<(), Box<dyn std::error::Error>> {
195 /// # use serenity::http::Http;
196 /// # let http: Http = unimplemented!();
197 /// # let user = UserId::new(1);
198 /// // assuming a `user` has already been bound
199 /// let _ = GuildId::new(81384788765712384).ban(&http, user, 4).await;
200 /// # Ok(())
201 /// # }
202 /// ```
203 ///
204 /// # Errors
205 ///
206 /// Returns a [`ModelError::DeleteMessageDaysAmount`] if the number of days' worth of messages
207 /// to delete is over the maximum.
208 ///
209 /// Also can return [`Error::Http`] if the current user lacks permission.
210 ///
211 /// [Ban Members]: Permissions::BAN_MEMBERS
212 #[inline]
213 pub async fn ban(self, http: impl AsRef<Http>, user: impl Into<UserId>, dmd: u8) -> Result<()> {
214 self.ban_(http, user.into(), dmd, None).await
215 }
216
217 /// Ban a [`User`] from the guild with a reason. Refer to [`Self::ban`] to further
218 /// documentation.
219 ///
220 /// # Errors
221 ///
222 /// In addition to the reasons [`Self::ban`] may return an error, may also return
223 /// [`Error::ExceededLimit`] if `reason` is too long.
224 #[inline]
225 pub async fn ban_with_reason(
226 self,
227 http: impl AsRef<Http>,
228 user: impl Into<UserId>,
229 dmd: u8,
230 reason: impl AsRef<str>,
231 ) -> Result<()> {
232 self.ban_(http, user.into(), dmd, Some(reason.as_ref())).await
233 }
234
235 async fn ban_(
236 self,
237 http: impl AsRef<Http>,
238 user: UserId,
239 dmd: u8,
240 reason: Option<&str>,
241 ) -> Result<()> {
242 if dmd > 7 {
243 return Err(Error::Model(ModelError::DeleteMessageDaysAmount(dmd)));
244 }
245
246 if let Some(reason) = reason {
247 if reason.chars().count() > 512 {
248 return Err(Error::ExceededLimit(reason.to_string(), 512));
249 }
250 }
251
252 http.as_ref().ban_user(self, user, dmd, reason).await
253 }
254
255 /// Bans multiple users from the guild, returning the users that were and weren't banned, and
256 /// optionally deleting messages that are younger than the provided `delete_message_seconds`.
257 ///
258 /// # Errors
259 ///
260 /// Errors if none of the users are banned or you do not have the
261 /// required [`BAN_MEMBERS`] and [`MANAGE_GUILD`] permissions.
262 ///
263 /// [`BAN_MEMBERS`]: Permissions::BAN_MEMBERS
264 /// [`MANAGE_GUILD`]: Permissions::MANAGE_GUILD
265 pub async fn bulk_ban(
266 self,
267 http: &Http,
268 user_ids: &[UserId],
269 delete_message_seconds: u32,
270 reason: Option<&str>,
271 ) -> Result<BulkBanResponse> {
272 #[derive(serde::Serialize)]
273 struct BulkBan<'a> {
274 user_ids: &'a [UserId],
275 delete_message_seconds: u32,
276 }
277
278 let map = BulkBan {
279 user_ids,
280 delete_message_seconds,
281 };
282
283 http.bulk_ban_users(self, &map, reason).await
284 }
285
286 /// Gets a list of the guild's bans, with additional options and filtering. See
287 /// [`Http::get_bans`] for details.
288 ///
289 /// **Note**: Requires the [Ban Members] permission.
290 ///
291 /// # Errors
292 ///
293 /// Returns [`Error::Http`] if the current user lacks permission.
294 ///
295 /// [Ban Members]: Permissions::BAN_MEMBERS
296 #[inline]
297 pub async fn bans(
298 self,
299 http: impl AsRef<Http>,
300 target: Option<UserPagination>,
301 limit: Option<u8>,
302 ) -> Result<Vec<Ban>> {
303 http.as_ref().get_bans(self, target, limit).await
304 }
305
306 /// Gets a user's ban from the guild.
307 /// See [`Http::get_ban`] for details.
308 ///
309 /// **Note**: Requires the [Ban Members] permission.
310 ///
311 /// # Errors
312 ///
313 /// Returns [`Error::Http`] if the current user lacks permission.
314 ///
315 /// [Ban Members]: Permissions::BAN_MEMBERS
316 #[inline]
317 pub async fn get_ban(self, http: impl AsRef<Http>, user_id: UserId) -> Result<Option<Ban>> {
318 http.as_ref().get_ban(self, user_id).await
319 }
320
321 /// Gets a list of the guild's audit log entries
322 ///
323 /// **Note**: Requires the [View Audit Log] permission.
324 ///
325 /// # Errors
326 ///
327 /// Returns [`Error::Http`] if the current user lacks permission, or if an invalid value is
328 /// given.
329 ///
330 /// [View Audit Log]: Permissions::VIEW_AUDIT_LOG
331 #[inline]
332 pub async fn audit_logs(
333 self,
334 http: impl AsRef<Http>,
335 action_type: Option<audit_log::Action>,
336 user_id: Option<UserId>,
337 before: Option<AuditLogEntryId>,
338 limit: Option<u8>,
339 ) -> Result<AuditLogs> {
340 http.as_ref().get_audit_logs(self, action_type, user_id, before, limit).await
341 }
342
343 /// Gets all of the guild's channels over the REST API.
344 ///
345 /// # Errors
346 ///
347 /// Returns [`Error::Http`] if the current user is not in the guild.
348 pub async fn channels(
349 self,
350 http: impl AsRef<Http>,
351 ) -> Result<HashMap<ChannelId, GuildChannel>> {
352 let channels = http.as_ref().get_channels(self).await?;
353
354 Ok(channels.into_iter().map(|c| (c.id, c)).collect())
355 }
356
357 /// Creates a [`GuildChannel`] in the the guild.
358 ///
359 /// Refer to [`Http::create_channel`] for more information.
360 ///
361 /// **Note**: Requires the [Manage Channels] permission.
362 ///
363 /// # Examples
364 ///
365 /// Create a voice channel in a guild with the name `test`:
366 ///
367 /// ```rust,no_run
368 /// # use serenity::http::Http;
369 /// use serenity::builder::CreateChannel;
370 /// use serenity::model::channel::ChannelType;
371 /// use serenity::model::id::GuildId;
372 ///
373 /// # async fn run() -> Result<(), Box<dyn std::error::Error>> {
374 /// # let http: Http = unimplemented!();
375 /// let builder = CreateChannel::new("test").kind(ChannelType::Voice);
376 /// let _channel = GuildId::new(7).create_channel(&http, builder).await?;
377 /// # Ok(())
378 /// # }
379 /// ```
380 ///
381 /// # Errors
382 ///
383 /// If the `cache` is enabled, returns a [`ModelError::InvalidPermissions`] if the current user
384 /// lacks permission. Otherwise returns [`Error::Http`], as well as if invalid data is given.
385 ///
386 /// [Manage Channels]: Permissions::MANAGE_CHANNELS
387 #[inline]
388 pub async fn create_channel(
389 self,
390 cache_http: impl CacheHttp,
391 builder: CreateChannel<'_>,
392 ) -> Result<GuildChannel> {
393 builder.execute(cache_http, self).await
394 }
395
396 /// Creates an emoji in the guild with a name and base64-encoded image.
397 ///
398 /// Refer to the documentation for [`Guild::create_emoji`] for more information.
399 ///
400 /// Requires the [Create Guild Expressions] permission.
401 ///
402 /// # Examples
403 ///
404 /// See the [`EditProfile::avatar`] example for an in-depth example as to how to read an image
405 /// from the filesystem and encode it as base64. Most of the example can be applied similarly
406 /// for this method.
407 ///
408 /// # Errors
409 ///
410 /// Returns [`Error::Http`] if the current user lacks permission, if the name is too long, or
411 /// if the image is too big.
412 ///
413 /// [`EditProfile::avatar`]: crate::builder::EditProfile::avatar
414 /// [Create Guild Expressions]: Permissions::CREATE_GUILD_EXPRESSIONS
415 #[inline]
416 pub async fn create_emoji(
417 self,
418 http: impl AsRef<Http>,
419 name: &str,
420 image: &str,
421 ) -> Result<Emoji> {
422 let map = json!({
423 "name": name,
424 "image": image,
425 });
426
427 http.as_ref().create_emoji(self, &map, None).await
428 }
429
430 /// Creates an integration for the guild.
431 ///
432 /// Requires the [Manage Guild] permission.
433 ///
434 /// # Errors
435 ///
436 /// Returns [`Error::Http`] if the current user lacks permission.
437 ///
438 /// [Manage Guild]: Permissions::MANAGE_GUILD
439 #[inline]
440 pub async fn create_integration(
441 self,
442 http: impl AsRef<Http>,
443 integration_id: impl Into<IntegrationId>,
444 kind: &str,
445 ) -> Result<()> {
446 let integration_id = integration_id.into();
447 let map = json!({
448 "id": integration_id,
449 "type": kind,
450 });
451
452 http.as_ref().create_guild_integration(self, integration_id, &map, None).await
453 }
454
455 /// Creates a new role in the guild with the data set, if any.
456 ///
457 /// See the documentation for [`Guild::create_role`] on how to use this.
458 ///
459 /// **Note**: Requires the [Manage Roles] permission.
460 ///
461 /// # Errors
462 ///
463 /// If the `cache` is enabled, returns a [`ModelError::InvalidPermissions`] if the current user
464 /// lacks permission. Otherwise returns [`Error::Http`], as well as if invalid data is given.
465 ///
466 /// [Manage Roles]: Permissions::MANAGE_ROLES
467 #[inline]
468 pub async fn create_role(
469 self,
470 cache_http: impl CacheHttp,
471 builder: EditRole<'_>,
472 ) -> Result<Role> {
473 builder.execute(cache_http, (self, None)).await
474 }
475
476 /// Creates a new scheduled event in the guild with the data set, if any.
477 ///
478 /// **Note**: Requires the [Create Events] permission.
479 ///
480 /// # Errors
481 ///
482 /// If the `cache` is enabled, returns a [`ModelError::InvalidPermissions`] if the current user
483 /// lacks permission. Otherwise returns [`Error::Http`], as well as if invalid data is given.
484 ///
485 /// [Manage Events]: Permissions::CREATE_EVENTS
486 pub async fn create_scheduled_event(
487 self,
488 cache_http: impl CacheHttp,
489 builder: CreateScheduledEvent<'_>,
490 ) -> Result<ScheduledEvent> {
491 builder.execute(cache_http, self).await
492 }
493
494 /// Creates a new sticker in the guild with the data set, if any.
495 ///
496 /// **Note**: Requires the [Create Guild Expressions] permission.
497 ///
498 /// # Errors
499 ///
500 /// If the `cache` is enabled, returns a [`ModelError::InvalidPermissions`] if the current user
501 /// lacks permission. Otherwise returns [`Error::Http`], as well as if invalid data is given.
502 ///
503 /// [Create Guild Expressions]: Permissions::CREATE_GUILD_EXPRESSIONS
504 #[inline]
505 pub async fn create_sticker(
506 self,
507 cache_http: impl CacheHttp,
508 builder: CreateSticker<'_>,
509 ) -> Result<Sticker> {
510 builder.execute(cache_http, self).await
511 }
512
513 /// Deletes the current guild if the current account is the owner of the
514 /// guild.
515 ///
516 /// Refer to [`Guild::delete`] for more information.
517 ///
518 /// **Note**: Requires the current user to be the owner of the guild.
519 ///
520 /// # Errors
521 ///
522 /// Returns [`Error::Http`] if the current user is not the owner of the guild.
523 #[inline]
524 pub async fn delete(self, http: impl AsRef<Http>) -> Result<()> {
525 http.as_ref().delete_guild(self).await
526 }
527
528 /// Deletes an [`Emoji`] from the guild.
529 ///
530 /// **Note**: If the emoji was created by the current user, requires either the [Create Guild
531 /// Expressions] or the [Manage Guild Expressions] permission. Otherwise, the [Manage Guild
532 /// Expressions] permission is required.
533 ///
534 /// # Errors
535 ///
536 /// Returns [`Error::Http`] if the current user lacks permission, or if an emoji with the given
537 /// id does not exist in the guild.
538 ///
539 /// [Create Guild Expressions]: Permissions::CREATE_GUILD_EXPRESSIONS
540 /// [Manage Guild Expressions]: Permissions::MANAGE_GUILD_EXPRESSIONS
541 #[inline]
542 pub async fn delete_emoji(
543 self,
544 http: impl AsRef<Http>,
545 emoji_id: impl Into<EmojiId>,
546 ) -> Result<()> {
547 http.as_ref().delete_emoji(self, emoji_id.into(), None).await
548 }
549
550 /// Deletes an integration by Id from the guild.
551 ///
552 /// **Note**: Requires the [Manage Guild] permission.
553 ///
554 /// # Errors
555 ///
556 /// Returns [`Error::Http`] if the current user lacks permission, or if an integration with
557 /// that Id does not exist.
558 ///
559 /// [Manage Guild]: Permissions::MANAGE_GUILD
560 #[inline]
561 pub async fn delete_integration(
562 self,
563 http: impl AsRef<Http>,
564 integration_id: impl Into<IntegrationId>,
565 ) -> Result<()> {
566 http.as_ref().delete_guild_integration(self, integration_id.into(), None).await
567 }
568
569 /// Deletes a [`Role`] by Id from the guild.
570 ///
571 /// Also see [`Role::delete`] if you have the `cache` and `model` features enabled.
572 ///
573 /// **Note**: Requires the [Manage Roles] permission.
574 ///
575 /// # Errors
576 ///
577 /// Returns [`Error::Http`] if the current user lacks permission, or if a role with that Id
578 /// does not exist.
579 ///
580 /// [Manage Roles]: Permissions::MANAGE_ROLES
581 #[inline]
582 pub async fn delete_role(
583 self,
584 http: impl AsRef<Http>,
585 role_id: impl Into<RoleId>,
586 ) -> Result<()> {
587 http.as_ref().delete_role(self, role_id.into(), None).await
588 }
589
590 /// Deletes a specified scheduled event in the guild.
591 ///
592 /// **Note**: If the event was created by the current user, requires either [Create Events] or
593 /// the [Manage Events] permission. Otherwise, the [Manage Events] permission is required.
594 ///
595 /// # Errors
596 ///
597 /// Returns [`Error::Http`] if the current user lacks permission, or if invalid data is given.
598 ///
599 /// [Create Events]: Permissions::CREATE_EVENTS
600 /// [Manage Events]: Permissions::MANAGE_EVENTS
601 #[inline]
602 pub async fn delete_scheduled_event(
603 self,
604 http: impl AsRef<Http>,
605 event_id: impl Into<ScheduledEventId>,
606 ) -> Result<()> {
607 http.as_ref().delete_scheduled_event(self, event_id.into()).await
608 }
609
610 /// Deletes a [`Sticker`] by id from the guild.
611 ///
612 /// **Note**: If the sticker was created by the current user, requires either the [Create Guild
613 /// Expressions] or the [Manage Guild Expressions] permission. Otherwise, the [Manage Guild
614 /// Expressions] permission is required.
615 ///
616 /// # Errors
617 ///
618 /// Returns [`Error::Http`] if the current user lacks permission, or if a sticker with that id
619 /// does not exist.
620 ///
621 /// [Create Guild Expressions]: Permissions::CREATE_GUILD_EXPRESSIONS
622 /// [Manage Guild Expressions]: Permissions::MANAGE_GUILD_EXPRESSIONS
623 #[inline]
624 pub async fn delete_sticker(
625 self,
626 http: impl AsRef<Http>,
627 sticker_id: impl Into<StickerId>,
628 ) -> Result<()> {
629 http.as_ref().delete_sticker(self, sticker_id.into(), None).await
630 }
631
632 /// Edits the current guild with new data where specified.
633 ///
634 /// **Note**: Requires the [Manage Guild] permission.
635 ///
636 /// # Errors
637 ///
638 /// If the `cache` is enabled, returns a [`ModelError::InvalidPermissions`] if the current user
639 /// lacks permission. Otherwise returns [`Error::Http`], as well as if invalid data is given.
640 ///
641 /// [Manage Guild]: Permissions::MANAGE_GUILD
642 #[inline]
643 pub async fn edit(
644 self,
645 cache_http: impl CacheHttp,
646 builder: EditGuild<'_>,
647 ) -> Result<PartialGuild> {
648 builder.execute(cache_http, self).await
649 }
650
651 /// Edits an [`Emoji`]'s name in the guild.
652 ///
653 /// Also see [`Emoji::edit`] if you have the `cache` and `methods` features enabled.
654 ///
655 /// **Note**: If the emoji was created by the current user, requires either the [Create Guild
656 /// Expressions] or the [Manage Guild Expressions] permission. Otherwise, the [Manage Guild
657 /// Expressions] permission is required.
658 ///
659 /// # Errors
660 ///
661 /// Returns [`Error::Http`] if the current user lacks permission, or if an emoji with the given
662 /// id does not exist.
663 ///
664 /// [Create Guild Expressions]: Permissions::CREATE_GUILD_EXPRESSIONS
665 /// [Manage Guild Expressions]: Permissions::MANAGE_GUILD_EXPRESSIONS
666 #[inline]
667 pub async fn edit_emoji(
668 self,
669 http: impl AsRef<Http>,
670 emoji_id: impl Into<EmojiId>,
671 name: &str,
672 ) -> Result<Emoji> {
673 let map = json!({
674 "name": name,
675 });
676
677 http.as_ref().edit_emoji(self, emoji_id.into(), &map, None).await
678 }
679
680 /// Edits the properties a guild member, such as muting or nicknaming them. Returns the new
681 /// member.
682 ///
683 /// Refer to the documentation of [`EditMember`] for a full list of methods and permission
684 /// restrictions.
685 ///
686 /// # Examples
687 ///
688 /// Mute a member and set their roles to just one role with a predefined Id:
689 ///
690 /// ```rust,no_run
691 /// # use serenity::builder::EditMember;
692 /// # use serenity::http::Http;
693 /// # use serenity::model::id::{GuildId, RoleId, UserId};
694 /// #
695 /// # async fn run() -> Result<(), Box<dyn std::error::Error>> {
696 /// # let http: Http = unimplemented!();
697 /// # let role_id = RoleId::new(7);
698 /// # let user_id = UserId::new(7);
699 /// let builder = EditMember::new().mute(true).roles(vec![role_id]);
700 /// let _ = GuildId::new(7).edit_member(&http, user_id, builder).await?;
701 /// # Ok(())
702 /// # }
703 /// ```
704 ///
705 /// # Errors
706 ///
707 /// Returns [`Error::Http`] if the current user lacks permission, or if invalid data is given.
708 #[inline]
709 pub async fn edit_member(
710 self,
711 cache_http: impl CacheHttp,
712 user_id: impl Into<UserId>,
713 builder: EditMember<'_>,
714 ) -> Result<Member> {
715 builder.execute(cache_http, (self, user_id.into())).await
716 }
717
718 /// Edits the guild's MFA level. Returns the new level on success.
719 ///
720 /// Requires guild ownership.
721 ///
722 /// # Errors
723 ///
724 /// Returns [`Error::Http`] if the current user lacks permission.
725 pub async fn edit_mfa_level(
726 self,
727 http: impl AsRef<Http>,
728 mfa_level: MfaLevel,
729 audit_log_reason: Option<&str>,
730 ) -> Result<MfaLevel> {
731 let value = json!({
732 "level": mfa_level,
733 });
734 http.as_ref().edit_guild_mfa_level(self, &value, audit_log_reason).await
735 }
736
737 /// Edits the current user's nickname for the guild.
738 ///
739 /// Pass [`None`] to reset the nickname.
740 ///
741 /// Requires the [Change Nickname] permission.
742 ///
743 /// # Errors
744 ///
745 /// Returns [`Error::Http`] if the current user lacks permission.
746 ///
747 /// [Change Nickname]: Permissions::CHANGE_NICKNAME
748 #[inline]
749 pub async fn edit_nickname(
750 self,
751 http: impl AsRef<Http>,
752 new_nickname: Option<&str>,
753 ) -> Result<()> {
754 http.as_ref().edit_nickname(self, new_nickname, None).await
755 }
756
757 /// Edits a [`Role`], optionally setting its new fields.
758 ///
759 /// **Note**: Requires the [Manage Roles] permission.
760 ///
761 /// # Examples
762 ///
763 /// Make a role hoisted, and change its name:
764 ///
765 /// ```rust,no_run
766 /// # use serenity::builder::EditRole;
767 /// # use serenity::http::Http;
768 /// # use serenity::model::id::{GuildId, RoleId};
769 /// # use std::sync::Arc;
770 /// #
771 /// # async fn run() -> Result<(), Box<dyn std::error::Error>> {
772 /// # let http: Arc<Http> = unimplemented!();
773 /// # let guild_id = GuildId::new(2);
774 /// # let role_id = RoleId::new(8);
775 /// #
776 /// // assuming a `role_id` and `guild_id` has been bound
777 /// let builder = EditRole::new().name("a test role").hoist(true);
778 /// let role = guild_id.edit_role(&http, role_id, builder).await?;
779 /// # Ok(())
780 /// # }
781 /// ```
782 ///
783 /// # Errors
784 ///
785 /// If the `cache` is enabled, returns a [`ModelError::InvalidPermissions`] if the current user
786 /// lacks permission. Otherwise returns [`Error::Http`], as well as if invalid data is given.
787 ///
788 /// [Manage Roles]: Permissions::MANAGE_ROLES
789 #[inline]
790 pub async fn edit_role(
791 self,
792 cache_http: impl CacheHttp,
793 role_id: impl Into<RoleId>,
794 builder: EditRole<'_>,
795 ) -> Result<Role> {
796 builder.execute(cache_http, (self, Some(role_id.into()))).await
797 }
798
799 /// Modifies a scheduled event in the guild with the data set, if any.
800 ///
801 /// **Note**: If the event was created by the current user, requires either [Create Events] or
802 /// the [Manage Events] permission. Otherwise, the [Manage Events] permission is required.
803 ///
804 /// # Errors
805 ///
806 /// If the `cache` is enabled, returns a [`ModelError::InvalidPermissions`] if the current user
807 /// lacks permission. Otherwise returns [`Error::Http`], as well as if invalid data is given.
808 ///
809 /// [Create Events]: Permissions::CREATE_EVENTS
810 /// [Manage Events]: Permissions::MANAGE_EVENTS
811 pub async fn edit_scheduled_event(
812 self,
813 cache_http: impl CacheHttp,
814 event_id: impl Into<ScheduledEventId>,
815 builder: EditScheduledEvent<'_>,
816 ) -> Result<ScheduledEvent> {
817 builder.execute(cache_http, (self, event_id.into())).await
818 }
819
820 /// Edits a sticker.
821 ///
822 /// **Note**: If the sticker was created by the current user, requires either the [Create Guild
823 /// Expressions] or the [Manage Guild Expressions] permission. Otherwise, the [Manage Guild
824 /// Expressions] permission is required.
825 ///
826 /// # Examples
827 ///
828 /// Rename a sticker:
829 ///
830 /// ```rust,no_run
831 /// # use serenity::http::Http;
832 /// use serenity::builder::EditSticker;
833 /// use serenity::model::id::{GuildId, StickerId};
834 ///
835 /// # async fn run() -> Result<(), Box<dyn std::error::Error>> {
836 /// # let http: Http = unimplemented!();
837 /// let builder = EditSticker::new().name("Bun bun meow");
838 /// let _ = GuildId::new(7).edit_sticker(&http, StickerId::new(7), builder).await?;
839 /// # Ok(())
840 /// # }
841 /// ```
842 ///
843 /// # Errors
844 ///
845 /// Returns [`Error::Http`] if the current user lacks permission, or if invalid data is given.
846 ///
847 /// [Create Guild Expressions]: Permissions::CREATE_GUILD_EXPRESSIONS
848 /// [Manage Guild Expressions]: Permissions::MANAGE_GUILD_EXPRESSIONS
849 #[inline]
850 pub async fn edit_sticker(
851 self,
852 cache_http: impl CacheHttp,
853 sticker_id: impl Into<StickerId>,
854 builder: EditSticker<'_>,
855 ) -> Result<Sticker> {
856 builder.execute(cache_http, (self, sticker_id.into())).await
857 }
858
859 /// Edit the position of a [`Role`] relative to all others in the [`Guild`].
860 ///
861 /// **Note**: Requires the [Manage Roles] permission.
862 ///
863 /// # Examples
864 ///
865 /// ```rust,ignore
866 /// use serenity::model::{GuildId, RoleId};
867 /// GuildId::new(7).edit_role_position(&context, RoleId::new(8), 2);
868 /// ```
869 ///
870 /// # Errors
871 ///
872 /// Returns an [`Error::Http`] if the current user lacks permission.
873 ///
874 /// [Manage Roles]: Permissions::MANAGE_ROLES
875 #[inline]
876 pub async fn edit_role_position(
877 self,
878 http: impl AsRef<Http>,
879 role_id: impl Into<RoleId>,
880 position: u16,
881 ) -> Result<Vec<Role>> {
882 http.as_ref().edit_role_position(self, role_id.into(), position, None).await
883 }
884
885 /// Edits the guild's welcome screen.
886 ///
887 /// **Note**: Requires the [Manage Guild] permission.
888 ///
889 /// # Errors
890 ///
891 /// Returns [`Error::Http`] if the current user lacks permission.
892 ///
893 /// [Manage Guild]: Permissions::MANAGE_GUILD
894 pub async fn edit_welcome_screen(
895 self,
896 cache_http: impl CacheHttp,
897 builder: EditGuildWelcomeScreen<'_>,
898 ) -> Result<GuildWelcomeScreen> {
899 builder.execute(cache_http, self).await
900 }
901
902 /// Edits the guild's widget.
903 ///
904 /// **Note**: Requires the [Manage Guild] permission.
905 ///
906 /// # Errors
907 ///
908 /// Returns [`Error::Http`] if the current user lacks permission.
909 ///
910 /// [Manage Guild]: Permissions::MANAGE_GUILD
911 pub async fn edit_widget(
912 self,
913 cache_http: impl CacheHttp,
914 builder: EditGuildWidget<'_>,
915 ) -> Result<GuildWidget> {
916 builder.execute(cache_http, self).await
917 }
918
919 /// Gets a specific role in the guild, by Id.
920 ///
921 /// # Errors
922 ///
923 /// Returns [`Error::Http`] if the current user is not in the guild, or if the role does not
924 /// exist.
925 pub async fn role(self, http: impl AsRef<Http>, role_id: RoleId) -> Result<Role> {
926 http.as_ref().get_guild_role(self, role_id).await
927 }
928
929 /// Gets all of the guild's roles over the REST API.
930 ///
931 /// # Errors
932 ///
933 /// Returns [`Error::Http`] if the current user is not in
934 /// the guild.
935 pub async fn roles(self, http: impl AsRef<Http>) -> Result<HashMap<RoleId, Role>> {
936 let roles = http.as_ref().get_guild_roles(self).await?;
937
938 Ok(roles.into_iter().map(|r| (r.id, r)).collect())
939 }
940
941 /// Gets the default permission role (@everyone) from the guild.
942 #[inline]
943 #[must_use]
944 pub fn everyone_role(&self) -> RoleId {
945 RoleId::from(self.get())
946 }
947
948 /// Tries to find the [`Guild`] by its Id in the cache.
949 #[cfg(feature = "cache")]
950 #[inline]
951 pub fn to_guild_cached(self, cache: &impl AsRef<Cache>) -> Option<GuildRef<'_>> {
952 cache.as_ref().guild(self)
953 }
954
955 /// Requests [`PartialGuild`] over REST API.
956 ///
957 /// **Note**: This will not be a [`Guild`], as the REST API does not send
958 /// all data with a guild retrieval.
959 ///
960 /// # Errors
961 ///
962 /// Returns an [`Error::Http`] if the current user is not in the guild.
963 #[inline]
964 pub async fn to_partial_guild(self, cache_http: impl CacheHttp) -> Result<PartialGuild> {
965 #[cfg(feature = "cache")]
966 {
967 if let Some(cache) = cache_http.cache() {
968 if let Some(guild) = cache.guild(self) {
969 return Ok(guild.clone().into());
970 }
971 }
972 }
973
974 cache_http.http().get_guild(self).await
975 }
976
977 /// Requests [`PartialGuild`] over REST API with counts.
978 ///
979 /// **Note**: This will not be a [`Guild`], as the REST API does not send all data with a guild
980 /// retrieval.
981 ///
982 /// # Errors
983 ///
984 /// Returns an [`Error::Http`] if the current user is not in the guild.
985 #[inline]
986 pub async fn to_partial_guild_with_counts(
987 self,
988 http: impl AsRef<Http>,
989 ) -> Result<PartialGuild> {
990 http.as_ref().get_guild_with_counts(self).await
991 }
992
993 /// Gets all [`Emoji`]s of this guild via HTTP.
994 ///
995 /// # Errors
996 ///
997 /// Returns an [`Error::Http`] if the guild is unavailable.
998 #[inline]
999 pub async fn emojis(self, http: impl AsRef<Http>) -> Result<Vec<Emoji>> {
1000 http.as_ref().get_emojis(self).await
1001 }
1002
1003 /// Gets an [`Emoji`] of this guild by its ID via HTTP.
1004 ///
1005 /// # Errors
1006 ///
1007 /// Returns an [`Error::Http`] if an emoji with that id does not exist.
1008 #[inline]
1009 pub async fn emoji(self, http: impl AsRef<Http>, emoji_id: EmojiId) -> Result<Emoji> {
1010 http.as_ref().get_emoji(self, emoji_id).await
1011 }
1012
1013 /// Gets all [`Sticker`]s of this guild via HTTP.
1014 ///
1015 /// # Errors
1016 ///
1017 /// Returns an [`Error::Http`] if the guild is unavailable.
1018 #[inline]
1019 pub async fn stickers(self, http: impl AsRef<Http>) -> Result<Vec<Sticker>> {
1020 http.as_ref().get_guild_stickers(self).await
1021 }
1022
1023 /// Gets an [`Sticker`] of this guild by its ID via HTTP.
1024 ///
1025 /// # Errors
1026 ///
1027 /// Returns an [`Error::Http`] if an sticker with that Id does not exist.
1028 #[inline]
1029 pub async fn sticker(self, http: impl AsRef<Http>, sticker_id: StickerId) -> Result<Sticker> {
1030 http.as_ref().get_guild_sticker(self, sticker_id).await
1031 }
1032
1033 /// Gets all integration of the guild.
1034 ///
1035 /// Requires the [Manage Guild] permission.
1036 ///
1037 /// # Errors
1038 ///
1039 /// Returns an [`Error::Http`] if the current user lacks permission, also may return
1040 /// [`Error::Json`] if there is an error in deserializing the API response.
1041 ///
1042 /// [Manage Guild]: Permissions::MANAGE_GUILD
1043 #[inline]
1044 pub async fn integrations(self, http: impl AsRef<Http>) -> Result<Vec<Integration>> {
1045 http.as_ref().get_guild_integrations(self).await
1046 }
1047
1048 /// Gets all of the guild's invites.
1049 ///
1050 /// Requires the [Manage Guild] permission.
1051 ///
1052 /// # Errors
1053 ///
1054 /// Returns [`Error::Http`] if the current user lacks permission, also may return
1055 /// [`Error::Json`] if there is an error in deserializing the API response.
1056 ///
1057 /// [Manage Guild]: Permissions::MANAGE_GUILD
1058 #[inline]
1059 pub async fn invites(self, http: impl AsRef<Http>) -> Result<Vec<RichInvite>> {
1060 http.as_ref().get_guild_invites(self).await
1061 }
1062
1063 /// Kicks a [`Member`] from the guild.
1064 ///
1065 /// Requires the [Kick Members] permission.
1066 ///
1067 /// # Errors
1068 ///
1069 /// Returns [`Error::Http`] if the member cannot be kicked by the current user.
1070 ///
1071 /// [Kick Members]: Permissions::KICK_MEMBERS
1072 #[inline]
1073 pub async fn kick(self, http: impl AsRef<Http>, user_id: impl Into<UserId>) -> Result<()> {
1074 http.as_ref().kick_member(self, user_id.into(), None).await
1075 }
1076
1077 /// # Errors
1078 ///
1079 /// In addition to the reasons [`Self::kick`] may return an error, may also return an error if
1080 /// the reason is too long.
1081 #[inline]
1082 pub async fn kick_with_reason(
1083 self,
1084 http: impl AsRef<Http>,
1085 user_id: impl Into<UserId>,
1086 reason: &str,
1087 ) -> Result<()> {
1088 http.as_ref().kick_member(self, user_id.into(), Some(reason)).await
1089 }
1090
1091 /// Returns a guild [`Member`] object for the current user.
1092 ///
1093 /// See [`Http::get_current_user_guild_member`] for more.
1094 ///
1095 /// # Errors
1096 ///
1097 /// Returns an [`Error::Http`] if the current user is not in the guild or the access token
1098 /// lacks the necessary scope.
1099 #[inline]
1100 pub async fn current_user_member(self, http: impl AsRef<Http>) -> Result<Member> {
1101 http.as_ref().get_current_user_guild_member(self).await
1102 }
1103
1104 /// Leaves the guild.
1105 ///
1106 /// # Errors
1107 ///
1108 /// May return an [`Error::Http`] if the current user cannot leave the guild, or currently is
1109 /// not in the guild.
1110 #[inline]
1111 pub async fn leave(self, http: impl AsRef<Http>) -> Result<()> {
1112 http.as_ref().leave_guild(self).await
1113 }
1114
1115 /// Gets a user's [`Member`] for the guild by Id.
1116 ///
1117 /// If the cache feature is enabled the cache will be checked first. If not found it will
1118 /// resort to an http request.
1119 ///
1120 /// # Errors
1121 ///
1122 /// Returns an [`Error::Http`] if the user is not in the guild, or if the guild is otherwise
1123 /// unavailable
1124 #[inline]
1125 pub async fn member(
1126 self,
1127 cache_http: impl CacheHttp,
1128 user_id: impl Into<UserId>,
1129 ) -> Result<Member> {
1130 let user_id = user_id.into();
1131
1132 #[cfg(feature = "cache")]
1133 {
1134 if let Some(cache) = cache_http.cache() {
1135 if let Some(guild) = cache.guild(self) {
1136 if let Some(member) = guild.members.get(&user_id) {
1137 return Ok(member.clone());
1138 }
1139 }
1140 }
1141 }
1142
1143 cache_http.http().get_member(self, user_id).await
1144 }
1145
1146 /// Gets a list of the guild's members.
1147 ///
1148 /// Optionally pass in the `limit` to limit the number of results. Minimum value is 1, maximum
1149 /// and default value is 1000.
1150 ///
1151 /// Optionally pass in `after` to offset the results by a [`User`]'s Id.
1152 ///
1153 /// # Errors
1154 ///
1155 /// Returns an [`Error::Http`] if the API returns an error, may also return
1156 /// [`Error::NotInRange`] if the input is not within range.
1157 ///
1158 /// [`User`]: crate::model::user::User
1159 #[inline]
1160 pub async fn members(
1161 self,
1162 http: impl AsRef<Http>,
1163 limit: Option<u64>,
1164 after: impl Into<Option<UserId>>,
1165 ) -> Result<Vec<Member>> {
1166 http.as_ref().get_guild_members(self, limit, after.into().map(UserId::get)).await
1167 }
1168
1169 /// Streams over all the members in a guild.
1170 ///
1171 /// This is accomplished and equivalent to repeated calls to [`Self::members`]. A buffer of at
1172 /// most 1,000 members is used to reduce the number of calls necessary.
1173 ///
1174 /// # Examples
1175 /// ```rust,no_run
1176 /// # use serenity::model::id::GuildId;
1177 /// # use serenity::http::Http;
1178 /// #
1179 /// # async fn run() {
1180 /// # let guild_id = GuildId::new(1);
1181 /// # let ctx: Http = unimplemented!();
1182 /// use serenity::futures::StreamExt;
1183 /// use serenity::model::guild::MembersIter;
1184 ///
1185 /// let mut members = guild_id.members_iter(&ctx).boxed();
1186 /// while let Some(member_result) = members.next().await {
1187 /// match member_result {
1188 /// Ok(member) => println!("{} is {}", member, member.display_name(),),
1189 /// Err(error) => eprintln!("Uh oh! Error: {}", error),
1190 /// }
1191 /// }
1192 /// # }
1193 /// ```
1194 pub fn members_iter<H: AsRef<Http>>(self, http: H) -> impl Stream<Item = Result<Member>> {
1195 MembersIter::<H>::stream(http, self)
1196 }
1197
1198 /// Gets a user's voice state in this guild.
1199 ///
1200 /// # Errors
1201 ///
1202 /// Returns [`Error::Http`] if the user is not in a voice channel in this guild.
1203 pub async fn get_user_voice_state(self, http: &Http, user_id: UserId) -> Result<VoiceState> {
1204 http.get_user_voice_state(self, user_id).await
1205 }
1206
1207 /// Moves a member to a specific voice channel.
1208 ///
1209 /// **Note**: Requires the [Move Members] permission.
1210 ///
1211 /// # Errors
1212 ///
1213 /// Returns [`Error::Http`] if the current user lacks permission, or if the member is not
1214 /// currently in a voice channel for this [`Guild`].
1215 ///
1216 /// [Move Members]: Permissions::MOVE_MEMBERS
1217 #[inline]
1218 pub async fn move_member(
1219 self,
1220 cache_http: impl CacheHttp,
1221 user_id: impl Into<UserId>,
1222 channel_id: impl Into<ChannelId>,
1223 ) -> Result<Member> {
1224 let builder = EditMember::new().voice_channel(channel_id.into());
1225 self.edit_member(cache_http, user_id, builder).await
1226 }
1227
1228 /// Returns the name of whatever guild this id holds.
1229 #[cfg(feature = "cache")]
1230 #[must_use]
1231 pub fn name(self, cache: impl AsRef<Cache>) -> Option<String> {
1232 self.to_guild_cached(cache.as_ref()).map(|g| g.name.clone())
1233 }
1234
1235 /// Disconnects a member from a voice channel in the guild.
1236 ///
1237 /// **Note**: Requires the [Move Members] permission.
1238 ///
1239 /// # Errors
1240 ///
1241 /// Returns [`Error::Http`] if the current user lacks permission, or if the member is not
1242 /// currently in a voice channel for this [`Guild`].
1243 ///
1244 /// [Move Members]: Permissions::MOVE_MEMBERS
1245 #[inline]
1246 pub async fn disconnect_member(
1247 self,
1248 cache_http: impl CacheHttp,
1249 user_id: impl Into<UserId>,
1250 ) -> Result<Member> {
1251 self.edit_member(cache_http, user_id, EditMember::new().disconnect_member()).await
1252 }
1253
1254 /// Gets the number of [`Member`]s that would be pruned with the given number of days.
1255 ///
1256 /// Requires the [Kick Members] permission.
1257 ///
1258 /// # Errors
1259 ///
1260 /// Returns [`Error::Http`] if the current user does not have permission.
1261 ///
1262 /// [Kick Members]: Permissions::KICK_MEMBERS
1263 #[inline]
1264 pub async fn prune_count(self, http: impl AsRef<Http>, days: u8) -> Result<GuildPrune> {
1265 http.as_ref().get_guild_prune_count(self, days).await
1266 }
1267
1268 /// Re-orders the channels of the guild.
1269 ///
1270 /// Accepts an iterator of a tuple of the channel ID to modify and its new position.
1271 ///
1272 /// Although not required, you should specify all channels' positions, regardless of whether
1273 /// they were updated. Otherwise, positioning can sometimes get weird.
1274 ///
1275 /// **Note**: Requires the [Manage Channels] permission.
1276 ///
1277 /// # Errors
1278 ///
1279 /// Returns [`Error::Http`] if the current user lacks permission.
1280 ///
1281 /// [Manage Channels]: Permissions::MANAGE_CHANNELS
1282 #[inline]
1283 pub async fn reorder_channels(
1284 self,
1285 http: impl AsRef<Http>,
1286 channels: impl IntoIterator<Item = (ChannelId, u64)>,
1287 ) -> Result<()> {
1288 let items = channels
1289 .into_iter()
1290 .map(|(id, pos)| {
1291 json!({
1292 "id": id,
1293 "position": pos,
1294 })
1295 })
1296 .collect::<Vec<_>>()
1297 .into();
1298
1299 http.as_ref().edit_guild_channel_positions(self, &items).await
1300 }
1301
1302 /// Returns a list of [`Member`]s in a [`Guild`] whose username or nickname starts with a
1303 /// provided string.
1304 ///
1305 /// Optionally pass in the `limit` to limit the number of results. Minimum value is 1, maximum
1306 /// and default value is 1000.
1307 ///
1308 /// # Errors
1309 ///
1310 /// Returns an [`Error::Http`] if the API returns an error.
1311 #[inline]
1312 pub async fn search_members(
1313 self,
1314 http: impl AsRef<Http>,
1315 query: &str,
1316 limit: Option<u64>,
1317 ) -> Result<Vec<Member>> {
1318 http.as_ref().search_guild_members(self, query, limit).await
1319 }
1320
1321 /// Fetches a specified scheduled event in the guild, by Id. If `with_user_count` is set to
1322 /// `true`, then the `user_count` field will be populated, indicating the number of users
1323 /// interested in the event.
1324 ///
1325 /// **Note**: Requires the [View Channel] permission for the channel associated with the event.
1326 ///
1327 /// # Errors
1328 ///
1329 /// Returns [`Error::Http`] if the current user lacks permission, or if the provided id is
1330 /// invalid.
1331 ///
1332 /// [View Channel]: Permissions::VIEW_CHANNEL
1333 pub async fn scheduled_event(
1334 self,
1335 http: impl AsRef<Http>,
1336 event_id: impl Into<ScheduledEventId>,
1337 with_user_count: bool,
1338 ) -> Result<ScheduledEvent> {
1339 http.as_ref().get_scheduled_event(self, event_id.into(), with_user_count).await
1340 }
1341
1342 /// Fetches a list of all scheduled events in the guild. If `with_user_count` is set to `true`,
1343 /// then each event returned will have its `user_count` field populated.
1344 ///
1345 /// **Note**: Requires the [View Channel] permission at the guild level.
1346 ///
1347 /// # Errors
1348 ///
1349 /// Returns [`Error::Http`] if the current user lacks permission.
1350 ///
1351 /// [View Channel]: Permissions::VIEW_CHANNEL
1352 pub async fn scheduled_events(
1353 self,
1354 http: impl AsRef<Http>,
1355 with_user_count: bool,
1356 ) -> Result<Vec<ScheduledEvent>> {
1357 http.as_ref().get_scheduled_events(self, with_user_count).await
1358 }
1359
1360 /// Fetches a list of interested users for the specified event.
1361 ///
1362 /// If `limit` is left unset, by default at most 100 users are returned.
1363 ///
1364 /// **Note**: Requires the [View Channel] permission for the channel associated with the event.
1365 ///
1366 /// # Errors
1367 ///
1368 /// Returns [`Error::Http`] if the current user lacks permission, or if the provided Id is
1369 /// invalid.
1370 ///
1371 /// [View Channel]: Permissions::VIEW_CHANNEL
1372 pub async fn scheduled_event_users(
1373 self,
1374 http: impl AsRef<Http>,
1375 event_id: impl Into<ScheduledEventId>,
1376 limit: Option<u64>,
1377 ) -> Result<Vec<ScheduledEventUser>> {
1378 http.as_ref().get_scheduled_event_users(self, event_id.into(), limit, None, None).await
1379 }
1380
1381 /// Fetches a list of interested users for the specified event, with additional options and
1382 /// filtering. See [`Http::get_scheduled_event_users`] for details.
1383 ///
1384 /// **Note**: Requires the [View Channel] permission for the channel associated with the event.
1385 ///
1386 /// # Errors
1387 ///
1388 /// Returns [`Error::Http`] if the current user lacks permission, or if the provided Id is
1389 /// invalid.
1390 ///
1391 /// [View Channel]: Permissions::VIEW_CHANNEL
1392 pub async fn scheduled_event_users_optioned(
1393 self,
1394 http: impl AsRef<Http>,
1395 event_id: impl Into<ScheduledEventId>,
1396 limit: Option<u64>,
1397 target: Option<UserPagination>,
1398 with_member: Option<bool>,
1399 ) -> Result<Vec<ScheduledEventUser>> {
1400 http.as_ref()
1401 .get_scheduled_event_users(self, event_id.into(), limit, target, with_member)
1402 .await
1403 }
1404
1405 /// Returns the Id of the shard associated with the guild.
1406 ///
1407 /// When the cache is enabled this will automatically retrieve the total number of shards.
1408 ///
1409 /// **Note**: When the cache is enabled, this function unlocks the cache to retrieve the total
1410 /// number of shards in use. If you already have the total, consider using [`utils::shard_id`].
1411 ///
1412 /// [`utils::shard_id`]: crate::utils::shard_id
1413 #[cfg(all(feature = "cache", feature = "utils"))]
1414 #[inline]
1415 #[must_use]
1416 pub fn shard_id(self, cache: impl AsRef<Cache>) -> u32 {
1417 crate::utils::shard_id(self, cache.as_ref().shard_count())
1418 }
1419
1420 /// Returns the Id of the shard associated with the guild.
1421 ///
1422 /// When the cache is enabled this will automatically retrieve the total number of shards.
1423 ///
1424 /// When the cache is not enabled, the total number of shards being used will need to be
1425 /// passed.
1426 ///
1427 /// # Examples
1428 ///
1429 /// Retrieve the Id of the shard for a guild with Id `81384788765712384`, using 17 shards:
1430 ///
1431 /// ```rust
1432 /// use serenity::model::id::GuildId;
1433 /// use serenity::utils;
1434 ///
1435 /// let guild_id = GuildId::new(81384788765712384);
1436 ///
1437 /// assert_eq!(guild_id.shard_id(17), 7);
1438 /// ```
1439 #[cfg(all(feature = "utils", not(feature = "cache")))]
1440 #[inline]
1441 #[must_use]
1442 pub fn shard_id(self, shard_count: u32) -> u32 {
1443 crate::utils::shard_id(self, shard_count)
1444 }
1445
1446 /// Starts an integration sync for the given integration Id.
1447 ///
1448 /// Requires the [Manage Guild] permission.
1449 ///
1450 /// # Errors
1451 ///
1452 /// Returns [`Error::Http`] if the current user lacks permission, or if an [`Integration`] with
1453 /// that Id does not exist.
1454 ///
1455 /// [Manage Guild]: Permissions::MANAGE_GUILD
1456 #[inline]
1457 pub async fn start_integration_sync(
1458 self,
1459 http: impl AsRef<Http>,
1460 integration_id: impl Into<IntegrationId>,
1461 ) -> Result<()> {
1462 http.as_ref().start_integration_sync(self, integration_id.into()).await
1463 }
1464
1465 /// Starts a prune of [`Member`]s.
1466 ///
1467 /// See the documentation on [`GuildPrune`] for more information.
1468 ///
1469 /// **Note**: Requires [Kick Members] and [Manage Guild] permissions.
1470 ///
1471 /// # Errors
1472 ///
1473 /// Returns [`Error::Http`] if the current user lacks permission.
1474 ///
1475 /// [Kick Members]: Permissions::KICK_MEMBERS
1476 /// [Manage Guild]: Permissions::MANAGE_GUILD
1477 #[inline]
1478 pub async fn start_prune(self, http: impl AsRef<Http>, days: u8) -> Result<GuildPrune> {
1479 http.as_ref().start_guild_prune(self, days, None).await
1480 }
1481
1482 /// Unbans a [`User`] from the guild.
1483 ///
1484 /// **Note**: Requires the [Ban Members] permission.
1485 ///
1486 /// # Errors
1487 ///
1488 /// Returns [`Error::Http`] if the current user does not have permission.
1489 ///
1490 /// [Ban Members]: Permissions::BAN_MEMBERS
1491 #[inline]
1492 pub async fn unban(self, http: impl AsRef<Http>, user_id: impl Into<UserId>) -> Result<()> {
1493 http.as_ref().remove_ban(self, user_id.into(), None).await
1494 }
1495
1496 /// Retrieve's the guild's vanity URL.
1497 ///
1498 /// **Note**: Requires the [Manage Guild] permission.
1499 ///
1500 /// # Errors
1501 ///
1502 /// Will return [`Error::Http`] if the current user lacks permission. Can also return
1503 /// [`Error::Json`] if there is an error deserializing the API response.
1504 ///
1505 /// [Manage Guild]: Permissions::MANAGE_GUILD
1506 #[inline]
1507 pub async fn vanity_url(self, http: impl AsRef<Http>) -> Result<String> {
1508 http.as_ref().get_guild_vanity_url(self).await
1509 }
1510
1511 /// Retrieves the guild's webhooks.
1512 ///
1513 /// **Note**: Requires the [Manage Webhooks] permission.
1514 ///
1515 /// [Manage Webhooks]: Permissions::MANAGE_WEBHOOKS
1516 ///
1517 /// # Errors
1518 ///
1519 /// Will return an [`Error::Http`] if the bot is lacking permissions. Can also return an
1520 /// [`Error::Json`] if there is an error deserializing the API response.
1521 #[inline]
1522 pub async fn webhooks(self, http: impl AsRef<Http>) -> Result<Vec<Webhook>> {
1523 http.as_ref().get_guild_webhooks(self).await
1524 }
1525 /// Returns a builder which can be awaited to obtain a message or stream of messages in this
1526 /// guild.
1527 #[cfg(feature = "collector")]
1528 pub fn await_reply(self, shard_messenger: impl AsRef<ShardMessenger>) -> MessageCollector {
1529 MessageCollector::new(shard_messenger).guild_id(self)
1530 }
1531
1532 /// Same as [`Self::await_reply`].
1533 #[cfg(feature = "collector")]
1534 pub fn await_replies(&self, shard_messenger: impl AsRef<ShardMessenger>) -> MessageCollector {
1535 self.await_reply(shard_messenger)
1536 }
1537
1538 /// Returns a builder which can be awaited to obtain a message or stream of reactions sent in
1539 /// this guild.
1540 #[cfg(feature = "collector")]
1541 pub fn await_reaction(self, shard_messenger: impl AsRef<ShardMessenger>) -> ReactionCollector {
1542 ReactionCollector::new(shard_messenger).guild_id(self)
1543 }
1544
1545 /// Same as [`Self::await_reaction`].
1546 #[cfg(feature = "collector")]
1547 pub fn await_reactions(
1548 &self,
1549 shard_messenger: impl AsRef<ShardMessenger>,
1550 ) -> ReactionCollector {
1551 self.await_reaction(shard_messenger)
1552 }
1553
1554 /// Create a guild specific application [`Command`].
1555 ///
1556 /// **Note**: Unlike global commands, guild commands will update instantly.
1557 ///
1558 /// # Errors
1559 ///
1560 /// See [`CreateCommand::execute`] for a list of possible errors.
1561 pub async fn create_command(
1562 self,
1563 cache_http: impl CacheHttp,
1564 builder: CreateCommand,
1565 ) -> Result<Command> {
1566 builder.execute(cache_http, (Some(self), None)).await
1567 }
1568
1569 /// Override all guild application commands.
1570 ///
1571 /// # Errors
1572 ///
1573 /// Returns the same errors as [`Self::create_command`].
1574 pub async fn set_commands(
1575 self,
1576 http: impl AsRef<Http>,
1577 commands: Vec<CreateCommand>,
1578 ) -> Result<Vec<Command>> {
1579 http.as_ref().create_guild_commands(self, &commands).await
1580 }
1581
1582 /// Overwrites permissions for a specific command.
1583 ///
1584 /// **Note**: It will update instantly.
1585 ///
1586 /// # Errors
1587 ///
1588 /// See [`EditCommandPermissions::execute`] for a list of possible errors.
1589 pub async fn edit_command_permissions(
1590 self,
1591 cache_http: impl CacheHttp,
1592 command_id: CommandId,
1593 builder: EditCommandPermissions,
1594 ) -> Result<CommandPermissions> {
1595 builder.execute(cache_http, (self, command_id)).await
1596 }
1597
1598 /// Get all guild application commands.
1599 ///
1600 /// # Errors
1601 ///
1602 /// If there is an error, it will be either [`Error::Http`] or [`Error::Json`].
1603 pub async fn get_commands(self, http: impl AsRef<Http>) -> Result<Vec<Command>> {
1604 http.as_ref().get_guild_commands(self).await
1605 }
1606
1607 /// Get all guild application commands with localizations.
1608 ///
1609 /// # Errors
1610 ///
1611 /// If there is an error, it will be either [`Error::Http`] or [`Error::Json`].
1612 pub async fn get_commands_with_localizations(
1613 self,
1614 http: impl AsRef<Http>,
1615 ) -> Result<Vec<Command>> {
1616 http.as_ref().get_guild_commands_with_localizations(self).await
1617 }
1618
1619 /// Get a specific guild application command by its Id.
1620 ///
1621 /// # Errors
1622 ///
1623 /// If there is an error, it will be either [`Error::Http`] or [`Error::Json`].
1624 pub async fn get_command(
1625 self,
1626 http: impl AsRef<Http>,
1627 command_id: CommandId,
1628 ) -> Result<Command> {
1629 http.as_ref().get_guild_command(self, command_id).await
1630 }
1631
1632 /// Edit a guild application command, given its Id.
1633 ///
1634 /// # Errors
1635 ///
1636 /// See [`CreateCommand::execute`] for a list of possible errors.
1637 pub async fn edit_command(
1638 self,
1639 cache_http: impl CacheHttp,
1640 command_id: CommandId,
1641 builder: CreateCommand,
1642 ) -> Result<Command> {
1643 builder.execute(cache_http, (Some(self), Some(command_id))).await
1644 }
1645
1646 /// Delete guild application command by its Id.
1647 ///
1648 /// # Errors
1649 ///
1650 /// If there is an error, it will be either [`Error::Http`] or [`Error::Json`].
1651 pub async fn delete_command(self, http: impl AsRef<Http>, command_id: CommandId) -> Result<()> {
1652 http.as_ref().delete_guild_command(self, command_id).await
1653 }
1654
1655 /// Get all guild application commands permissions only.
1656 ///
1657 /// # Errors
1658 ///
1659 /// If there is an error, it will be either [`Error::Http`] or [`Error::Json`].
1660 pub async fn get_commands_permissions(
1661 self,
1662 http: impl AsRef<Http>,
1663 ) -> Result<Vec<CommandPermissions>> {
1664 http.as_ref().get_guild_commands_permissions(self).await
1665 }
1666
1667 /// Get permissions for specific guild application command by its Id.
1668 ///
1669 /// # Errors
1670 ///
1671 /// If there is an error, it will be either [`Error::Http`] or [`Error::Json`].
1672 pub async fn get_command_permissions(
1673 self,
1674 http: impl AsRef<Http>,
1675 command_id: CommandId,
1676 ) -> Result<CommandPermissions> {
1677 http.as_ref().get_guild_command_permissions(self, command_id).await
1678 }
1679
1680 /// Get the guild welcome screen.
1681 ///
1682 /// # Errors
1683 ///
1684 /// Returns [`Error::Http`] if the guild does not have a welcome screen.
1685 pub async fn get_welcome_screen(self, http: impl AsRef<Http>) -> Result<GuildWelcomeScreen> {
1686 http.as_ref().get_guild_welcome_screen(self).await
1687 }
1688
1689 /// Get the guild preview.
1690 ///
1691 /// **Note**: The bot need either to be part of the guild or the guild needs to have the
1692 /// `DISCOVERABLE` feature.
1693 ///
1694 /// # Errors
1695 ///
1696 /// Returns [`Error::Http`] if the bot cannot see the guild preview, see the note.
1697 pub async fn get_preview(self, http: impl AsRef<Http>) -> Result<GuildPreview> {
1698 http.as_ref().get_guild_preview(self).await
1699 }
1700
1701 /// Get the guild widget.
1702 ///
1703 /// # Errors
1704 ///
1705 /// Returns [`Error::Http`] if the bot does not have `MANAGE_MESSAGES` permission.
1706 pub async fn get_widget(self, http: impl AsRef<Http>) -> Result<GuildWidget> {
1707 http.as_ref().get_guild_widget(self).await
1708 }
1709
1710 /// Get the widget image URL.
1711 #[must_use]
1712 pub fn widget_image_url(self, style: GuildWidgetStyle) -> String {
1713 api!("/guilds/{}/widget.png?style={}", self, style)
1714 }
1715
1716 /// Gets the guild active threads.
1717 ///
1718 /// # Errors
1719 ///
1720 /// Returns [`Error::Http`] if there is an error in the deserialization, or if the bot issuing
1721 /// the request is not in the guild.
1722 pub async fn get_active_threads(self, http: impl AsRef<Http>) -> Result<ThreadsData> {
1723 http.as_ref().get_guild_active_threads(self).await
1724 }
1725
1726 /// Gets a soundboard sound from the guild.
1727 ///
1728 /// # Errors
1729 ///
1730 /// Returns [`Error::Http`] if there is an error in the deserialization, or if the bot issuing
1731 /// the request is not in the guild.
1732 pub async fn get_soundboard(
1733 self,
1734 http: impl AsRef<Http>,
1735 sound_id: SoundId,
1736 ) -> Result<Soundboard> {
1737 http.as_ref().get_guild_soundboard(self, sound_id).await
1738 }
1739
1740 /// Gets all soundboard sounds from the guild.
1741 ///
1742 /// # Errors
1743 ///
1744 /// Returns [`Error::Http`] if there is an error in the deserialization, or if the bot issuing
1745 /// the request is not in the guild.
1746 pub async fn get_soundboards(self, http: impl AsRef<Http>) -> Result<Vec<Soundboard>> {
1747 http.as_ref().get_guild_soundboards(self).await
1748 }
1749
1750 /// Creates a soundboard sound for the guild.
1751 ///
1752 /// # Errors
1753 ///
1754 /// See [`CreateSoundboard::execute`] for a list of possible errors.
1755 pub async fn create_soundboard(
1756 self,
1757 cache_http: impl CacheHttp,
1758 builder: CreateSoundboard<'_>,
1759 ) -> Result<Soundboard> {
1760 builder.execute(cache_http, self).await
1761 }
1762
1763 /// Edits a soundboard sound for the guild.
1764 ///
1765 /// # Errors
1766 ///
1767 /// See [`EditSoundboard::execute`] for a list of possible errors.
1768 pub async fn edit_soundboard(
1769 self,
1770 cache_http: impl CacheHttp,
1771 sound_id: SoundId,
1772 builder: EditSoundboard<'_>,
1773 ) -> Result<Soundboard> {
1774 builder.execute(cache_http, (self, sound_id)).await
1775 }
1776
1777 /// Deletes a soundboard sound for the guild.
1778 ///
1779 /// # Errors
1780 ///
1781 /// Returns [`Error::Http`] if the current user lacks permission, or if a
1782 /// soundboard sound with that Id does not exist.
1783 pub async fn delete_soundboard(
1784 self,
1785 http: impl AsRef<Http>,
1786 sound_id: SoundId,
1787 audit_log_reason: Option<&str>,
1788 ) -> Result<()> {
1789 http.as_ref().delete_guild_soundboard(self, sound_id, audit_log_reason).await
1790 }
1791
1792 /// Edits the guild incident actions
1793 ///
1794 /// **Note**: Requires the [Manage Guild] permission.
1795 ///
1796 /// [Manage Guild]: Permissions::MANAGE_GUILD
1797 ///
1798 /// # Errors
1799 ///
1800 /// Returns [`Error::Http`] if invalid data is given. See [Discord's docs] for more details.
1801 ///
1802 /// May also return [`Error::Json`] if there is an error in deserializing the API response.
1803 ///
1804 /// [Discord's docs]: https://discord.com/developers/docs/resources/guild#modify-guild-incident-actions
1805 pub async fn edit_guild_incident_actions(
1806 self,
1807 http: &Http,
1808 guild_id: GuildId,
1809 builder: EditGuildIncidentActions,
1810 ) -> Result<IncidentsData> {
1811 builder.execute(http, guild_id).await
1812 }
1813}
1814
1815impl From<PartialGuild> for GuildId {
1816 /// Gets the Id of a partial guild.
1817 fn from(guild: PartialGuild) -> GuildId {
1818 guild.id
1819 }
1820}
1821
1822impl From<&PartialGuild> for GuildId {
1823 /// Gets the Id of a partial guild.
1824 fn from(guild: &PartialGuild) -> GuildId {
1825 guild.id
1826 }
1827}
1828
1829impl From<GuildInfo> for GuildId {
1830 /// Gets the Id of Guild information struct.
1831 fn from(guild_info: GuildInfo) -> GuildId {
1832 guild_info.id
1833 }
1834}
1835
1836impl From<&GuildInfo> for GuildId {
1837 /// Gets the Id of Guild information struct.
1838 fn from(guild_info: &GuildInfo) -> GuildId {
1839 guild_info.id
1840 }
1841}
1842
1843impl From<InviteGuild> for GuildId {
1844 /// Gets the Id of Invite Guild struct.
1845 fn from(invite_guild: InviteGuild) -> GuildId {
1846 invite_guild.id
1847 }
1848}
1849
1850impl From<&InviteGuild> for GuildId {
1851 /// Gets the Id of Invite Guild struct.
1852 fn from(invite_guild: &InviteGuild) -> GuildId {
1853 invite_guild.id
1854 }
1855}
1856
1857impl From<Guild> for GuildId {
1858 /// Gets the Id of Guild.
1859 fn from(live_guild: Guild) -> GuildId {
1860 live_guild.id
1861 }
1862}
1863
1864impl From<&Guild> for GuildId {
1865 /// Gets the Id of Guild.
1866 fn from(live_guild: &Guild) -> GuildId {
1867 live_guild.id
1868 }
1869}
1870
1871impl From<WebhookGuild> for GuildId {
1872 /// Gets the Id of Webhook Guild struct.
1873 fn from(webhook_guild: WebhookGuild) -> GuildId {
1874 webhook_guild.id
1875 }
1876}
1877
1878impl From<&WebhookGuild> for GuildId {
1879 /// Gets the Id of Webhook Guild struct.
1880 fn from(webhook_guild: &WebhookGuild) -> GuildId {
1881 webhook_guild.id
1882 }
1883}
1884
1885/// A helper class returned by [`GuildId::members_iter`]
1886#[derive(Clone, Debug)]
1887#[cfg(feature = "model")]
1888pub struct MembersIter<H: AsRef<Http>> {
1889 guild_id: GuildId,
1890 http: H,
1891 buffer: Vec<Member>,
1892 after: Option<UserId>,
1893 tried_fetch: bool,
1894}
1895
1896#[cfg(feature = "model")]
1897impl<H: AsRef<Http>> MembersIter<H> {
1898 fn new(guild_id: GuildId, http: H) -> MembersIter<H> {
1899 MembersIter {
1900 guild_id,
1901 http,
1902 buffer: Vec::new(),
1903 after: None,
1904 tried_fetch: false,
1905 }
1906 }
1907
1908 /// Fills the `self.buffer` cache of Members.
1909 ///
1910 /// This drops any members that were currently in the buffer, so it should only be called when
1911 /// `self.buffer` is empty. Additionally, this updates `self.after` so that the next call does
1912 /// not return duplicate items. If there are no more members to be fetched, then this marks
1913 /// `self.after` as None, indicating that no more calls ought to be made.
1914 async fn refresh(&mut self) -> Result<()> {
1915 // Number of profiles to fetch
1916 let grab_size: u64 = 1000;
1917
1918 self.buffer = self.guild_id.members(&self.http, Some(grab_size), self.after).await?;
1919
1920 // Get the last member. If shorter than 1000, there are no more results anyway
1921 self.after = self.buffer.get(grab_size as usize - 1).map(|member| member.user.id);
1922
1923 // Reverse to optimize pop()
1924 self.buffer.reverse();
1925
1926 self.tried_fetch = true;
1927
1928 Ok(())
1929 }
1930
1931 /// Streams over all the members in a guild.
1932 ///
1933 /// This is accomplished and equivalent to repeated calls to [`GuildId::members`]. A buffer of
1934 /// at most 1,000 members is used to reduce the number of calls necessary.
1935 ///
1936 /// # Examples
1937 ///
1938 /// ```rust,no_run
1939 /// # use serenity::model::id::GuildId;
1940 /// # use serenity::http::Http;
1941 /// #
1942 /// # async fn run() {
1943 /// # let guild_id = GuildId::new(1);
1944 /// # let ctx: Http = unimplemented!();
1945 /// use serenity::futures::StreamExt;
1946 /// use serenity::model::guild::MembersIter;
1947 ///
1948 /// let mut members = MembersIter::<Http>::stream(&ctx, guild_id).boxed();
1949 /// while let Some(member_result) = members.next().await {
1950 /// match member_result {
1951 /// Ok(member) => println!("{} is {}", member, member.display_name(),),
1952 /// Err(error) => eprintln!("Uh oh! Error: {}", error),
1953 /// }
1954 /// }
1955 /// # }
1956 /// ```
1957 pub fn stream(http: impl AsRef<Http>, guild_id: GuildId) -> impl Stream<Item = Result<Member>> {
1958 let init_state = MembersIter::new(guild_id, http);
1959
1960 futures::stream::unfold(init_state, |mut state| async {
1961 if state.buffer.is_empty() && state.after.is_some() || !state.tried_fetch {
1962 if let Err(error) = state.refresh().await {
1963 return Some((Err(error), state));
1964 }
1965 }
1966
1967 state.buffer.pop().map(|entry| (Ok(entry), state))
1968 })
1969 }
1970}
1971
1972#[derive(Clone, Copy, Debug, Eq, Hash, PartialEq, Deserialize, Serialize)]
1973#[non_exhaustive]
1974pub enum GuildWidgetStyle {
1975 Shield,
1976 Banner1,
1977 Banner2,
1978 Banner3,
1979 Banner4,
1980}
1981
1982impl fmt::Display for GuildWidgetStyle {
1983 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1984 match self {
1985 Self::Shield => f.write_str("shield"),
1986 Self::Banner1 => f.write_str("banner1"),
1987 Self::Banner2 => f.write_str("banner2"),
1988 Self::Banner3 => f.write_str("banner3"),
1989 Self::Banner4 => f.write_str("banner4"),
1990 }
1991 }
1992}