*: Add typed Snowflake IDs (#122)

This PR closes #120.
This commit is contained in:
Tadeo Kondrak 2020-07-21 14:27:59 -06:00 committed by diamondburned
parent 24f7ed0499
commit d290b0d01c
43 changed files with 687 additions and 505 deletions

View File

@ -9,7 +9,7 @@ import (
var EndpointChannels = Endpoint + "channels/" var EndpointChannels = Endpoint + "channels/"
// Channels returns a list of guild channel objects. // Channels returns a list of guild channel objects.
func (c *Client) Channels(guildID discord.Snowflake) ([]discord.Channel, error) { func (c *Client) Channels(guildID discord.GuildID) ([]discord.Channel, error) {
var chs []discord.Channel var chs []discord.Channel
return chs, c.RequestJSON(&chs, "GET", EndpointGuilds+guildID.String()+"/channels") return chs, c.RequestJSON(&chs, "GET", EndpointGuilds+guildID.String()+"/channels")
} }
@ -56,7 +56,7 @@ type CreateChannelData struct {
// CategoryID is the id of the parent category for a channel. // CategoryID is the id of the parent category for a channel.
// //
// Channel Types: Text, News, Store, Voice // Channel Types: Text, News, Store, Voice
CategoryID discord.Snowflake `json:"parent_id,string,omitempty"` CategoryID discord.ChannelID `json:"parent_id,string,omitempty"`
// NSFW specifies whether the channel is nsfw. // NSFW specifies whether the channel is nsfw.
// //
// Channel Types: Text, News, Store. // Channel Types: Text, News, Store.
@ -68,7 +68,7 @@ type CreateChannelData struct {
// Requires the MANAGE_CHANNELS permission. // Requires the MANAGE_CHANNELS permission.
// Fires a Channel Create Gateway event. // Fires a Channel Create Gateway event.
func (c *Client) CreateChannel( func (c *Client) CreateChannel(
guildID discord.Snowflake, data CreateChannelData) (*discord.Channel, error) { guildID discord.GuildID, data CreateChannelData) (*discord.Channel, error) {
var ch *discord.Channel var ch *discord.Channel
return ch, c.RequestJSON( return ch, c.RequestJSON(
&ch, "POST", &ch, "POST",
@ -79,7 +79,7 @@ func (c *Client) CreateChannel(
type MoveChannelData struct { type MoveChannelData struct {
// ID is the channel id. // ID is the channel id.
ID discord.Snowflake `json:"id"` ID discord.ChannelID `json:"id"`
// Position is the sorting position of the channel // Position is the sorting position of the channel
Position option.Int `json:"position"` Position option.Int `json:"position"`
} }
@ -87,7 +87,7 @@ type MoveChannelData struct {
// MoveChannel modifies the position of channels in the guild. // MoveChannel modifies the position of channels in the guild.
// //
// Requires MANAGE_CHANNELS. // Requires MANAGE_CHANNELS.
func (c *Client) MoveChannel(guildID discord.Snowflake, datum []MoveChannelData) error { func (c *Client) MoveChannel(guildID discord.GuildID, datum []MoveChannelData) error {
return c.FastRequest( return c.FastRequest(
"PATCH", "PATCH",
EndpointGuilds+guildID.String()+"/channels", httputil.WithJSONBody(datum), EndpointGuilds+guildID.String()+"/channels", httputil.WithJSONBody(datum),
@ -95,7 +95,7 @@ func (c *Client) MoveChannel(guildID discord.Snowflake, datum []MoveChannelData)
} }
// Channel gets a channel by ID. Returns a channel object. // Channel gets a channel by ID. Returns a channel object.
func (c *Client) Channel(channelID discord.Snowflake) (*discord.Channel, error) { func (c *Client) Channel(channelID discord.ChannelID) (*discord.Channel, error) {
var channel *discord.Channel var channel *discord.Channel
return channel, c.RequestJSON(&channel, "GET", EndpointChannels+channelID.String()) return channel, c.RequestJSON(&channel, "GET", EndpointChannels+channelID.String())
} }
@ -147,13 +147,13 @@ type ModifyChannelData struct {
Permissions *[]discord.Overwrite `json:"permission_overwrites,omitempty"` Permissions *[]discord.Overwrite `json:"permission_overwrites,omitempty"`
// CategoryID is the id of the new parent category for a channel. // CategoryID is the id of the new parent category for a channel.
// Channel Types: Text, News, Store, Voice // Channel Types: Text, News, Store, Voice
CategoryID discord.Snowflake `json:"parent_id,string,omitempty"` CategoryID discord.ChannelID `json:"parent_id,string,omitempty"`
} }
// ModifyChannel updates a channel's settings. // ModifyChannel updates a channel's settings.
// //
// Requires the MANAGE_CHANNELS permission for the guild. // Requires the MANAGE_CHANNELS permission for the guild.
func (c *Client) ModifyChannel(channelID discord.Snowflake, data ModifyChannelData) error { func (c *Client) ModifyChannel(channelID discord.ChannelID, data ModifyChannelData) error {
return c.FastRequest("PATCH", EndpointChannels+channelID.String(), httputil.WithJSONBody(data)) return c.FastRequest("PATCH", EndpointChannels+channelID.String(), httputil.WithJSONBody(data))
} }
@ -163,7 +163,7 @@ func (c *Client) ModifyChannel(channelID discord.Snowflake, data ModifyChannelDa
// Channel Update Gateway event will fire for each of them. // Channel Update Gateway event will fire for each of them.
// //
// Fires a Channel Delete Gateway event. // Fires a Channel Delete Gateway event.
func (c *Client) DeleteChannel(channelID discord.Snowflake) error { func (c *Client) DeleteChannel(channelID discord.ChannelID) error {
return c.FastRequest("DELETE", EndpointChannels+channelID.String()) return c.FastRequest("DELETE", EndpointChannels+channelID.String())
} }
@ -181,7 +181,7 @@ type EditChannelPermissionData struct {
// //
// Requires the MANAGE_ROLES permission. // Requires the MANAGE_ROLES permission.
func (c *Client) EditChannelPermission( func (c *Client) EditChannelPermission(
channelID, overwriteID discord.Snowflake, data EditChannelPermissionData) error { channelID discord.ChannelID, overwriteID discord.Snowflake, data EditChannelPermissionData) error {
return c.FastRequest( return c.FastRequest(
"PUT", EndpointChannels+channelID.String()+"/permissions/"+overwriteID.String(), "PUT", EndpointChannels+channelID.String()+"/permissions/"+overwriteID.String(),
@ -202,13 +202,13 @@ func (c *Client) DeleteChannelPermission(channelID, overwriteID discord.Snowflak
// Typing posts a typing indicator to the channel. Undocumented, but the client // Typing posts a typing indicator to the channel. Undocumented, but the client
// usually clears the typing indicator after 8-10 seconds (or after a message). // usually clears the typing indicator after 8-10 seconds (or after a message).
func (c *Client) Typing(channelID discord.Snowflake) error { func (c *Client) Typing(channelID discord.ChannelID) error {
return c.FastRequest("POST", EndpointChannels+channelID.String()+"/typing") return c.FastRequest("POST", EndpointChannels+channelID.String()+"/typing")
} }
// PinnedMessages returns all pinned messages in the channel as an array of // PinnedMessages returns all pinned messages in the channel as an array of
// message objects. // message objects.
func (c *Client) PinnedMessages(channelID discord.Snowflake) ([]discord.Message, error) { func (c *Client) PinnedMessages(channelID discord.ChannelID) ([]discord.Message, error) {
var pinned []discord.Message var pinned []discord.Message
return pinned, c.RequestJSON(&pinned, "GET", EndpointChannels+channelID.String()+"/pins") return pinned, c.RequestJSON(&pinned, "GET", EndpointChannels+channelID.String()+"/pins")
} }
@ -216,22 +216,21 @@ func (c *Client) PinnedMessages(channelID discord.Snowflake) ([]discord.Message,
// PinMessage pins a message in a channel. // PinMessage pins a message in a channel.
// //
// Requires the MANAGE_MESSAGES permission. // Requires the MANAGE_MESSAGES permission.
func (c *Client) PinMessage(channelID, messageID discord.Snowflake) error { func (c *Client) PinMessage(channelID discord.ChannelID, messageID discord.MessageID) error {
return c.FastRequest("PUT", EndpointChannels+channelID.String()+"/pins/"+messageID.String()) return c.FastRequest("PUT", EndpointChannels+channelID.String()+"/pins/"+messageID.String())
} }
// UnpinMessage deletes a pinned message in a channel. // UnpinMessage deletes a pinned message in a channel.
// //
// Requires the MANAGE_MESSAGES permission. // Requires the MANAGE_MESSAGES permission.
func (c *Client) UnpinMessage(channelID, messageID discord.Snowflake) error { func (c *Client) UnpinMessage(channelID discord.ChannelID, messageID discord.MessageID) error {
return c.FastRequest("DELETE", EndpointChannels+channelID.String()+"/pins/"+messageID.String()) return c.FastRequest("DELETE", EndpointChannels+channelID.String()+"/pins/"+messageID.String())
} }
// AddRecipient adds a user to a group direct message. As accessToken is needed, // AddRecipient adds a user to a group direct message. As accessToken is needed,
// clearly this endpoint should only be used for OAuth. AccessToken can be // clearly this endpoint should only be used for OAuth. AccessToken can be
// obtained with the "gdm.join" scope. // obtained with the "gdm.join" scope.
func (c *Client) AddRecipient( func (c *Client) AddRecipient(channelID discord.ChannelID, userID discord.UserID, accessToken, nickname string) error {
channelID, userID discord.Snowflake, accessToken, nickname string) error {
var params struct { var params struct {
AccessToken string `json:"access_token"` AccessToken string `json:"access_token"`
@ -249,7 +248,7 @@ func (c *Client) AddRecipient(
} }
// RemoveRecipient removes a user from a group direct message. // RemoveRecipient removes a user from a group direct message.
func (c *Client) RemoveRecipient(channelID, userID discord.Snowflake) error { func (c *Client) RemoveRecipient(channelID discord.ChannelID, userID discord.UserID) error {
return c.FastRequest( return c.FastRequest(
"DELETE", "DELETE",
EndpointChannels+channelID.String()+"/recipients/"+userID.String(), EndpointChannels+channelID.String()+"/recipients/"+userID.String(),
@ -264,7 +263,7 @@ type Ack struct {
// Ack marks the read state of a channel. This is undocumented. The method will // Ack marks the read state of a channel. This is undocumented. The method will
// write to the ack variable passed in. If this method is called asynchronously, // write to the ack variable passed in. If this method is called asynchronously,
// then ack should be mutex guarded. // then ack should be mutex guarded.
func (c *Client) Ack(channelID, messageID discord.Snowflake, ack *Ack) error { func (c *Client) Ack(channelID discord.ChannelID, messageID discord.MessageID, ack *Ack) error {
return c.RequestJSON( return c.RequestJSON(
ack, "POST", ack, "POST",
EndpointChannels+channelID.String()+"/messages/"+messageID.String()+"/ack", EndpointChannels+channelID.String()+"/messages/"+messageID.String()+"/ack",

View File

@ -12,18 +12,18 @@ type Emoji = string
// NewCustomEmoji creates a new Emoji using a custom guild emoji as // NewCustomEmoji creates a new Emoji using a custom guild emoji as
// base. // base.
// Unicode emojis should be directly passed to the function using Emoji. // Unicode emojis should be directly passed to the function using Emoji.
func NewCustomEmoji(id discord.Snowflake, name string) Emoji { func NewCustomEmoji(id discord.EmojiID, name string) Emoji {
return name + ":" + id.String() return name + ":" + id.String()
} }
// Emojis returns a list of emoji objects for the given guild. // Emojis returns a list of emoji objects for the given guild.
func (c *Client) Emojis(guildID discord.Snowflake) ([]discord.Emoji, error) { func (c *Client) Emojis(guildID discord.GuildID) ([]discord.Emoji, error) {
var emjs []discord.Emoji var emjs []discord.Emoji
return emjs, c.RequestJSON(&emjs, "GET", EndpointGuilds+guildID.String()+"/emojis") return emjs, c.RequestJSON(&emjs, "GET", EndpointGuilds+guildID.String()+"/emojis")
} }
// Emoji returns an emoji object for the given guild and emoji IDs. // Emoji returns an emoji object for the given guild and emoji IDs.
func (c *Client) Emoji(guildID, emojiID discord.Snowflake) (*discord.Emoji, error) { func (c *Client) Emoji(guildID discord.GuildID, emojiID discord.EmojiID) (*discord.Emoji, error) {
var emj *discord.Emoji var emj *discord.Emoji
return emj, c.RequestJSON(&emj, "GET", return emj, c.RequestJSON(&emj, "GET",
EndpointGuilds+guildID.String()+"/emojis/"+emojiID.String()) EndpointGuilds+guildID.String()+"/emojis/"+emojiID.String())
@ -36,7 +36,7 @@ type CreateEmojiData struct {
// Image is the the 128x128 emoji image. // Image is the the 128x128 emoji image.
Image Image `json:"image"` Image Image `json:"image"`
// Roles are the roles for which this emoji will be whitelisted. // Roles are the roles for which this emoji will be whitelisted.
Roles *[]discord.Snowflake `json:"roles,omitempty"` Roles *[]discord.RoleID `json:"roles,omitempty"`
} }
// CreateEmoji creates a new emoji in the guild. This endpoint requires // CreateEmoji creates a new emoji in the guild. This endpoint requires
@ -44,8 +44,7 @@ type CreateEmojiData struct {
// "image/gif". However, ContentType can also be automatically detected // "image/gif". However, ContentType can also be automatically detected
// (though shouldn't be relied on). // (though shouldn't be relied on).
// Emojis and animated emojis have a maximum file size of 256kb. // Emojis and animated emojis have a maximum file size of 256kb.
func (c *Client) CreateEmoji( func (c *Client) CreateEmoji(guildID discord.GuildID, data CreateEmojiData) (*discord.Emoji, error) {
guildID discord.Snowflake, data CreateEmojiData) (*discord.Emoji, error) {
// Max 256KB // Max 256KB
if err := data.Image.Validate(256 * 1000); err != nil { if err := data.Image.Validate(256 * 1000); err != nil {
@ -65,14 +64,14 @@ type ModifyEmojiData struct {
// Name is the name of the emoji. // Name is the name of the emoji.
Name string `json:"name,omitempty"` Name string `json:"name,omitempty"`
// Roles are the roles to which this emoji will be whitelisted. // Roles are the roles to which this emoji will be whitelisted.
Roles *[]discord.Snowflake `json:"roles,omitempty"` Roles *[]discord.RoleID `json:"roles,omitempty"`
} }
// ModifyEmoji changes an existing emoji. This requires MANAGE_EMOJIS. Name and // ModifyEmoji changes an existing emoji. This requires MANAGE_EMOJIS. Name and
// roles are optional fields (though you'd want to change either though). // roles are optional fields (though you'd want to change either though).
// //
// Fires a Guild Emojis Update Gateway event. // Fires a Guild Emojis Update Gateway event.
func (c *Client) ModifyEmoji(guildID, emojiID discord.Snowflake, data ModifyEmojiData) error { func (c *Client) ModifyEmoji(guildID discord.GuildID, emojiID discord.EmojiID, data ModifyEmojiData) error {
return c.FastRequest( return c.FastRequest(
"PATCH", "PATCH",
EndpointGuilds+guildID.String()+"/emojis/"+emojiID.String(), EndpointGuilds+guildID.String()+"/emojis/"+emojiID.String(),
@ -84,6 +83,6 @@ func (c *Client) ModifyEmoji(guildID, emojiID discord.Snowflake, data ModifyEmoj
// //
// Requires the MANAGE_EMOJIS permission. // Requires the MANAGE_EMOJIS permission.
// Fires a Guild Emojis Update Gateway event. // Fires a Guild Emojis Update Gateway event.
func (c *Client) DeleteEmoji(guildID, emojiID discord.Snowflake) error { func (c *Client) DeleteEmoji(guildID discord.GuildID, emojiID discord.EmojiID) error {
return c.FastRequest("DELETE", EndpointGuilds+guildID.String()+"/emojis/"+emojiID.String()) return c.FastRequest("DELETE", EndpointGuilds+guildID.String()+"/emojis/"+emojiID.String())
} }

View File

@ -55,13 +55,13 @@ type CreateGuildData struct {
Channels []discord.Channel `json:"channels,omitempty"` Channels []discord.Channel `json:"channels,omitempty"`
// AFKChannelID is the id for the afk channel. // AFKChannelID is the id for the afk channel.
AFKChannelID discord.Snowflake `json:"afk_channel_id,omitempty"` AFKChannelID discord.ChannelID `json:"afk_channel_id,omitempty"`
// AFKTimeout is the afk timeout in seconds. // AFKTimeout is the afk timeout in seconds.
AFKTimeout option.Seconds `json:"afk_timeout,omitempty"` AFKTimeout option.Seconds `json:"afk_timeout,omitempty"`
// SystemChannelID is the id of the channel where guild notices such as // SystemChannelID is the id of the channel where guild notices such as
// welcome messages and boost events are posted. // welcome messages and boost events are posted.
SystemChannelID discord.Snowflake `json:"system_channel_id,omitempty"` SystemChannelID discord.ChannelID `json:"system_channel_id,omitempty"`
} }
// CreateGuild creates a new guild. Returns a guild object on success. // CreateGuild creates a new guild. Returns a guild object on success.
@ -75,7 +75,7 @@ func (c *Client) CreateGuild(data CreateGuildData) (*discord.Guild, error) {
// Guild returns the guild object for the given id. // Guild returns the guild object for the given id.
// ApproximateMembers and ApproximatePresences will not be set. // ApproximateMembers and ApproximatePresences will not be set.
func (c *Client) Guild(id discord.Snowflake) (*discord.Guild, error) { func (c *Client) Guild(id discord.GuildID) (*discord.Guild, error) {
var g *discord.Guild var g *discord.Guild
return g, c.RequestJSON(&g, "GET", EndpointGuilds+id.String()) return g, c.RequestJSON(&g, "GET", EndpointGuilds+id.String())
} }
@ -84,7 +84,7 @@ func (c *Client) Guild(id discord.Snowflake) (*discord.Guild, error) {
// user is not in the guild. // user is not in the guild.
// //
// This endpoint is only for public guilds. // This endpoint is only for public guilds.
func (c *Client) GuildPreview(id discord.Snowflake) (*discord.GuildPreview, error) { func (c *Client) GuildPreview(id discord.GuildID) (*discord.GuildPreview, error) {
var g *discord.GuildPreview var g *discord.GuildPreview
return g, c.RequestJSON(&g, "GET", EndpointGuilds+id.String()+"/preview") return g, c.RequestJSON(&g, "GET", EndpointGuilds+id.String()+"/preview")
} }
@ -92,7 +92,7 @@ func (c *Client) GuildPreview(id discord.Snowflake) (*discord.GuildPreview, erro
// GuildWithCount returns the guild object for the given id. // GuildWithCount returns the guild object for the given id.
// This will also set the ApproximateMembers and ApproximatePresences fields // This will also set the ApproximateMembers and ApproximatePresences fields
// of the guild struct. // of the guild struct.
func (c *Client) GuildWithCount(id discord.Snowflake) (*discord.Guild, error) { func (c *Client) GuildWithCount(id discord.GuildID) (*discord.Guild, error) {
var g *discord.Guild var g *discord.Guild
return g, c.RequestJSON( return g, c.RequestJSON(
&g, "GET", &g, "GET",
@ -133,7 +133,7 @@ func (c *Client) Guilds(limit uint) ([]discord.Guild, error) {
// may be less, if no more guilds are available. // may be less, if no more guilds are available.
// //
// Requires the guilds OAuth2 scope. // Requires the guilds OAuth2 scope.
func (c *Client) GuildsBefore(before discord.Snowflake, limit uint) ([]discord.Guild, error) { func (c *Client) GuildsBefore(before discord.GuildID, limit uint) ([]discord.Guild, error) {
var guilds []discord.Guild var guilds []discord.Guild
// this is the limit of max guilds per request,as imposed by Discord // this is the limit of max guilds per request,as imposed by Discord
@ -175,7 +175,7 @@ func (c *Client) GuildsBefore(before discord.Snowflake, limit uint) ([]discord.G
// may be less, if no more guilds are available. // may be less, if no more guilds are available.
// //
// Requires the guilds OAuth2 scope. // Requires the guilds OAuth2 scope.
func (c *Client) GuildsAfter(after discord.Snowflake, limit uint) ([]discord.Guild, error) { func (c *Client) GuildsAfter(after discord.GuildID, limit uint) ([]discord.Guild, error) {
var guilds []discord.Guild var guilds []discord.Guild
// this is the limit of max guilds per request, as imposed by Discord // this is the limit of max guilds per request, as imposed by Discord
@ -208,11 +208,11 @@ func (c *Client) GuildsAfter(after discord.Snowflake, limit uint) ([]discord.Gui
} }
func (c *Client) guildsRange( func (c *Client) guildsRange(
before, after discord.Snowflake, limit uint) ([]discord.Guild, error) { before, after discord.GuildID, limit uint) ([]discord.Guild, error) {
var param struct { var param struct {
Before discord.Snowflake `schema:"before,omitempty"` Before discord.GuildID `schema:"before,omitempty"`
After discord.Snowflake `schema:"after,omitempty"` After discord.GuildID `schema:"after,omitempty"`
Limit uint `schema:"limit"` Limit uint `schema:"limit"`
} }
@ -230,7 +230,7 @@ func (c *Client) guildsRange(
} }
// LeaveGuild leaves a guild. // LeaveGuild leaves a guild.
func (c *Client) LeaveGuild(id discord.Snowflake) error { func (c *Client) LeaveGuild(id discord.GuildID) error {
return c.FastRequest("DELETE", EndpointMe+"/guilds/"+id.String()) return c.FastRequest("DELETE", EndpointMe+"/guilds/"+id.String())
} }
@ -257,7 +257,7 @@ type ModifyGuildData struct {
// AFKChannelID is the id for the afk channel. // AFKChannelID is the id for the afk channel.
// //
// This field is nullable. // This field is nullable.
AFKChannelID discord.Snowflake `json:"afk_channel_id,string,omitempty"` AFKChannelID discord.ChannelID `json:"afk_channel_id,string,omitempty"`
// AFKTimeout is the afk timeout in seconds. // AFKTimeout is the afk timeout in seconds.
AFKTimeout option.Seconds `json:"afk_timeout,omitempty"` AFKTimeout option.Seconds `json:"afk_timeout,omitempty"`
// Icon is the base64 1024x1024 png/jpeg/gif image for the guild icon // Icon is the base64 1024x1024 png/jpeg/gif image for the guild icon
@ -271,23 +271,23 @@ type ModifyGuildData struct {
Banner *Image `json:"banner,omitempty"` Banner *Image `json:"banner,omitempty"`
// OwnerID is the user id to transfer guild ownership to (must be owner). // OwnerID is the user id to transfer guild ownership to (must be owner).
OwnerID discord.Snowflake `json:"owner_id,omitempty"` OwnerID discord.UserID `json:"owner_id,omitempty"`
// SystemChannelID is the id of the channel where guild notices such as // SystemChannelID is the id of the channel where guild notices such as
// welcome messages and boost events are posted. // welcome messages and boost events are posted.
// //
// This field is nullable. // This field is nullable.
SystemChannelID discord.Snowflake `json:"system_channel_id,omitempty"` SystemChannelID discord.ChannelID `json:"system_channel_id,omitempty"`
// RulesChannelID is the id of the channel where "PUBLIC" guilds display // RulesChannelID is the id of the channel where "PUBLIC" guilds display
// rules and/or guidelines. // rules and/or guidelines.
// //
// This field is nullable. // This field is nullable.
RulesChannelID discord.Snowflake `json:"rules_channel_id,omitempty"` RulesChannelID discord.ChannelID `json:"rules_channel_id,omitempty"`
// PublicUpdatesChannelID is the id of the channel where admins and // PublicUpdatesChannelID is the id of the channel where admins and
// moderators of "PUBLIC" guilds receive notices from Discord. // moderators of "PUBLIC" guilds receive notices from Discord.
// //
// This field is nullable. // This field is nullable.
PublicUpdatesChannelID discord.Snowflake `json:"public_updates_channel_id,omitempty"` PublicUpdatesChannelID discord.ChannelID `json:"public_updates_channel_id,omitempty"`
// PreferredLocale is the preferred locale of a "PUBLIC" guild used in // PreferredLocale is the preferred locale of a "PUBLIC" guild used in
// server discovery and notices from Discord. // server discovery and notices from Discord.
@ -298,7 +298,7 @@ type ModifyGuildData struct {
// ModifyGuild modifies a guild's settings. Requires the MANAGE_GUILD permission. // ModifyGuild modifies a guild's settings. Requires the MANAGE_GUILD permission.
// Fires a Guild Update Gateway event. // Fires a Guild Update Gateway event.
func (c *Client) ModifyGuild(id discord.Snowflake, data ModifyGuildData) (*discord.Guild, error) { func (c *Client) ModifyGuild(id discord.GuildID, data ModifyGuildData) (*discord.Guild, error) {
var g *discord.Guild var g *discord.Guild
return g, c.RequestJSON( return g, c.RequestJSON(
&g, "PATCH", &g, "PATCH",
@ -311,13 +311,13 @@ func (c *Client) ModifyGuild(id discord.Snowflake, data ModifyGuildData) (*disco
// DeleteGuild deletes a guild permanently. The User must be owner. // DeleteGuild deletes a guild permanently. The User must be owner.
// //
// Fires a Guild Delete Gateway event. // Fires a Guild Delete Gateway event.
func (c *Client) DeleteGuild(id discord.Snowflake) error { func (c *Client) DeleteGuild(id discord.GuildID) error {
return c.FastRequest("DELETE", EndpointGuilds+id.String()) return c.FastRequest("DELETE", EndpointGuilds+id.String())
} }
// GuildVoiceRegions is the same as /voice, but returns VIP ones as well if // GuildVoiceRegions is the same as /voice, but returns VIP ones as well if
// available. // available.
func (c *Client) VoiceRegionsGuild(guildID discord.Snowflake) ([]discord.VoiceRegion, error) { func (c *Client) VoiceRegionsGuild(guildID discord.GuildID) ([]discord.VoiceRegion, error) {
var vrs []discord.VoiceRegion var vrs []discord.VoiceRegion
return vrs, c.RequestJSON(&vrs, "GET", EndpointGuilds+guildID.String()+"/regions") return vrs, c.RequestJSON(&vrs, "GET", EndpointGuilds+guildID.String()+"/regions")
} }
@ -325,7 +325,7 @@ func (c *Client) VoiceRegionsGuild(guildID discord.Snowflake) ([]discord.VoiceRe
// https://discord.com/developers/docs/resources/audit-log#get-guild-audit-log-query-string-parameters // https://discord.com/developers/docs/resources/audit-log#get-guild-audit-log-query-string-parameters
type AuditLogData struct { type AuditLogData struct {
// UserID filters the log for actions made by a user. // UserID filters the log for actions made by a user.
UserID discord.Snowflake `schema:"user_id,omitempty"` UserID discord.UserID `schema:"user_id,omitempty"`
// ActionType is the type of audit log event. // ActionType is the type of audit log event.
ActionType discord.AuditLogEvent `schema:"action_type,omitempty"` ActionType discord.AuditLogEvent `schema:"action_type,omitempty"`
// Before filters the log before a certain entry ID. // Before filters the log before a certain entry ID.
@ -338,7 +338,7 @@ type AuditLogData struct {
// AuditLog returns an audit log object for the guild. // AuditLog returns an audit log object for the guild.
// //
// Requires the VIEW_AUDIT_LOG permission. // Requires the VIEW_AUDIT_LOG permission.
func (c *Client) AuditLog(guildID discord.Snowflake, data AuditLogData) (*discord.AuditLog, error) { func (c *Client) AuditLog(guildID discord.GuildID, data AuditLogData) (*discord.AuditLog, error) {
switch { switch {
case data.Limit == 0: case data.Limit == 0:
data.Limit = 50 data.Limit = 50
@ -358,7 +358,7 @@ func (c *Client) AuditLog(guildID discord.Snowflake, data AuditLogData) (*discor
// Integrations returns a list of integration objects for the guild. // Integrations returns a list of integration objects for the guild.
// //
// Requires the MANAGE_GUILD permission. // Requires the MANAGE_GUILD permission.
func (c *Client) Integrations(guildID discord.Snowflake) ([]discord.Integration, error) { func (c *Client) Integrations(guildID discord.GuildID) ([]discord.Integration, error) {
var ints []discord.Integration var ints []discord.Integration
return ints, c.RequestJSON(&ints, "GET", EndpointGuilds+guildID.String()+"/integrations") return ints, c.RequestJSON(&ints, "GET", EndpointGuilds+guildID.String()+"/integrations")
} }
@ -369,11 +369,11 @@ func (c *Client) Integrations(guildID discord.Snowflake) ([]discord.Integration,
// Requires the MANAGE_GUILD permission. // Requires the MANAGE_GUILD permission.
// Fires a Guild Integrations Update Gateway event. // Fires a Guild Integrations Update Gateway event.
func (c *Client) AttachIntegration(guildID, func (c *Client) AttachIntegration(guildID,
integrationID discord.Snowflake, integrationType discord.Service) error { integrationID discord.IntegrationID, integrationType discord.Service) error {
var param struct { var param struct {
Type discord.Service `json:"type"` Type discord.Service `json:"type"`
ID discord.Snowflake `json:"id"` ID discord.IntegrationID `json:"id"`
} }
param.Type = integrationType param.Type = integrationType
@ -405,7 +405,7 @@ type ModifyIntegrationData struct {
// Requires the MANAGE_GUILD permission. // Requires the MANAGE_GUILD permission.
// Fires a Guild Integrations Update Gateway event. // Fires a Guild Integrations Update Gateway event.
func (c *Client) ModifyIntegration( func (c *Client) ModifyIntegration(
guildID, integrationID discord.Snowflake, data ModifyIntegrationData) error { guildID discord.GuildID, integrationID discord.IntegrationID, data ModifyIntegrationData) error {
return c.FastRequest( return c.FastRequest(
"PATCH", "PATCH",
EndpointGuilds+guildID.String()+"/integrations/"+integrationID.String(), EndpointGuilds+guildID.String()+"/integrations/"+integrationID.String(),
@ -414,7 +414,7 @@ func (c *Client) ModifyIntegration(
} }
// Sync an integration. Requires the MANAGE_GUILD permission. // Sync an integration. Requires the MANAGE_GUILD permission.
func (c *Client) SyncIntegration(guildID, integrationID discord.Snowflake) error { func (c *Client) SyncIntegration(guildID discord.GuildID, integrationID discord.IntegrationID) error {
return c.FastRequest( return c.FastRequest(
"POST", "POST",
EndpointGuilds+guildID.String()+"/integrations/"+integrationID.String()+"/sync", EndpointGuilds+guildID.String()+"/integrations/"+integrationID.String()+"/sync",
@ -424,7 +424,7 @@ func (c *Client) SyncIntegration(guildID, integrationID discord.Snowflake) error
// GuildWidget returns the guild widget object. // GuildWidget returns the guild widget object.
// //
// Requires the MANAGE_GUILD permission. // Requires the MANAGE_GUILD permission.
func (c *Client) GuildWidget(guildID discord.Snowflake) (*discord.GuildWidget, error) { func (c *Client) GuildWidget(guildID discord.GuildID) (*discord.GuildWidget, error) {
var ge *discord.GuildWidget var ge *discord.GuildWidget
return ge, c.RequestJSON(&ge, "GET", EndpointGuilds+guildID.String()+"/widget") return ge, c.RequestJSON(&ge, "GET", EndpointGuilds+guildID.String()+"/widget")
} }
@ -434,14 +434,14 @@ type ModifyGuildWidgetData struct {
// Enabled specifies whether the widget is enabled. // Enabled specifies whether the widget is enabled.
Enabled option.Bool `json:"enabled,omitempty"` Enabled option.Bool `json:"enabled,omitempty"`
// ChannelID is the widget channel id. // ChannelID is the widget channel id.
ChannelID discord.Snowflake `json:"channel_id,omitempty"` ChannelID discord.ChannelID `json:"channel_id,omitempty"`
} }
// ModifyGuildWidget modifies a guild widget object for the guild. // ModifyGuildWidget modifies a guild widget object for the guild.
// //
// Requires the MANAGE_GUILD permission. // Requires the MANAGE_GUILD permission.
func (c *Client) ModifyGuildWidget( func (c *Client) ModifyGuildWidget(
guildID discord.Snowflake, data ModifyGuildWidgetData) (*discord.GuildWidget, error) { guildID discord.GuildID, data ModifyGuildWidgetData) (*discord.GuildWidget, error) {
var w *discord.GuildWidget var w *discord.GuildWidget
return w, c.RequestJSON( return w, c.RequestJSON(
@ -456,7 +456,7 @@ func (c *Client) ModifyGuildWidget(
// guild is not set. // guild is not set.
// //
// Requires MANAGE_GUILD. // Requires MANAGE_GUILD.
func (c *Client) GuildVanityURL(guildID discord.Snowflake) (*discord.Invite, error) { func (c *Client) GuildVanityURL(guildID discord.GuildID) (*discord.Invite, error) {
var inv *discord.Invite var inv *discord.Invite
return inv, c.RequestJSON(&inv, "GET", EndpointGuilds+guildID.String()+"/vanity-url") return inv, c.RequestJSON(&inv, "GET", EndpointGuilds+guildID.String()+"/vanity-url")
} }
@ -496,13 +496,13 @@ const (
// GuildImageURL returns a link to the PNG image widget for the guild. // GuildImageURL returns a link to the PNG image widget for the guild.
// //
// Requires no permissions or authentication. // Requires no permissions or authentication.
func (c *Client) GuildImageURL(guildID discord.Snowflake, img GuildImageStyle) string { func (c *Client) GuildImageURL(guildID discord.GuildID, img GuildImageStyle) string {
return EndpointGuilds + guildID.String() + "/widget.png?style=" + string(img) return EndpointGuilds + guildID.String() + "/widget.png?style=" + string(img)
} }
// GuildImage returns a PNG image widget for the guild. Requires no permissions // GuildImage returns a PNG image widget for the guild. Requires no permissions
// or authentication. // or authentication.
func (c *Client) GuildImage(guildID discord.Snowflake, img GuildImageStyle) (io.ReadCloser, error) { func (c *Client) GuildImage(guildID discord.GuildID, img GuildImageStyle) (io.ReadCloser, error) {
r, err := c.Request("GET", c.GuildImageURL(guildID, img)) r, err := c.Request("GET", c.GuildImageURL(guildID, img))
if err != nil { if err != nil {
return nil, err return nil, err

View File

@ -14,7 +14,7 @@ import (
type testConfig struct { type testConfig struct {
BotToken string BotToken string
ChannelID discord.Snowflake ChannelID discord.ChannelID
} }
func mustConfig(t *testing.T) testConfig { func mustConfig(t *testing.T) testConfig {
@ -35,7 +35,7 @@ func mustConfig(t *testing.T) testConfig {
return testConfig{ return testConfig{
BotToken: token, BotToken: token,
ChannelID: id, ChannelID: discord.ChannelID(id),
} }
} }

View File

@ -39,7 +39,7 @@ func (c *Client) InviteWithCounts(code string) (*discord.Invite, error) {
// the channel. Only usable for guild channels. // the channel. Only usable for guild channels.
// //
// Requires the MANAGE_CHANNELS permission. // Requires the MANAGE_CHANNELS permission.
func (c *Client) ChannelInvites(channelID discord.Snowflake) ([]discord.Invite, error) { func (c *Client) ChannelInvites(channelID discord.ChannelID) ([]discord.Invite, error) {
var invs []discord.Invite var invs []discord.Invite
return invs, c.RequestJSON(&invs, "GET", return invs, c.RequestJSON(&invs, "GET",
EndpointChannels+channelID.String()+"/invites") EndpointChannels+channelID.String()+"/invites")
@ -49,7 +49,7 @@ func (c *Client) ChannelInvites(channelID discord.Snowflake) ([]discord.Invite,
// guild. // guild.
// //
// Requires the MANAGE_GUILD permission. // Requires the MANAGE_GUILD permission.
func (c *Client) GuildInvites(guildID discord.Snowflake) ([]discord.Invite, error) { func (c *Client) GuildInvites(guildID discord.GuildID) ([]discord.Invite, error) {
var invs []discord.Invite var invs []discord.Invite
return invs, c.RequestJSON(&invs, "GET", return invs, c.RequestJSON(&invs, "GET",
EndpointGuilds+guildID.String()+"/invites") EndpointGuilds+guildID.String()+"/invites")
@ -82,7 +82,7 @@ type CreateInviteData struct {
// //
// Requires the CREATE_INSTANT_INVITE permission. // Requires the CREATE_INSTANT_INVITE permission.
func (c *Client) CreateInvite( func (c *Client) CreateInvite(
channelID discord.Snowflake, data CreateInviteData) (*discord.Invite, error) { channelID discord.ChannelID, data CreateInviteData) (*discord.Invite, error) {
var inv *discord.Invite var inv *discord.Invite
return inv, c.RequestJSON( return inv, c.RequestJSON(
&inv, "POST", &inv, "POST",

View File

@ -7,7 +7,7 @@ import (
) )
// Member returns a guild member object for the specified user.. // Member returns a guild member object for the specified user..
func (c *Client) Member(guildID, userID discord.Snowflake) (*discord.Member, error) { func (c *Client) Member(guildID discord.GuildID, userID discord.UserID) (*discord.Member, error) {
var m *discord.Member var m *discord.Member
return m, c.RequestJSON(&m, "GET", EndpointGuilds+guildID.String()+"/members/"+userID.String()) return m, c.RequestJSON(&m, "GET", EndpointGuilds+guildID.String()+"/members/"+userID.String())
} }
@ -21,7 +21,7 @@ func (c *Client) Member(guildID, userID discord.Snowflake) (*discord.Member, err
// they may be less, if no more members are available. // they may be less, if no more members are available.
// //
// When fetching the members, those with the smallest ID will be fetched first. // When fetching the members, those with the smallest ID will be fetched first.
func (c *Client) Members(guildID discord.Snowflake, limit uint) ([]discord.Member, error) { func (c *Client) Members(guildID discord.GuildID, limit uint) ([]discord.Member, error) {
return c.MembersAfter(guildID, 0, limit) return c.MembersAfter(guildID, 0, limit)
} }
@ -33,7 +33,7 @@ func (c *Client) Members(guildID discord.Snowflake, limit uint) ([]discord.Membe
// maximum a total of limit/1000 rounded up requests will be made, although // maximum a total of limit/1000 rounded up requests will be made, although
// they may be less, if no more members are available. // they may be less, if no more members are available.
func (c *Client) MembersAfter( func (c *Client) MembersAfter(
guildID, after discord.Snowflake, limit uint) ([]discord.Member, error) { guildID discord.GuildID, after discord.UserID, limit uint) ([]discord.Member, error) {
var mems []discord.Member var mems []discord.Member
@ -67,7 +67,7 @@ func (c *Client) MembersAfter(
} }
func (c *Client) membersAfter( func (c *Client) membersAfter(
guildID, after discord.Snowflake, limit uint) ([]discord.Member, error) { guildID discord.GuildID, after discord.UserID, limit uint) ([]discord.Member, error) {
switch { switch {
case limit == 0: case limit == 0:
@ -77,8 +77,8 @@ func (c *Client) membersAfter(
} }
var param struct { var param struct {
After discord.Snowflake `schema:"after,omitempty"` After discord.UserID `schema:"after,omitempty"`
Limit uint `schema:"limit"` Limit uint `schema:"limit"`
} }
param.Limit = limit param.Limit = limit
@ -104,7 +104,7 @@ type AddMemberData struct {
// Roles is an array of role ids the member is assigned. // Roles is an array of role ids the member is assigned.
// //
// Requires MANAGE_ROLES. // Requires MANAGE_ROLES.
Roles *[]discord.Snowflake `json:"roles,omitempty"` Roles *[]discord.RoleID `json:"roles,omitempty"`
// Mute specifies whether the user is muted in voice channels. // Mute specifies whether the user is muted in voice channels.
// //
// Requires MUTE_MEMBERS. // Requires MUTE_MEMBERS.
@ -126,7 +126,7 @@ type AddMemberData struct {
// application used for authorization), and the bot must be a member of the // application used for authorization), and the bot must be a member of the
// guild with CREATE_INSTANT_INVITE permission. // guild with CREATE_INSTANT_INVITE permission.
func (c *Client) AddMember( func (c *Client) AddMember(
guildID, userID discord.Snowflake, data AddMemberData) (*discord.Member, error) { guildID discord.GuildID, userID discord.UserID, data AddMemberData) (*discord.Member, error) {
var mem *discord.Member var mem *discord.Member
return mem, c.RequestJSON( return mem, c.RequestJSON(
&mem, "PUT", &mem, "PUT",
@ -144,7 +144,7 @@ type ModifyMemberData struct {
// Roles is an array of role ids the member is assigned. // Roles is an array of role ids the member is assigned.
// //
// Requires MANAGE_ROLES. // Requires MANAGE_ROLES.
Roles *[]discord.Snowflake `json:"roles,omitempty"` Roles *[]discord.RoleID `json:"roles,omitempty"`
// Mute specifies whether the user is muted in voice channels. // Mute specifies whether the user is muted in voice channels.
// //
// Requires MUTE_MEMBERS. // Requires MUTE_MEMBERS.
@ -158,14 +158,14 @@ type ModifyMemberData struct {
// connected to voice). // connected to voice).
// //
// Requires MOVE_MEMBER // Requires MOVE_MEMBER
VoiceChannel discord.Snowflake `json:"channel_id,omitempty"` VoiceChannel discord.ChannelID `json:"channel_id,omitempty"`
} }
// ModifyMember modifies attributes of a guild member. If the channel_id is set // ModifyMember modifies attributes of a guild member. If the channel_id is set
// to null, this will force the target user to be disconnected from voice. // to null, this will force the target user to be disconnected from voice.
// //
// Fires a Guild Member Update Gateway event. // Fires a Guild Member Update Gateway event.
func (c *Client) ModifyMember(guildID, userID discord.Snowflake, data ModifyMemberData) error { func (c *Client) ModifyMember(guildID discord.GuildID, userID discord.UserID, data ModifyMemberData) error {
return c.FastRequest( return c.FastRequest(
"PATCH", "PATCH",
@ -179,7 +179,7 @@ type PruneCountData struct {
// Days is the number of days to count prune for (1 or more, default 7). // Days is the number of days to count prune for (1 or more, default 7).
Days uint `schema:"days"` Days uint `schema:"days"`
// IncludedRoles are the role(s) to include. // IncludedRoles are the role(s) to include.
IncludedRoles []discord.Snowflake `schema:"include_roles,omitempty"` IncludedRoles []discord.RoleID `schema:"include_roles,omitempty"`
} }
// PruneCount returns the number of members that would be removed in a prune // PruneCount returns the number of members that would be removed in a prune
@ -191,7 +191,7 @@ type PruneCountData struct {
// will be counted in the prune and users with additional roles will not. // will be counted in the prune and users with additional roles will not.
// //
// Requires KICK_MEMBERS. // Requires KICK_MEMBERS.
func (c *Client) PruneCount(guildID discord.Snowflake, data PruneCountData) (uint, error) { func (c *Client) PruneCount(guildID discord.GuildID, data PruneCountData) (uint, error) {
if data.Days == 0 { if data.Days == 0 {
data.Days = 7 data.Days = 7
} }
@ -215,7 +215,7 @@ type PruneData struct {
// large guilds. // large guilds.
ReturnCount bool `schema:"compute_prune_count"` ReturnCount bool `schema:"compute_prune_count"`
// IncludedRoles are the role(s) to include. // IncludedRoles are the role(s) to include.
IncludedRoles []discord.Snowflake `schema:"include_roles,omitempty"` IncludedRoles []discord.RoleID `schema:"include_roles,omitempty"`
} }
// Prune begins a prune. Days must be 1 or more, default 7. // Prune begins a prune. Days must be 1 or more, default 7.
@ -227,7 +227,7 @@ type PruneData struct {
// //
// Requires KICK_MEMBERS. // Requires KICK_MEMBERS.
// Fires multiple Guild Member Remove Gateway events. // Fires multiple Guild Member Remove Gateway events.
func (c *Client) Prune(guildID discord.Snowflake, data PruneData) (uint, error) { func (c *Client) Prune(guildID discord.GuildID, data PruneData) (uint, error) {
if data.Days == 0 { if data.Days == 0 {
data.Days = 7 data.Days = 7
} }
@ -247,7 +247,7 @@ func (c *Client) Prune(guildID discord.Snowflake, data PruneData) (uint, error)
// //
// Requires KICK_MEMBERS permission. // Requires KICK_MEMBERS permission.
// Fires a Guild Member Remove Gateway event. // Fires a Guild Member Remove Gateway event.
func (c *Client) Kick(guildID, userID discord.Snowflake) error { func (c *Client) Kick(guildID discord.GuildID, userID discord.UserID) error {
return c.FastRequest( return c.FastRequest(
"DELETE", "DELETE",
EndpointGuilds+guildID.String()+"/members/"+userID.String(), EndpointGuilds+guildID.String()+"/members/"+userID.String(),
@ -257,7 +257,7 @@ func (c *Client) Kick(guildID, userID discord.Snowflake) error {
// Bans returns a list of ban objects for the users banned from this guild. // Bans returns a list of ban objects for the users banned from this guild.
// //
// Requires the BAN_MEMBERS permission. // Requires the BAN_MEMBERS permission.
func (c *Client) Bans(guildID discord.Snowflake) ([]discord.Ban, error) { func (c *Client) Bans(guildID discord.GuildID) ([]discord.Ban, error) {
var bans []discord.Ban var bans []discord.Ban
return bans, c.RequestJSON( return bans, c.RequestJSON(
&bans, "GET", &bans, "GET",
@ -268,7 +268,7 @@ func (c *Client) Bans(guildID discord.Snowflake) ([]discord.Ban, error) {
// GetBan returns a ban object for the given user. // GetBan returns a ban object for the given user.
// //
// Requires the BAN_MEMBERS permission. // Requires the BAN_MEMBERS permission.
func (c *Client) GetBan(guildID, userID discord.Snowflake) (*discord.Ban, error) { func (c *Client) GetBan(guildID discord.GuildID, userID discord.UserID) (*discord.Ban, error) {
var ban *discord.Ban var ban *discord.Ban
return ban, c.RequestJSON( return ban, c.RequestJSON(
&ban, "GET", &ban, "GET",
@ -288,7 +288,7 @@ type BanData struct {
// banned user. // banned user.
// //
// Requires the BAN_MEMBERS permission. // Requires the BAN_MEMBERS permission.
func (c *Client) Ban(guildID, userID discord.Snowflake, data BanData) error { func (c *Client) Ban(guildID discord.GuildID, userID discord.UserID, data BanData) error {
return c.FastRequest( return c.FastRequest(
"PUT", "PUT",
EndpointGuilds+guildID.String()+"/bans/"+userID.String(), EndpointGuilds+guildID.String()+"/bans/"+userID.String(),
@ -300,6 +300,6 @@ func (c *Client) Ban(guildID, userID discord.Snowflake, data BanData) error {
// //
// Requires the BAN_MEMBERS permissions. // Requires the BAN_MEMBERS permissions.
// Fires a Guild Ban Remove Gateway event. // Fires a Guild Ban Remove Gateway event.
func (c *Client) Unban(guildID, userID discord.Snowflake) error { func (c *Client) Unban(guildID discord.GuildID, userID discord.UserID) error {
return c.FastRequest("DELETE", EndpointGuilds+guildID.String()+"/bans/"+userID.String()) return c.FastRequest("DELETE", EndpointGuilds+guildID.String()+"/bans/"+userID.String())
} }

View File

@ -18,13 +18,13 @@ import (
// //
// When fetching the messages, those with the smallest ID will be fetched // When fetching the messages, those with the smallest ID will be fetched
// first. // first.
func (c *Client) Messages(channelID discord.Snowflake, limit uint) ([]discord.Message, error) { func (c *Client) Messages(channelID discord.ChannelID, limit uint) ([]discord.Message, error) {
return c.MessagesAfter(channelID, 0, limit) return c.MessagesAfter(channelID, 0, limit)
} }
// MessagesAround returns messages around the ID, with a limit of 100. // MessagesAround returns messages around the ID, with a limit of 100.
func (c *Client) MessagesAround( func (c *Client) MessagesAround(
channelID, around discord.Snowflake, limit uint) ([]discord.Message, error) { channelID discord.ChannelID, around discord.MessageID, limit uint) ([]discord.Message, error) {
return c.messagesRange(channelID, 0, 0, around, limit) return c.messagesRange(channelID, 0, 0, around, limit)
} }
@ -38,7 +38,7 @@ func (c *Client) MessagesAround(
// maximum a total of limit/100 rounded up requests will be made, although they // maximum a total of limit/100 rounded up requests will be made, although they
// may be less, if no more messages are available. // may be less, if no more messages are available.
func (c *Client) MessagesBefore( func (c *Client) MessagesBefore(
channelID, before discord.Snowflake, limit uint) ([]discord.Message, error) { channelID discord.ChannelID, before discord.MessageID, limit uint) ([]discord.Message, error) {
var msgs []discord.Message var msgs []discord.Message
@ -80,7 +80,7 @@ func (c *Client) MessagesBefore(
// maximum a total of limit/100 rounded up requests will be made, although they // maximum a total of limit/100 rounded up requests will be made, although they
// may be less, if no more messages are available. // may be less, if no more messages are available.
func (c *Client) MessagesAfter( func (c *Client) MessagesAfter(
channelID, after discord.Snowflake, limit uint) ([]discord.Message, error) { channelID discord.ChannelID, after discord.MessageID, limit uint) ([]discord.Message, error) {
var msgs []discord.Message var msgs []discord.Message
@ -114,7 +114,7 @@ func (c *Client) MessagesAfter(
} }
func (c *Client) messagesRange( func (c *Client) messagesRange(
channelID, before, after, around discord.Snowflake, limit uint) ([]discord.Message, error) { channelID discord.ChannelID, before, after, around discord.MessageID, limit uint) ([]discord.Message, error) {
switch { switch {
case limit == 0: case limit == 0:
@ -124,9 +124,9 @@ func (c *Client) messagesRange(
} }
var param struct { var param struct {
Before discord.Snowflake `schema:"before,omitempty"` Before discord.MessageID `schema:"before,omitempty"`
After discord.Snowflake `schema:"after,omitempty"` After discord.MessageID `schema:"after,omitempty"`
Around discord.Snowflake `schema:"around,omitempty"` Around discord.MessageID `schema:"around,omitempty"`
Limit uint `schema:"limit"` Limit uint `schema:"limit"`
} }
@ -148,7 +148,7 @@ func (c *Client) messagesRange(
// //
// If operating on a guild channel, this endpoint requires the // If operating on a guild channel, this endpoint requires the
// READ_MESSAGE_HISTORY permission to be present on the current user. // READ_MESSAGE_HISTORY permission to be present on the current user.
func (c *Client) Message(channelID, messageID discord.Snowflake) (*discord.Message, error) { func (c *Client) Message(channelID discord.ChannelID, messageID discord.MessageID) (*discord.Message, error) {
var msg *discord.Message var msg *discord.Message
return msg, c.RequestJSON(&msg, "GET", return msg, c.RequestJSON(&msg, "GET",
EndpointChannels+channelID.String()+"/messages/"+messageID.String()) EndpointChannels+channelID.String()+"/messages/"+messageID.String())
@ -160,7 +160,7 @@ func (c *Client) Message(channelID, messageID discord.Snowflake) (*discord.Messa
// permission to be present on the current user. // permission to be present on the current user.
// //
// Fires a Message Create Gateway event. // Fires a Message Create Gateway event.
func (c *Client) SendText(channelID discord.Snowflake, content string) (*discord.Message, error) { func (c *Client) SendText(channelID discord.ChannelID, content string) (*discord.Message, error) {
return c.SendMessageComplex(channelID, SendMessageData{ return c.SendMessageComplex(channelID, SendMessageData{
Content: content, Content: content,
}) })
@ -173,7 +173,7 @@ func (c *Client) SendText(channelID discord.Snowflake, content string) (*discord
// //
// Fires a Message Create Gateway event. // Fires a Message Create Gateway event.
func (c *Client) SendEmbed( func (c *Client) SendEmbed(
channelID discord.Snowflake, e discord.Embed) (*discord.Message, error) { channelID discord.ChannelID, e discord.Embed) (*discord.Message, error) {
return c.SendMessageComplex(channelID, SendMessageData{ return c.SendMessageComplex(channelID, SendMessageData{
Embed: &e, Embed: &e,
@ -187,7 +187,7 @@ func (c *Client) SendEmbed(
// //
// Fires a Message Create Gateway event. // Fires a Message Create Gateway event.
func (c *Client) SendMessage( func (c *Client) SendMessage(
channelID discord.Snowflake, content string, embed *discord.Embed) (*discord.Message, error) { channelID discord.ChannelID, content string, embed *discord.Embed) (*discord.Message, error) {
return c.SendMessageComplex(channelID, SendMessageData{ return c.SendMessageComplex(channelID, SendMessageData{
Content: content, Content: content,
@ -213,7 +213,7 @@ type EditMessageData struct {
// EditText edits the contents of a previously sent message. For more // EditText edits the contents of a previously sent message. For more
// documentation, refer to EditMessageComplex. // documentation, refer to EditMessageComplex.
func (c *Client) EditText( func (c *Client) EditText(
channelID, messageID discord.Snowflake, content string) (*discord.Message, error) { channelID discord.ChannelID, messageID discord.MessageID, content string) (*discord.Message, error) {
return c.EditMessageComplex(channelID, messageID, EditMessageData{ return c.EditMessageComplex(channelID, messageID, EditMessageData{
Content: option.NewNullableString(content), Content: option.NewNullableString(content),
@ -223,7 +223,7 @@ func (c *Client) EditText(
// EditEmbed edits the embed of a previously sent message. For more // EditEmbed edits the embed of a previously sent message. For more
// documentation, refer to EditMessageComplex. // documentation, refer to EditMessageComplex.
func (c *Client) EditEmbed( func (c *Client) EditEmbed(
channelID, messageID discord.Snowflake, embed discord.Embed) (*discord.Message, error) { channelID discord.ChannelID, messageID discord.MessageID, embed discord.Embed) (*discord.Message, error) {
return c.EditMessageComplex(channelID, messageID, EditMessageData{ return c.EditMessageComplex(channelID, messageID, EditMessageData{
Embed: &embed, Embed: &embed,
@ -233,7 +233,7 @@ func (c *Client) EditEmbed(
// EditMessage edits a previously sent message. For more documentation, refer to // EditMessage edits a previously sent message. For more documentation, refer to
// EditMessageComplex. // EditMessageComplex.
func (c *Client) EditMessage( func (c *Client) EditMessage(
channelID, messageID discord.Snowflake, content string, channelID discord.ChannelID, messageID discord.MessageID, content string,
embed *discord.Embed, suppressEmbeds bool) (*discord.Message, error) { embed *discord.Embed, suppressEmbeds bool) (*discord.Message, error) {
var data = EditMessageData{ var data = EditMessageData{
@ -258,7 +258,7 @@ func (c *Client) EditMessage(
// //
// Fires a Message Update Gateway event. // Fires a Message Update Gateway event.
func (c *Client) EditMessageComplex( func (c *Client) EditMessageComplex(
channelID, messageID discord.Snowflake, data EditMessageData) (*discord.Message, error) { channelID discord.ChannelID, messageID discord.MessageID, data EditMessageData) (*discord.Message, error) {
if data.AllowedMentions != nil { if data.AllowedMentions != nil {
if err := data.AllowedMentions.Verify(); err != nil { if err := data.AllowedMentions.Verify(); err != nil {
@ -283,7 +283,7 @@ func (c *Client) EditMessageComplex(
// DeleteMessage delete a message. If operating on a guild channel and trying // DeleteMessage delete a message. If operating on a guild channel and trying
// to delete a message that was not sent by the current user, this endpoint // to delete a message that was not sent by the current user, this endpoint
// requires the MANAGE_MESSAGES permission. // requires the MANAGE_MESSAGES permission.
func (c *Client) DeleteMessage(channelID, messageID discord.Snowflake) error { func (c *Client) DeleteMessage(channelID discord.ChannelID, messageID discord.MessageID) error {
return c.FastRequest("DELETE", EndpointChannels+channelID.String()+ return c.FastRequest("DELETE", EndpointChannels+channelID.String()+
"/messages/"+messageID.String()) "/messages/"+messageID.String())
} }
@ -297,9 +297,9 @@ func (c *Client) DeleteMessage(channelID, messageID discord.Snowflake) error {
// provided. // provided.
// //
// Fires a Message Delete Bulk Gateway event. // Fires a Message Delete Bulk Gateway event.
func (c *Client) DeleteMessages(channelID discord.Snowflake, messageIDs []discord.Snowflake) error { func (c *Client) DeleteMessages(channelID discord.ChannelID, messageIDs []discord.MessageID) error {
var param struct { var param struct {
Messages []discord.Snowflake `json:"messages"` Messages []discord.MessageID `json:"messages"`
} }
param.Messages = messageIDs param.Messages = messageIDs

View File

@ -13,7 +13,7 @@ import (
// the current user. Additionally, if nobody else has reacted to the message // the current user. Additionally, if nobody else has reacted to the message
// using this emoji, this endpoint requires the 'ADD_REACTIONS' permission to // using this emoji, this endpoint requires the 'ADD_REACTIONS' permission to
// be present on the current user. // be present on the current user.
func (c *Client) React(channelID, messageID discord.Snowflake, emoji Emoji) error { func (c *Client) React(channelID discord.ChannelID, messageID discord.MessageID, emoji Emoji) error {
var msgURL = EndpointChannels + channelID.String() + var msgURL = EndpointChannels + channelID.String() +
"/messages/" + messageID.String() + "/messages/" + messageID.String() +
"/reactions/" + url.PathEscape(emoji) + "/@me" "/reactions/" + url.PathEscape(emoji) + "/@me"
@ -21,7 +21,7 @@ func (c *Client) React(channelID, messageID discord.Snowflake, emoji Emoji) erro
} }
// Unreact removes a reaction the current user has made for the message. // Unreact removes a reaction the current user has made for the message.
func (c *Client) Unreact(chID, msgID discord.Snowflake, emoji Emoji) error { func (c *Client) Unreact(chID discord.ChannelID, msgID discord.MessageID, emoji Emoji) error {
return c.DeleteUserReaction(chID, msgID, 0, emoji) return c.DeleteUserReaction(chID, msgID, 0, emoji)
} }
@ -35,7 +35,7 @@ func (c *Client) Unreact(chID, msgID discord.Snowflake, emoji Emoji) error {
// //
// When fetching the users, those with the smallest ID will be fetched first. // When fetching the users, those with the smallest ID will be fetched first.
func (c *Client) Reactions( func (c *Client) Reactions(
channelID, messageID discord.Snowflake, emoji Emoji, limit uint) ([]discord.User, error) { channelID discord.ChannelID, messageID discord.MessageID, emoji Emoji, limit uint) ([]discord.User, error) {
return c.ReactionsAfter(channelID, messageID, 0, emoji, limit) return c.ReactionsAfter(channelID, messageID, 0, emoji, limit)
} }
@ -48,7 +48,7 @@ func (c *Client) Reactions(
// maximum a total of limit/100 rounded up requests will be made, although they // maximum a total of limit/100 rounded up requests will be made, although they
// may be less, if no more guilds are available. // may be less, if no more guilds are available.
func (c *Client) ReactionsBefore( func (c *Client) ReactionsBefore(
channelID, messageID, before discord.Snowflake, emoji Emoji, channelID discord.ChannelID, messageID discord.MessageID, before discord.UserID, emoji Emoji,
limit uint) ([]discord.User, error) { limit uint) ([]discord.User, error) {
var users []discord.User var users []discord.User
@ -89,7 +89,7 @@ func (c *Client) ReactionsBefore(
// maximum a total of limit/100 rounded up requests will be made, although they // maximum a total of limit/100 rounded up requests will be made, although they
// may be less, if no more guilds are available. // may be less, if no more guilds are available.
func (c *Client) ReactionsAfter( func (c *Client) ReactionsAfter(
channelID, messageID, after discord.Snowflake, emoji Emoji, channelID discord.ChannelID, messageID discord.MessageID, after discord.UserID, emoji Emoji,
limit uint) ([]discord.User, error) { limit uint) ([]discord.User, error) {
var users []discord.User var users []discord.User
@ -125,7 +125,7 @@ func (c *Client) ReactionsAfter(
// reactionsRange get users before and after IDs. Before, after, and limit are // reactionsRange get users before and after IDs. Before, after, and limit are
// optional. A maximum limit of only 100 reactions could be returned. // optional. A maximum limit of only 100 reactions could be returned.
func (c *Client) reactionsRange( func (c *Client) reactionsRange(
channelID, messageID, before, after discord.Snowflake, emoji Emoji, channelID discord.ChannelID, messageID discord.MessageID, before, after discord.UserID, emoji Emoji,
limit uint) ([]discord.User, error) { limit uint) ([]discord.User, error) {
switch { switch {
@ -136,8 +136,8 @@ func (c *Client) reactionsRange(
} }
var param struct { var param struct {
Before discord.Snowflake `schema:"before,omitempty"` Before discord.UserID `schema:"before,omitempty"`
After discord.Snowflake `schema:"after,omitempty"` After discord.UserID `schema:"after,omitempty"`
Limit uint `schema:"limit"` Limit uint `schema:"limit"`
} }
@ -160,7 +160,7 @@ func (c *Client) reactionsRange(
// This endpoint requires the MANAGE_MESSAGES permission to be present on the // This endpoint requires the MANAGE_MESSAGES permission to be present on the
// current user. // current user.
func (c *Client) DeleteUserReaction( func (c *Client) DeleteUserReaction(
channelID, messageID, userID discord.Snowflake, emoji Emoji) error { channelID discord.ChannelID, messageID discord.MessageID, userID discord.UserID, emoji Emoji) error {
var user = "@me" var user = "@me"
if userID > 0 { if userID > 0 {
@ -180,7 +180,7 @@ func (c *Client) DeleteUserReaction(
// current user. // current user.
// Fires a Message Reaction Remove Emoji Gateway event. // Fires a Message Reaction Remove Emoji Gateway event.
func (c *Client) DeleteReactions( func (c *Client) DeleteReactions(
channelID, messageID discord.Snowflake, emoji Emoji) error { channelID discord.ChannelID, messageID discord.MessageID, emoji Emoji) error {
return c.FastRequest( return c.FastRequest(
"DELETE", "DELETE",
@ -194,7 +194,7 @@ func (c *Client) DeleteReactions(
// This endpoint requires the MANAGE_MESSAGES permission to be present on the // This endpoint requires the MANAGE_MESSAGES permission to be present on the
// current user. // current user.
// Fires a Message Reaction Remove All Gateway event. // Fires a Message Reaction Remove All Gateway event.
func (c *Client) DeleteAllReactions(channelID, messageID discord.Snowflake) error { func (c *Client) DeleteAllReactions(channelID discord.ChannelID, messageID discord.MessageID) error {
return c.FastRequest( return c.FastRequest(
"DELETE", "DELETE",
EndpointChannels+channelID.String()+"/messages/"+messageID.String()+"/reactions/", EndpointChannels+channelID.String()+"/messages/"+messageID.String()+"/reactions/",

View File

@ -9,7 +9,7 @@ import (
// Adds a role to a guild member. // Adds a role to a guild member.
// //
// Requires the MANAGE_ROLES permission. // Requires the MANAGE_ROLES permission.
func (c *Client) AddRole(guildID, userID, roleID discord.Snowflake) error { func (c *Client) AddRole(guildID discord.GuildID, userID discord.UserID, roleID discord.RoleID) error {
return c.FastRequest( return c.FastRequest(
"PUT", "PUT",
EndpointGuilds+guildID.String()+"/members/"+userID.String()+"/roles/"+roleID.String(), EndpointGuilds+guildID.String()+"/members/"+userID.String()+"/roles/"+roleID.String(),
@ -20,7 +20,7 @@ func (c *Client) AddRole(guildID, userID, roleID discord.Snowflake) error {
// //
// Requires the MANAGE_ROLES permission. // Requires the MANAGE_ROLES permission.
// Fires a Guild Member Update Gateway event. // Fires a Guild Member Update Gateway event.
func (c *Client) RemoveRole(guildID, userID, roleID discord.Snowflake) error { func (c *Client) RemoveRole(guildID discord.GuildID, userID discord.UserID, roleID discord.RoleID) error {
return c.FastRequest( return c.FastRequest(
"DELETE", "DELETE",
EndpointGuilds+guildID.String()+"/members/"+userID.String()+"/roles/"+roleID.String(), EndpointGuilds+guildID.String()+"/members/"+userID.String()+"/roles/"+roleID.String(),
@ -28,7 +28,7 @@ func (c *Client) RemoveRole(guildID, userID, roleID discord.Snowflake) error {
} }
// Roles returns a list of role objects for the guild. // Roles returns a list of role objects for the guild.
func (c *Client) Roles(guildID discord.Snowflake) ([]discord.Role, error) { func (c *Client) Roles(guildID discord.GuildID) ([]discord.Role, error) {
var roles []discord.Role var roles []discord.Role
return roles, c.RequestJSON(&roles, "GET", EndpointGuilds+guildID.String()+"/roles") return roles, c.RequestJSON(&roles, "GET", EndpointGuilds+guildID.String()+"/roles")
} }
@ -62,8 +62,7 @@ type CreateRoleData struct {
// //
// Requires the MANAGE_ROLES permission. // Requires the MANAGE_ROLES permission.
// Fires a Guild Role Create Gateway event. // Fires a Guild Role Create Gateway event.
func (c *Client) CreateRole( func (c *Client) CreateRole(guildID discord.GuildID, data CreateRoleData) (*discord.Role, error) {
guildID discord.Snowflake, data CreateRoleData) (*discord.Role, error) {
var role *discord.Role var role *discord.Role
return role, c.RequestJSON( return role, c.RequestJSON(
@ -76,7 +75,7 @@ func (c *Client) CreateRole(
// https://discord.com/developers/docs/resources/guild#modify-guild-role-positions-json-params // https://discord.com/developers/docs/resources/guild#modify-guild-role-positions-json-params
type MoveRoleData struct { type MoveRoleData struct {
// ID is the id of the role. // ID is the id of the role.
ID discord.Snowflake `json:"id"` ID discord.RoleID `json:"id"`
// Position is the sorting position of the role. // Position is the sorting position of the role.
Position option.NullableInt `json:"position,omitempty"` Position option.NullableInt `json:"position,omitempty"`
} }
@ -85,7 +84,7 @@ type MoveRoleData struct {
// //
// Requires the MANAGE_ROLES permission. // Requires the MANAGE_ROLES permission.
// Fires multiple Guild Role Update Gateway events. // Fires multiple Guild Role Update Gateway events.
func (c *Client) MoveRole(guildID discord.Snowflake, data []MoveRoleData) ([]discord.Role, error) { func (c *Client) MoveRole(guildID discord.GuildID, data []MoveRoleData) ([]discord.Role, error) {
var roles []discord.Role var roles []discord.Role
return roles, c.RequestJSON( return roles, c.RequestJSON(
&roles, "PATCH", &roles, "PATCH",
@ -113,7 +112,7 @@ type ModifyRoleData struct {
// //
// Requires the MANAGE_ROLES permission. // Requires the MANAGE_ROLES permission.
func (c *Client) ModifyRole( func (c *Client) ModifyRole(
guildID, roleID discord.Snowflake, guildID discord.GuildID, roleID discord.RoleID,
data ModifyRoleData) (*discord.Role, error) { data ModifyRoleData) (*discord.Role, error) {
var role *discord.Role var role *discord.Role
@ -127,7 +126,7 @@ func (c *Client) ModifyRole(
// DeleteRole deletes a guild role. // DeleteRole deletes a guild role.
// //
// Requires the MANAGE_ROLES permission. // Requires the MANAGE_ROLES permission.
func (c *Client) DeleteRole(guildID, roleID discord.Snowflake) error { func (c *Client) DeleteRole(guildID discord.GuildID, roleID discord.RoleID) error {
return c.FastRequest( return c.FastRequest(
"DELETE", "DELETE",
EndpointGuilds+guildID.String()+"/roles/"+roleID.String(), EndpointGuilds+guildID.String()+"/roles/"+roleID.String(),

View File

@ -41,9 +41,9 @@ type AllowedMentions struct {
// Parse is an array of allowed mention types to parse from the content. // Parse is an array of allowed mention types to parse from the content.
Parse []AllowedMentionType `json:"parse"` Parse []AllowedMentionType `json:"parse"`
// Roles is an array of role_ids to mention (Max size of 100). // Roles is an array of role_ids to mention (Max size of 100).
Roles []discord.Snowflake `json:"roles,omitempty"` Roles []discord.RoleID `json:"roles,omitempty"`
// Users is an array of user_ids to mention (Max size of 100). // Users is an array of user_ids to mention (Max size of 100).
Users []discord.Snowflake `json:"users,omitempty"` Users []discord.UserID `json:"users,omitempty"`
} }
// AllowedMentionType is a constant that tells Discord what is allowed to parse // AllowedMentionType is a constant that tells Discord what is allowed to parse
@ -138,7 +138,7 @@ func (data *SendMessageData) WriteMultipart(body *multipart.Writer) error {
// least one of content, embed or file. For a file attachment, the // least one of content, embed or file. For a file attachment, the
// Content-Disposition subpart header MUST contain a filename parameter. // Content-Disposition subpart header MUST contain a filename parameter.
func (c *Client) SendMessageComplex( func (c *Client) SendMessageComplex(
channelID discord.Snowflake, data SendMessageData) (*discord.Message, error) { channelID discord.ChannelID, data SendMessageData) (*discord.Message, error) {
if data.Content == "" && data.Embed == nil && len(data.Files) == 0 { if data.Content == "" && data.Embed == nil && len(data.Files) == 0 {
return nil, ErrEmptyMessage return nil, ErrEmptyMessage
@ -211,7 +211,7 @@ func (data *ExecuteWebhookData) WriteMultipart(body *multipart.Writer) error {
// wait for the message to be delivered and will return the message body. This // wait for the message to be delivered and will return the message body. This
// also means the returned message will only be there if wait is true. // also means the returned message will only be there if wait is true.
func (c *Client) ExecuteWebhook( func (c *Client) ExecuteWebhook(
webhookID discord.Snowflake, webhookID discord.WebhookID,
token string, token string,
wait bool, // if false, then nil returned for *Message. wait bool, // if false, then nil returned for *Message.
data ExecuteWebhookData) (*discord.Message, error) { data ExecuteWebhookData) (*discord.Message, error) {

View File

@ -34,7 +34,7 @@ func TestMarshalAllowedMentions(t *testing.T) {
t.Run("allow certain user IDs", func(t *testing.T) { t.Run("allow certain user IDs", func(t *testing.T) {
var data = SendMessageData{ var data = SendMessageData{
AllowedMentions: &AllowedMentions{ AllowedMentions: &AllowedMentions{
Users: []discord.Snowflake{1, 2}, Users: []discord.UserID{1, 2},
}, },
} }
@ -48,7 +48,7 @@ func TestVerifyAllowedMentions(t *testing.T) {
t.Run("invalid", func(t *testing.T) { t.Run("invalid", func(t *testing.T) {
var am = AllowedMentions{ var am = AllowedMentions{
Parse: []AllowedMentionType{AllowEveryoneMention, AllowUserMention}, Parse: []AllowedMentionType{AllowEveryoneMention, AllowUserMention},
Users: []discord.Snowflake{69, 420}, Users: []discord.UserID{69, 420},
} }
err := am.Verify() err := am.Verify()
@ -57,7 +57,7 @@ func TestVerifyAllowedMentions(t *testing.T) {
t.Run("users too long", func(t *testing.T) { t.Run("users too long", func(t *testing.T) {
var am = AllowedMentions{ var am = AllowedMentions{
Users: make([]discord.Snowflake, 101), Users: make([]discord.UserID, 101),
} }
err := am.Verify() err := am.Verify()
@ -66,7 +66,7 @@ func TestVerifyAllowedMentions(t *testing.T) {
t.Run("roles too long", func(t *testing.T) { t.Run("roles too long", func(t *testing.T) {
var am = AllowedMentions{ var am = AllowedMentions{
Roles: make([]discord.Snowflake, 101), Roles: make([]discord.RoleID, 101),
} }
err := am.Verify() err := am.Verify()
@ -76,8 +76,8 @@ func TestVerifyAllowedMentions(t *testing.T) {
t.Run("valid", func(t *testing.T) { t.Run("valid", func(t *testing.T) {
var am = AllowedMentions{ var am = AllowedMentions{
Parse: []AllowedMentionType{AllowEveryoneMention, AllowUserMention}, Parse: []AllowedMentionType{AllowEveryoneMention, AllowUserMention},
Roles: []discord.Snowflake{1337}, Roles: []discord.RoleID{1337},
Users: []discord.Snowflake{}, Users: []discord.UserID{},
} }
if err := am.Verify(); err != nil { if err := am.Verify(); err != nil {
@ -125,7 +125,7 @@ func TestSendMessage(t *testing.T) {
Content: "hime arikawa", Content: "hime arikawa",
AllowedMentions: &AllowedMentions{ AllowedMentions: &AllowedMentions{
Parse: []AllowedMentionType{AllowEveryoneMention, AllowUserMention}, Parse: []AllowedMentionType{AllowEveryoneMention, AllowUserMention},
Users: []discord.Snowflake{69, 420}, Users: []discord.UserID{69, 420},
}, },
} }

View File

@ -12,7 +12,7 @@ var (
) )
// User returns a user object for a given user ID. // User returns a user object for a given user ID.
func (c *Client) User(userID discord.Snowflake) (*discord.User, error) { func (c *Client) User(userID discord.UserID) (*discord.User, error) {
var u *discord.User var u *discord.User
return u, c.RequestJSON(&u, "GET", EndpointUsers+userID.String()) return u, c.RequestJSON(&u, "GET", EndpointUsers+userID.String())
} }
@ -44,7 +44,7 @@ func (c *Client) ModifyMe(data ModifySelfData) (*discord.User, error) {
// //
// Fires a Guild Member Update Gateway event. // Fires a Guild Member Update Gateway event.
func (c *Client) ChangeOwnNickname( func (c *Client) ChangeOwnNickname(
guildID discord.Snowflake, nick string) error { guildID discord.GuildID, nick string) error {
var param struct { var param struct {
Nick string `json:"nick"` Nick string `json:"nick"`
@ -68,9 +68,9 @@ func (c *Client) PrivateChannels() ([]discord.Channel, error) {
} }
// CreatePrivateChannel creates a new DM channel with a user. // CreatePrivateChannel creates a new DM channel with a user.
func (c *Client) CreatePrivateChannel(recipientID discord.Snowflake) (*discord.Channel, error) { func (c *Client) CreatePrivateChannel(recipientID discord.UserID) (*discord.Channel, error) {
var param struct { var param struct {
RecipientID discord.Snowflake `json:"recipient_id"` RecipientID discord.UserID `json:"recipient_id"`
} }
param.RecipientID = recipientID param.RecipientID = recipientID
@ -88,7 +88,7 @@ func (c *Client) UserConnections() ([]discord.Connection, error) {
// SetNote sets a note for the user. This endpoint is undocumented and might // SetNote sets a note for the user. This endpoint is undocumented and might
// only work for user accounts. // only work for user accounts.
func (c *Client) SetNote(userID discord.Snowflake, note string) error { func (c *Client) SetNote(userID discord.UserID, note string) error {
var body = struct { var body = struct {
Note string `json:"note"` Note string `json:"note"`
}{ }{
@ -103,7 +103,7 @@ func (c *Client) SetNote(userID discord.Snowflake, note string) error {
// SetRelationship sets the relationship type between the current user and the // SetRelationship sets the relationship type between the current user and the
// given user. // given user.
func (c *Client) SetRelationship(userID discord.Snowflake, t discord.RelationshipType) error { func (c *Client) SetRelationship(userID discord.UserID, t discord.RelationshipType) error {
var body = struct { var body = struct {
Type discord.RelationshipType `json:"type"` Type discord.RelationshipType `json:"type"`
}{ }{
@ -118,6 +118,6 @@ func (c *Client) SetRelationship(userID discord.Snowflake, t discord.Relationshi
// DeleteRelationship deletes the relationship between the current user and the // DeleteRelationship deletes the relationship between the current user and the
// given user. // given user.
func (c *Client) DeleteRelationship(userID discord.Snowflake) error { func (c *Client) DeleteRelationship(userID discord.UserID) error {
return c.FastRequest("DELETE", EndpointMe+"/relationships/"+userID.String()) return c.FastRequest("DELETE", EndpointMe+"/relationships/"+userID.String())
} }

View File

@ -22,7 +22,7 @@ type CreateWebhookData struct {
// //
// Requires the MANAGE_WEBHOOKS permission. // Requires the MANAGE_WEBHOOKS permission.
func (c *Client) CreateWebhook( func (c *Client) CreateWebhook(
channelID discord.Snowflake, data CreateWebhookData) (*discord.Webhook, error) { channelID discord.ChannelID, data CreateWebhookData) (*discord.Webhook, error) {
var w *discord.Webhook var w *discord.Webhook
return w, c.RequestJSON( return w, c.RequestJSON(
@ -35,7 +35,7 @@ func (c *Client) CreateWebhook(
// ChannelWebhooks returns the webhooks of the channel with the given ID. // ChannelWebhooks returns the webhooks of the channel with the given ID.
// //
// Requires the MANAGE_WEBHOOKS permission. // Requires the MANAGE_WEBHOOKS permission.
func (c *Client) ChannelWebhooks(channelID discord.Snowflake) ([]discord.Webhook, error) { func (c *Client) ChannelWebhooks(channelID discord.ChannelID) ([]discord.Webhook, error) {
var ws []discord.Webhook var ws []discord.Webhook
return ws, c.RequestJSON(&ws, "GET", EndpointChannels+channelID.String()+"/webhooks") return ws, c.RequestJSON(&ws, "GET", EndpointChannels+channelID.String()+"/webhooks")
} }
@ -43,13 +43,13 @@ func (c *Client) ChannelWebhooks(channelID discord.Snowflake) ([]discord.Webhook
// GuildWebhooks returns the webhooks of the guild with the given ID. // GuildWebhooks returns the webhooks of the guild with the given ID.
// //
// Requires the MANAGE_WEBHOOKS permission. // Requires the MANAGE_WEBHOOKS permission.
func (c *Client) GuildWebhooks(guildID discord.Snowflake) ([]discord.Webhook, error) { func (c *Client) GuildWebhooks(guildID discord.GuildID) ([]discord.Webhook, error) {
var ws []discord.Webhook var ws []discord.Webhook
return ws, c.RequestJSON(&ws, "GET", EndpointGuilds+guildID.String()+"/webhooks") return ws, c.RequestJSON(&ws, "GET", EndpointGuilds+guildID.String()+"/webhooks")
} }
// Webhook returns the webhook with the given id. // Webhook returns the webhook with the given id.
func (c *Client) Webhook(webhookID discord.Snowflake) (*discord.Webhook, error) { func (c *Client) Webhook(webhookID discord.WebhookID) (*discord.Webhook, error) {
var w *discord.Webhook var w *discord.Webhook
return w, c.RequestJSON(&w, "GET", EndpointWebhooks+webhookID.String()) return w, c.RequestJSON(&w, "GET", EndpointWebhooks+webhookID.String())
} }
@ -57,7 +57,7 @@ func (c *Client) Webhook(webhookID discord.Snowflake) (*discord.Webhook, error)
// WebhookWithToken is the same as above, except this call does not require // WebhookWithToken is the same as above, except this call does not require
// authentication and returns no user in the webhook object. // authentication and returns no user in the webhook object.
func (c *Client) WebhookWithToken( func (c *Client) WebhookWithToken(
webhookID discord.Snowflake, token string) (*discord.Webhook, error) { webhookID discord.WebhookID, token string) (*discord.Webhook, error) {
var w *discord.Webhook var w *discord.Webhook
return w, c.RequestJSON(&w, "GET", EndpointWebhooks+webhookID.String()+"/"+token) return w, c.RequestJSON(&w, "GET", EndpointWebhooks+webhookID.String()+"/"+token)
@ -70,14 +70,14 @@ type ModifyWebhookData struct {
// Avatar is the image for the default webhook avatar. // Avatar is the image for the default webhook avatar.
Avatar *Image `json:"avatar,omitempty"` Avatar *Image `json:"avatar,omitempty"`
// ChannelID is the new channel id this webhook should be moved to. // ChannelID is the new channel id this webhook should be moved to.
ChannelID discord.Snowflake `json:"channel_id,omitempty"` ChannelID discord.ChannelID `json:"channel_id,omitempty"`
} }
// ModifyWebhook modifies a webhook. // ModifyWebhook modifies a webhook.
// //
// Requires the MANAGE_WEBHOOKS permission. // Requires the MANAGE_WEBHOOKS permission.
func (c *Client) ModifyWebhook( func (c *Client) ModifyWebhook(
webhookID discord.Snowflake, data ModifyWebhookData) (*discord.Webhook, error) { webhookID discord.WebhookID, data ModifyWebhookData) (*discord.Webhook, error) {
var w *discord.Webhook var w *discord.Webhook
return w, c.RequestJSON( return w, c.RequestJSON(
@ -91,7 +91,7 @@ func (c *Client) ModifyWebhook(
// require authentication, does not accept a channel_id parameter in the body, // require authentication, does not accept a channel_id parameter in the body,
// and does not return a user in the webhook object. // and does not return a user in the webhook object.
func (c *Client) ModifyWebhookWithToken( func (c *Client) ModifyWebhookWithToken(
webhookID discord.Snowflake, token string, data ModifyWebhookData) (*discord.Webhook, error) { webhookID discord.WebhookID, token string, data ModifyWebhookData) (*discord.Webhook, error) {
var w *discord.Webhook var w *discord.Webhook
return w, c.RequestJSON( return w, c.RequestJSON(
@ -104,12 +104,12 @@ func (c *Client) ModifyWebhookWithToken(
// DeleteWebhook deletes a webhook permanently. // DeleteWebhook deletes a webhook permanently.
// //
// Requires the MANAGE_WEBHOOKS permission. // Requires the MANAGE_WEBHOOKS permission.
func (c *Client) DeleteWebhook(webhookID discord.Snowflake) error { func (c *Client) DeleteWebhook(webhookID discord.WebhookID) error {
return c.FastRequest("DELETE", EndpointWebhooks+webhookID.String()) return c.FastRequest("DELETE", EndpointWebhooks+webhookID.String())
} }
// DeleteWebhookWithToken is the same as above, except this call does not // DeleteWebhookWithToken is the same as above, except this call does not
// require authentication. // require authentication.
func (c *Client) DeleteWebhookWithToken(webhookID discord.Snowflake, token string) error { func (c *Client) DeleteWebhookWithToken(webhookID discord.WebhookID, token string) error {
return c.FastRequest("DELETE", EndpointWebhooks+webhookID.String()+"/"+token) return c.FastRequest("DELETE", EndpointWebhooks+webhookID.String()+"/"+token)
} }

View File

@ -15,7 +15,7 @@ var (
) )
type Emoji struct { type Emoji struct {
ID discord.Snowflake ID discord.EmojiID
Name string Name string
Custom bool Custom bool
@ -83,7 +83,7 @@ func (e *Emoji) Parse(arg string) error {
e.Custom = true e.Custom = true
e.Animated = matches[1] == "a" e.Animated = matches[1] == "a"
e.Name = matches[2] e.Name = matches[2]
e.ID = id e.ID = discord.EmojiID(id)
return nil return nil
} }

View File

@ -17,9 +17,9 @@ var Regex = regexp.MustCompile(
// MessageURL contains info from a MessageURL // MessageURL contains info from a MessageURL
type MessageURL struct { type MessageURL struct {
GuildID discord.Snowflake GuildID discord.GuildID
ChannelID discord.Snowflake ChannelID discord.ChannelID
MessageID discord.Snowflake MessageID discord.MessageID
} }
func (url *MessageURL) Parse(arg string) error { func (url *MessageURL) Parse(arg string) error {
@ -55,8 +55,8 @@ func ParseMessageURL(url string) *MessageURL {
} }
return &MessageURL{ return &MessageURL{
GuildID: gID, GuildID: discord.GuildID(gID),
ChannelID: cID, ChannelID: discord.ChannelID(cID),
MessageID: mID, MessageID: discord.MessageID(mID),
} }
} }

View File

@ -15,7 +15,7 @@ var (
// //
type ChannelMention discord.Snowflake type ChannelMention discord.ChannelID
func (m *ChannelMention) Parse(arg string) error { func (m *ChannelMention) Parse(arg string) error {
return grabFirst(ChannelRegex, "channel mention", arg, (*discord.Snowflake)(m)) return grabFirst(ChannelRegex, "channel mention", arg, (*discord.Snowflake)(m))
@ -35,7 +35,7 @@ func (m *ChannelMention) Mention() string {
// //
type UserMention discord.Snowflake type UserMention discord.UserID
func (m *UserMention) Parse(arg string) error { func (m *UserMention) Parse(arg string) error {
return grabFirst(UserRegex, "user mention", arg, (*discord.Snowflake)(m)) return grabFirst(UserRegex, "user mention", arg, (*discord.Snowflake)(m))
@ -55,7 +55,7 @@ func (m *UserMention) Mention() string {
// //
type RoleMention discord.Snowflake type RoleMention discord.RoleID
func (m *RoleMention) Parse(arg string) error { func (m *RoleMention) Parse(arg string) error {
return grabFirst(RoleRegex, "role mention", arg, (*discord.Snowflake)(m)) return grabFirst(RoleRegex, "role mention", arg, (*discord.Snowflake)(m))

View File

@ -13,21 +13,21 @@ import (
// ChannelID looks for fields with name ChannelID, Channel, or in some special // ChannelID looks for fields with name ChannelID, Channel, or in some special
// cases, ID. // cases, ID.
func ChannelID(event interface{}) discord.Snowflake { func ChannelID(event interface{}) discord.ChannelID {
return reflectID(reflect.ValueOf(event), "Channel") return discord.ChannelID(reflectID(reflect.ValueOf(event), "Channel"))
} }
// GuildID looks for fields with name GuildID, Guild, or in some special cases, // GuildID looks for fields with name GuildID, Guild, or in some special cases,
// ID. // ID.
func GuildID(event interface{}) discord.Snowflake { func GuildID(event interface{}) discord.GuildID {
return reflectID(reflect.ValueOf(event), "Guild") return discord.GuildID(reflectID(reflect.ValueOf(event), "Guild"))
} }
// UserID looks for fields with name UserID, User, or in some special cases, ID. // UserID looks for fields with name UserID, User, or in some special cases, ID.
func UserID(event interface{}) discord.Snowflake { func UserID(event interface{}) discord.UserID {
// This may have a very fatal bug of accidentally mistaking another User's // This may have a very fatal bug of accidentally mistaking another User's
// ID. It also probably wouldn't work with things like RecipientID. // ID. It also probably wouldn't work with things like RecipientID.
return reflectID(reflect.ValueOf(event), "User") return discord.UserID(reflectID(reflect.ValueOf(event), "User"))
} }
func reflectID(v reflect.Value, thing string) discord.Snowflake { func reflectID(v reflect.Value, thing string) discord.Snowflake {

View File

@ -7,7 +7,7 @@ import (
) )
type hasID struct { type hasID struct {
ChannelID discord.Snowflake ChannelID discord.ChannelID
} }
type embedsID struct { type embedsID struct {
@ -16,7 +16,7 @@ type embedsID struct {
} }
type hasChannelInName struct { type hasChannelInName struct {
ID discord.Snowflake ID discord.ChannelID
} }
func TestReflectChannelID(t *testing.T) { func TestReflectChannelID(t *testing.T) {

View File

@ -162,7 +162,7 @@ type mockStore struct {
state.NoopStore state.NoopStore
} }
func (s *mockStore) Guild(id discord.Snowflake) (*discord.Guild, error) { func (s *mockStore) Guild(id discord.GuildID) (*discord.Guild, error) {
return &discord.Guild{ return &discord.Guild{
ID: id, ID: id,
Roles: []discord.Role{{ Roles: []discord.Role{{
@ -172,23 +172,23 @@ func (s *mockStore) Guild(id discord.Snowflake) (*discord.Guild, error) {
}, nil }, nil
} }
func (s *mockStore) Member(g, m discord.Snowflake) (*discord.Member, error) { func (s *mockStore) Member(guildID discord.GuildID, userID discord.UserID) (*discord.Member, error) {
return &discord.Member{ return &discord.Member{
User: discord.User{ID: m}, User: discord.User{ID: userID},
RoleIDs: []discord.Snowflake{m}, RoleIDs: []discord.RoleID{discord.RoleID(userID)},
}, nil }, nil
} }
// Channel returns a channel with a guildID for #69420. // Channel returns a channel with a guildID for #69420.
func (s *mockStore) Channel(chID discord.Snowflake) (*discord.Channel, error) { func (s *mockStore) Channel(id discord.ChannelID) (*discord.Channel, error) {
if chID == 69420 { if id == 69420 {
return &discord.Channel{ return &discord.Channel{
ID: chID, ID: id,
GuildID: 1337, GuildID: 1337,
}, nil }, nil
} }
return &discord.Channel{ return &discord.Channel{
ID: chID, ID: id,
}, nil }, nil
} }

View File

@ -24,13 +24,13 @@ type AuditLog struct {
// https://discord.com/developers/docs/resources/audit-log#audit-log-entry-object // https://discord.com/developers/docs/resources/audit-log#audit-log-entry-object
type AuditLogEntry struct { type AuditLogEntry struct {
// ID is the id of the entry. // ID is the id of the entry.
ID Snowflake `json:"id"` ID AuditLogEntryID `json:"id"`
// TargetID is the id of the affected entity (webhook, user, role, etc.). // TargetID is the id of the affected entity (webhook, user, role, etc.).
TargetID string `json:"target_id,omitempty"` TargetID string `json:"target_id,omitempty"`
// Changes are the changes made to the TargetID. // Changes are the changes made to the TargetID.
Changes []AuditLogChange `json:"changes,omitempty"` Changes []AuditLogChange `json:"changes,omitempty"`
// UserID is the id of the user who made the changes. // UserID is the id of the user who made the changes.
UserID Snowflake `json:"user_id"` UserID UserID `json:"user_id"`
// ActionType is the type of action that occurred. // ActionType is the type of action that occurred.
ActionType AuditLogEvent `json:"action_type"` ActionType AuditLogEvent `json:"action_type"`
@ -97,11 +97,11 @@ type AuditEntryInfo struct {
// ChannelID is the id of the channel in which the entities were targeted. // ChannelID is the id of the channel in which the entities were targeted.
// //
// Events: MEMBER_MOVE, MESSAGE_PIN, MESSAGE_UNPIN, MESSAGE_DELETE // Events: MEMBER_MOVE, MESSAGE_PIN, MESSAGE_UNPIN, MESSAGE_DELETE
ChannelID Snowflake `json:"channel_id,omitempty"` ChannelID ChannelID `json:"channel_id,omitempty"`
// MessagesID is the id of the message that was targeted. // MessagesID is the id of the message that was targeted.
// //
// Events: MESSAGE_PIN, MESSAGE_UNPIN // Events: MESSAGE_PIN, MESSAGE_UNPIN
MessageID Snowflake `json:"message_id,omitempty"` MessageID MessageID `json:"message_id,omitempty"`
// Count is the number of entities that were targeted. // Count is the number of entities that were targeted.
// //
// Events: MESSAGE_DELETE, MESSAGE_BULK_DELETE, MEMBER_DISCONNECT, // Events: MESSAGE_DELETE, MESSAGE_BULK_DELETE, MEMBER_DISCONNECT,
@ -151,8 +151,8 @@ const (
// return errors.New("not owner ID") // return errors.New("not owner ID")
// } // }
// //
// // We know these are snowflakes because the comment said so for AuditGuildOwnerID. // // We know these are UserIDs because the comment said so for AuditGuildOwnerID.
// var oldOwnerID, newOwnerID discord.Snowflake // var oldOwnerID, newOwnerID discord.UserID
// if err := change.UnmarshalValues(&oldOwnerID, &newOwnerID); err != nil { // if err := change.UnmarshalValues(&oldOwnerID, &newOwnerID); err != nil {
// return err // return err
// } // }
@ -199,7 +199,7 @@ const (
AuditGuildSplashHash AuditLogChangeKey = "splash_hash" AuditGuildSplashHash AuditLogChangeKey = "splash_hash"
// AuditGuildOwnerID gets sent if the guild's owner changed. // AuditGuildOwnerID gets sent if the guild's owner changed.
// //
// Type: Snowflake // Type: UserID
AuditGuildOwnerID AuditLogChangeKey = "owner_id" AuditGuildOwnerID AuditLogChangeKey = "owner_id"
// AuditGuildRegion gets sent if the guild's region changed. // AuditGuildRegion gets sent if the guild's region changed.
// //
@ -207,7 +207,7 @@ const (
AuditGuildRegion AuditLogChangeKey = "region" AuditGuildRegion AuditLogChangeKey = "region"
// AuditGuildAFKChannelID gets sent if the guild's afk channel changed. // AuditGuildAFKChannelID gets sent if the guild's afk channel changed.
// //
// Type: Snowflake // Type: ChannelID
AuditGuildAFKChannelID AuditLogChangeKey = "afk_channel_id" AuditGuildAFKChannelID AuditLogChangeKey = "afk_channel_id"
// AuditGuildAFKTimeout gets sent if the guild's afk timeout duration // AuditGuildAFKTimeout gets sent if the guild's afk timeout duration
// changed. // changed.
@ -259,12 +259,12 @@ const (
// AuditGuildWidgetChannelID gets sent if the channel ID of the guild // AuditGuildWidgetChannelID gets sent if the channel ID of the guild
// widget changed. // widget changed.
// //
// Type: Snowflake // Type: ChannelID
AuditGuildWidgetChannelID AuditLogChangeKey = "widget_channel_id" AuditGuildWidgetChannelID AuditLogChangeKey = "widget_channel_id"
// AuditGuildSystemChannelID gets sent if the ID of the guild's system // AuditGuildSystemChannelID gets sent if the ID of the guild's system
// channel changed. // channel changed.
// //
// Type: Snowflake // Type: ChannelID
AuditGuildSystemChannelID AuditLogChangeKey = "system_channel_id" AuditGuildSystemChannelID AuditLogChangeKey = "system_channel_id"
) )
@ -294,7 +294,7 @@ const (
// AuditChannelApplicationID contains the application ID of the added or // AuditChannelApplicationID contains the application ID of the added or
// removed webhook or bot. // removed webhook or bot.
// //
// Type: Snowflake // Type: AppID
AuditChannelApplicationID AuditLogChangeKey = "application_id" AuditChannelApplicationID AuditLogChangeKey = "application_id"
// AuditChannelRateLimitPerUser gets sent if the amount of seconds a user // AuditChannelRateLimitPerUser gets sent if the amount of seconds a user
// has to wait before sending another message changed. // has to wait before sending another message changed.
@ -342,12 +342,12 @@ const (
// AuditInviteChannelID gets sent if the channel for an invite code // AuditInviteChannelID gets sent if the channel for an invite code
// changed. // changed.
// //
// Type: Snowflake // Type: ChannelID
AuditInviteChannelID AuditLogChangeKey = "channel_id" AuditInviteChannelID AuditLogChangeKey = "channel_id"
// AuditInviteInviterID specifies the person who created invite code // AuditInviteInviterID specifies the person who created invite code
// changed. // changed.
// //
// Type: Snowflake // Type: UserID
AuditInviteInviterID AuditLogChangeKey = "inviter_id" AuditInviteInviterID AuditLogChangeKey = "inviter_id"
// AuditInviteMaxUses specifies the change to max number of times invite // AuditInviteMaxUses specifies the change to max number of times invite
// code can be used. // code can be used.

View File

@ -3,11 +3,11 @@ package discord
// https://discord.com/developers/docs/resources/channel#channel-object // https://discord.com/developers/docs/resources/channel#channel-object
type Channel struct { type Channel struct {
// ID is the id of this channel. // ID is the id of this channel.
ID Snowflake `json:"id,string"` ID ChannelID `json:"id,string"`
// Type is the type of channel. // Type is the type of channel.
Type ChannelType `json:"type"` Type ChannelType `json:"type"`
// GuildID is the id of the guild. // GuildID is the id of the guild.
GuildID Snowflake `json:"guild_id,string,omitempty"` GuildID GuildID `json:"guild_id,string,omitempty"`
// Position is the sorting position of the channel. // Position is the sorting position of the channel.
Position int `json:"position,omitempty"` Position int `json:"position,omitempty"`
@ -23,7 +23,7 @@ type Channel struct {
// LastMessageID is the id of the last message sent in this channel (may // LastMessageID is the id of the last message sent in this channel (may
// not point to an existing or valid message). // not point to an existing or valid message).
LastMessageID Snowflake `json:"last_message_id,string,omitempty"` LastMessageID MessageID `json:"last_message_id,string,omitempty"`
// VoiceBitrate is the bitrate (in bits) of the voice channel. // VoiceBitrate is the bitrate (in bits) of the voice channel.
VoiceBitrate uint `json:"bitrate,omitempty"` VoiceBitrate uint `json:"bitrate,omitempty"`
@ -40,15 +40,15 @@ type Channel struct {
// Icon is the icon hash. // Icon is the icon hash.
Icon Hash `json:"icon,omitempty"` Icon Hash `json:"icon,omitempty"`
// DMOwnerID is the id of the DM creator. // DMOwnerID is the id of the DM creator.
DMOwnerID Snowflake `json:"owner_id,string,omitempty"` DMOwnerID UserID `json:"owner_id,string,omitempty"`
// AppID is the application id of the group DM creator if it is // AppID is the application id of the group DM creator if it is
// bot-created. // bot-created.
AppID Snowflake `json:"application_id,string,omitempty"` AppID AppID `json:"application_id,string,omitempty"`
// CategoryID is the id of the parent category for a channel (each parent // CategoryID is the id of the parent category for a channel (each parent
// category can contain up to 50 channels). // category can contain up to 50 channels).
CategoryID Snowflake `json:"parent_id,string,omitempty"` CategoryID ChannelID `json:"parent_id,string,omitempty"`
// LastPinTime is when the last pinned message was pinned. // LastPinTime is when the last pinned message was pinned.
LastPinTime Timestamp `json:"last_pin_timestamp,omitempty"` LastPinTime Timestamp `json:"last_pin_timestamp,omitempty"`
} }

View File

@ -3,13 +3,13 @@ package discord
import "strings" import "strings"
type Emoji struct { type Emoji struct {
ID Snowflake `json:"id,string"` // NullSnowflake for unicode emojis ID EmojiID `json:"id,string"` // NullSnowflake for unicode emojis
Name string `json:"name"` Name string `json:"name"`
// These fields are optional // These fields are optional
RoleIDs []Snowflake `json:"roles,omitempty"` RoleIDs []RoleID `json:"roles,omitempty"`
User User `json:"user,omitempty"` User User `json:"user,omitempty"`
RequireColons bool `json:"require_colons,omitempty"` RequireColons bool `json:"require_colons,omitempty"`
Managed bool `json:"managed,omitempty"` Managed bool `json:"managed,omitempty"`
@ -33,7 +33,7 @@ func (e Emoji) EmojiURL() string {
// //
// Supported ImageTypes: PNG, GIF // Supported ImageTypes: PNG, GIF
func (e Emoji) EmojiURLWithType(t ImageType) string { func (e Emoji) EmojiURLWithType(t ImageType) string {
if e.ID == NullSnowflake { if e.ID.IsNull() {
return "" return ""
} }

View File

@ -3,7 +3,7 @@ package discord
// https://discord.com/developers/docs/resources/guild#guild-object // https://discord.com/developers/docs/resources/guild#guild-object
type Guild struct { type Guild struct {
// ID is the guild id. // ID is the guild id.
ID Snowflake `json:"id,string"` ID GuildID `json:"id,string"`
// Name is the guild name (2-100 characters, excluding trailing and leading // Name is the guild name (2-100 characters, excluding trailing and leading
// whitespace). // whitespace).
Name string `json:"name"` Name string `json:"name"`
@ -19,7 +19,7 @@ type Guild struct {
// Owner is true if the user is the owner of the guild. // Owner is true if the user is the owner of the guild.
Owner bool `json:"owner,omitempty"` Owner bool `json:"owner,omitempty"`
// OwnerID is the id of owner. // OwnerID is the id of owner.
OwnerID Snowflake `json:"owner_id,string"` OwnerID UserID `json:"owner_id,string"`
// Permissions are the total permissions for the user in the guild // Permissions are the total permissions for the user in the guild
// (excludes overrides). // (excludes overrides).
@ -29,7 +29,7 @@ type Guild struct {
VoiceRegion string `json:"region"` VoiceRegion string `json:"region"`
// AFKChannelID is the id of the afk channel. // AFKChannelID is the id of the afk channel.
AFKChannelID Snowflake `json:"afk_channel_id,string,omitempty"` AFKChannelID ChannelID `json:"afk_channel_id,string,omitempty"`
// AFKTimeout is the afk timeout in seconds. // AFKTimeout is the afk timeout in seconds.
AFKTimeout Seconds `json:"afk_timeout"` AFKTimeout Seconds `json:"afk_timeout"`
@ -41,7 +41,7 @@ type Guild struct {
// to, or null if set to no invite . // to, or null if set to no invite .
// //
// Deprecated: replaced with WidgetChannelID // Deprecated: replaced with WidgetChannelID
EmbedChannelID Snowflake `json:"embed_channel_id,string,omitempty"` EmbedChannelID ChannelID `json:"embed_channel_id,string,omitempty"`
// Verification is the verification level required for the guild. // Verification is the verification level required for the guild.
Verification Verification `json:"verification_level"` Verification Verification `json:"verification_level"`
@ -63,23 +63,23 @@ type Guild struct {
// AppID is the application id of the guild creator if it is bot-created. // AppID is the application id of the guild creator if it is bot-created.
// //
// This field is nullable. // This field is nullable.
AppID Snowflake `json:"application_id,string,omitempty"` AppID AppID `json:"application_id,string,omitempty"`
// Widget is true if the server widget is enabled. // Widget is true if the server widget is enabled.
Widget bool `json:"widget_enabled,omitempty"` Widget bool `json:"widget_enabled,omitempty"`
// WidgetChannelID is the channel id that the widget will generate an // WidgetChannelID is the channel id that the widget will generate an
// invite to, or null if set to no invite. // invite to, or null if set to no invite.
WidgetChannelID Snowflake `json:"widget_channel_id,string,omitempty"` WidgetChannelID ChannelID `json:"widget_channel_id,string,omitempty"`
// SystemChannelID is the the id of the channel where guild notices such as // SystemChannelID is the the id of the channel where guild notices such as
// welcome messages and boost events are posted. // welcome messages and boost events are posted.
SystemChannelID Snowflake `json:"system_channel_id,string,omitempty"` SystemChannelID ChannelID `json:"system_channel_id,string,omitempty"`
// SystemChannelFlags are the system channel flags. // SystemChannelFlags are the system channel flags.
SystemChannelFlags SystemChannelFlags `json:"system_channel_flags"` SystemChannelFlags SystemChannelFlags `json:"system_channel_flags"`
// RulesChannelID is the id of the channel where guilds with the "PUBLIC" // RulesChannelID is the id of the channel where guilds with the "PUBLIC"
// feature can display rules and/or guidelines. // feature can display rules and/or guidelines.
RulesChannelID Snowflake `json:"rules_channel_id"` RulesChannelID ChannelID `json:"rules_channel_id"`
// MaxPresences is the maximum number of presences for the guild (the // MaxPresences is the maximum number of presences for the guild (the
// default value, currently 25000, is in effect when null is returned, so // default value, currently 25000, is in effect when null is returned, so
@ -110,7 +110,7 @@ type Guild struct {
// PublicUpdatesChannelID is the id of the channel where admins and // PublicUpdatesChannelID is the id of the channel where admins and
// moderators of guilds with the "PUBLIC" feature receive notices from // moderators of guilds with the "PUBLIC" feature receive notices from
// Discord. // Discord.
PublicUpdatesChannelID Snowflake `json:"public_updates_channel_id"` PublicUpdatesChannelID ChannelID `json:"public_updates_channel_id"`
// MaxVideoChannelUsers is the maximum amount of users in a video channel. // MaxVideoChannelUsers is the maximum amount of users in a video channel.
MaxVideoChannelUsers uint64 `json:"max_video_channel_users,omitempty"` MaxVideoChannelUsers uint64 `json:"max_video_channel_users,omitempty"`
@ -200,7 +200,7 @@ func (g Guild) DiscoverySplashURLWithType(t ImageType) string {
// https://discord.com/developers/docs/resources/guild#guild-preview-object // https://discord.com/developers/docs/resources/guild#guild-preview-object
type GuildPreview struct { type GuildPreview struct {
// ID is the guild id. // ID is the guild id.
ID Snowflake `json:"id"` ID GuildID `json:"id"`
// Name is the guild name (2-100 characters). // Name is the guild name (2-100 characters).
Name string `json:"name"` Name string `json:"name"`
@ -285,7 +285,7 @@ func (g GuildPreview) DiscoverySplashURLWithType(t ImageType) string {
// https://discord.com/developers/docs/topics/permissions#role-object // https://discord.com/developers/docs/topics/permissions#role-object
type Role struct { type Role struct {
// ID is the role id. // ID is the role id.
ID Snowflake `json:"id,string"` ID RoleID `json:"id,string"`
// Name is the role name. // Name is the role name.
Name string `json:"name"` Name string `json:"name"`
@ -315,7 +315,7 @@ type Presence struct {
// User is the user presence is being updated for. // User is the user presence is being updated for.
User User `json:"user"` User User `json:"user"`
// RoleIDs are the roles this user is in. // RoleIDs are the roles this user is in.
RoleIDs []Snowflake `json:"roles"` RoleIDs []RoleID `json:"roles"`
// These fields are only filled in gateway events, according to the // These fields are only filled in gateway events, according to the
// documentation. // documentation.
@ -324,7 +324,7 @@ type Presence struct {
Game *Activity `json:"game"` Game *Activity `json:"game"`
// GuildID is the id of the guild // GuildID is the id of the guild
GuildID Snowflake `json:"guild_id"` GuildID GuildID `json:"guild_id"`
// Status is either "idle", "dnd", "online", or "offline". // Status is either "idle", "dnd", "online", or "offline".
Status Status `json:"status"` Status Status `json:"status"`
@ -360,7 +360,7 @@ type Member struct {
// Nick is this users guild nickname. // Nick is this users guild nickname.
Nick string `json:"nick,omitempty"` Nick string `json:"nick,omitempty"`
// RoleIDs is an array of role object ids. // RoleIDs is an array of role object ids.
RoleIDs []Snowflake `json:"roles"` RoleIDs []RoleID `json:"roles"`
// Joined specifies when the user joined the guild. // Joined specifies when the user joined the guild.
Joined Timestamp `json:"joined_at"` Joined Timestamp `json:"joined_at"`
@ -389,7 +389,7 @@ type Ban struct {
// https://discord.com/developers/docs/resources/guild#integration-object // https://discord.com/developers/docs/resources/guild#integration-object
type Integration struct { type Integration struct {
// ID is the integration id. // ID is the integration id.
ID Snowflake `json:"id"` ID IntegrationID `json:"id"`
// Name is the integration name. // Name is the integration name.
Name string `json:"name"` Name string `json:"name"`
// Type is the integration type (twitch, youtube, etc). // Type is the integration type (twitch, youtube, etc).
@ -401,7 +401,7 @@ type Integration struct {
Syncing bool `json:"syncing"` Syncing bool `json:"syncing"`
// RoleID is the id that this integration uses for "subscribers". // RoleID is the id that this integration uses for "subscribers".
RoleID Snowflake `json:"role_id"` RoleID RoleID `json:"role_id"`
// EnableEmoticons specifies whether emoticons should be synced for this // EnableEmoticons specifies whether emoticons should be synced for this
// integration (twitch only currently). // integration (twitch only currently).
@ -434,7 +434,7 @@ type GuildWidget struct {
// Enabled specifies whether the widget is enabled. // Enabled specifies whether the widget is enabled.
Enabled bool `json:"enabled"` Enabled bool `json:"enabled"`
// ChannelID is the widget channel id. // ChannelID is the widget channel id.
ChannelID Snowflake `json:"channel_id,omitempty"` ChannelID ChannelID `json:"channel_id,omitempty"`
} }
// DefaultMemberColor is the color used for members without colored roles. // DefaultMemberColor is the color used for members without colored roles.

View File

@ -7,10 +7,10 @@ import (
) )
type Message struct { type Message struct {
ID Snowflake `json:"id,string"` ID MessageID `json:"id,string"`
Type MessageType `json:"type"` Type MessageType `json:"type"`
ChannelID Snowflake `json:"channel_id,string"` ChannelID ChannelID `json:"channel_id,string"`
GuildID Snowflake `json:"guild_id,string,omitempty"` GuildID GuildID `json:"guild_id,string,omitempty"`
// The author object follows the structure of the user object, but is only // The author object follows the structure of the user object, but is only
// a valid user in the case where the message is generated by a user or bot // a valid user in the case where the message is generated by a user or bot
@ -33,8 +33,8 @@ type Message struct {
// text-based guild channels. // text-based guild channels.
Mentions []GuildUser `json:"mentions"` Mentions []GuildUser `json:"mentions"`
MentionRoleIDs []Snowflake `json:"mention_roles"` MentionRoleIDs []RoleID `json:"mention_roles"`
MentionEveryone bool `json:"mention_everyone"` MentionEveryone bool `json:"mention_everyone"`
// Not all channel mentions in a message will appear in mention_channels. // Not all channel mentions in a message will appear in mention_channels.
MentionChannels []ChannelMention `json:"mention_channels,omitempty"` MentionChannels []ChannelMention `json:"mention_channels,omitempty"`
@ -47,7 +47,7 @@ type Message struct {
// Used for validating a message was sent // Used for validating a message was sent
Nonce string `json:"nonce,omitempty"` Nonce string `json:"nonce,omitempty"`
WebhookID Snowflake `json:"webhook_id,string,omitempty"` WebhookID WebhookID `json:"webhook_id,string,omitempty"`
Activity *MessageActivity `json:"activity,omitempty"` Activity *MessageActivity `json:"activity,omitempty"`
Application *MessageApplication `json:"application,omitempty"` Application *MessageApplication `json:"application,omitempty"`
Reference *MessageReference `json:"message_reference,omitempty"` Reference *MessageReference `json:"message_reference,omitempty"`
@ -100,8 +100,8 @@ var (
) )
type ChannelMention struct { type ChannelMention struct {
ChannelID Snowflake `json:"id,string"` ChannelID ChannelID `json:"id,string"`
GuildID Snowflake `json:"guild_id,string"` GuildID GuildID `json:"guild_id,string"`
ChannelType ChannelType `json:"type"` ChannelType ChannelType `json:"type"`
ChannelName string `json:"name"` ChannelName string `json:"name"`
} }
@ -132,29 +132,29 @@ const (
// //
type MessageApplication struct { type MessageApplication struct {
ID Snowflake `json:"id,string"` ID AppID `json:"id,string"`
CoverID string `json:"cover_image,omitempty"` CoverID string `json:"cover_image,omitempty"`
Description string `json:"description"` Description string `json:"description"`
Icon string `json:"icon"` Icon string `json:"icon"`
Name string `json:"name"` Name string `json:"name"`
} }
// //
type MessageReference struct { type MessageReference struct {
ChannelID Snowflake `json:"channel_id,string"` ChannelID ChannelID `json:"channel_id,string"`
// Field might not be provided // Field might not be provided
MessageID Snowflake `json:"message_id,string,omitempty"` MessageID MessageID `json:"message_id,string,omitempty"`
GuildID Snowflake `json:"guild_id,string,omitempty"` GuildID GuildID `json:"guild_id,string,omitempty"`
} }
// //
type Attachment struct { type Attachment struct {
ID Snowflake `json:"id,string"` ID AttachmentID `json:"id,string"`
Filename string `json:"filename"` Filename string `json:"filename"`
Size uint64 `json:"size"` Size uint64 `json:"size"`
URL URL `json:"url"` URL URL `json:"url"`
Proxy URL `json:"proxy_url"` Proxy URL `json:"proxy_url"`

View File

@ -126,7 +126,7 @@ func CalcOverwrites(guild Guild, channel Channel, member Member) Permissions {
var perm Permissions var perm Permissions
for _, role := range guild.Roles { for _, role := range guild.Roles {
if role.ID == guild.ID { if role.ID == RoleID(guild.ID) {
perm |= role.Permissions perm |= role.Permissions
break break
} }
@ -146,7 +146,7 @@ func CalcOverwrites(guild Guild, channel Channel, member Member) Permissions {
} }
for _, overwrite := range channel.Permissions { for _, overwrite := range channel.Permissions {
if overwrite.ID == guild.ID { if GuildID(overwrite.ID) == guild.ID {
perm &= ^overwrite.Deny perm &= ^overwrite.Deny
perm |= overwrite.Allow perm |= overwrite.Allow
break break
@ -157,7 +157,7 @@ func CalcOverwrites(guild Guild, channel Channel, member Member) Permissions {
for _, overwrite := range channel.Permissions { for _, overwrite := range channel.Permissions {
for _, id := range member.RoleIDs { for _, id := range member.RoleIDs {
if id == overwrite.ID && overwrite.Type == "role" { if id == RoleID(overwrite.ID) && overwrite.Type == "role" {
deny |= overwrite.Deny deny |= overwrite.Deny
allow |= overwrite.Allow allow |= overwrite.Allow
break break
@ -169,7 +169,7 @@ func CalcOverwrites(guild Guild, channel Channel, member Member) Permissions {
perm |= allow perm |= allow
for _, overwrite := range channel.Permissions { for _, overwrite := range channel.Permissions {
if overwrite.ID == member.User.ID { if UserID(overwrite.ID) == member.User.ID {
perm &= ^overwrite.Deny perm &= ^overwrite.Deny
perm |= overwrite.Allow perm |= overwrite.Allow
break break

View File

@ -73,6 +73,11 @@ func (s Snowflake) Valid() bool {
return int64(s) > 0 return int64(s) > 0
} }
// IsNull returns whether or not the snowflake is null.
func (s Snowflake) IsNull() bool {
return s == NullSnowflake
}
func (s Snowflake) Time() time.Time { func (s Snowflake) Time() time.Time {
unixnano := ((time.Duration(s) >> 22) * time.Millisecond) + DiscordEpoch unixnano := ((time.Duration(s) >> 22) * time.Millisecond) + DiscordEpoch
return time.Unix(0, int64(unixnano)) return time.Unix(0, int64(unixnano))
@ -89,3 +94,135 @@ func (s Snowflake) PID() uint8 {
func (s Snowflake) Increment() uint16 { func (s Snowflake) Increment() uint16 {
return uint16(s & 0xFFF) return uint16(s & 0xFFF)
} }
type AppID Snowflake
func (s AppID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *AppID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s AppID) String() string { return Snowflake(s).String() }
func (s AppID) Valid() bool { return Snowflake(s).Valid() }
func (s AppID) IsNull() bool { return Snowflake(s).IsNull() }
func (s AppID) Time() time.Time { return Snowflake(s).Time() }
func (s AppID) Worker() uint8 { return Snowflake(s).Worker() }
func (s AppID) PID() uint8 { return Snowflake(s).PID() }
func (s AppID) Increment() uint16 { return Snowflake(s).Increment() }
type AttachmentID Snowflake
func (s AttachmentID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *AttachmentID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s AttachmentID) String() string { return Snowflake(s).String() }
func (s AttachmentID) Valid() bool { return Snowflake(s).Valid() }
func (s AttachmentID) IsNull() bool { return Snowflake(s).IsNull() }
func (s AttachmentID) Time() time.Time { return Snowflake(s).Time() }
func (s AttachmentID) Worker() uint8 { return Snowflake(s).Worker() }
func (s AttachmentID) PID() uint8 { return Snowflake(s).PID() }
func (s AttachmentID) Increment() uint16 { return Snowflake(s).Increment() }
type AuditLogEntryID Snowflake
func (s AuditLogEntryID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *AuditLogEntryID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s AuditLogEntryID) String() string { return Snowflake(s).String() }
func (s AuditLogEntryID) Valid() bool { return Snowflake(s).Valid() }
func (s AuditLogEntryID) IsNull() bool { return Snowflake(s).IsNull() }
func (s AuditLogEntryID) Time() time.Time { return Snowflake(s).Time() }
func (s AuditLogEntryID) Worker() uint8 { return Snowflake(s).Worker() }
func (s AuditLogEntryID) PID() uint8 { return Snowflake(s).PID() }
func (s AuditLogEntryID) Increment() uint16 { return Snowflake(s).Increment() }
type ChannelID Snowflake
func (s ChannelID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *ChannelID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s ChannelID) String() string { return Snowflake(s).String() }
func (s ChannelID) Valid() bool { return Snowflake(s).Valid() }
func (s ChannelID) IsNull() bool { return Snowflake(s).IsNull() }
func (s ChannelID) Time() time.Time { return Snowflake(s).Time() }
func (s ChannelID) Worker() uint8 { return Snowflake(s).Worker() }
func (s ChannelID) PID() uint8 { return Snowflake(s).PID() }
func (s ChannelID) Increment() uint16 { return Snowflake(s).Increment() }
type EmojiID Snowflake
func (s EmojiID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *EmojiID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s EmojiID) String() string { return Snowflake(s).String() }
func (s EmojiID) Valid() bool { return Snowflake(s).Valid() }
func (s EmojiID) IsNull() bool { return Snowflake(s).IsNull() }
func (s EmojiID) Time() time.Time { return Snowflake(s).Time() }
func (s EmojiID) Worker() uint8 { return Snowflake(s).Worker() }
func (s EmojiID) PID() uint8 { return Snowflake(s).PID() }
func (s EmojiID) Increment() uint16 { return Snowflake(s).Increment() }
type IntegrationID Snowflake
func (s IntegrationID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *IntegrationID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s IntegrationID) String() string { return Snowflake(s).String() }
func (s IntegrationID) Valid() bool { return Snowflake(s).Valid() }
func (s IntegrationID) IsNull() bool { return Snowflake(s).IsNull() }
func (s IntegrationID) Time() time.Time { return Snowflake(s).Time() }
func (s IntegrationID) Worker() uint8 { return Snowflake(s).Worker() }
func (s IntegrationID) PID() uint8 { return Snowflake(s).PID() }
func (s IntegrationID) Increment() uint16 { return Snowflake(s).Increment() }
type GuildID Snowflake
func (s GuildID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *GuildID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s GuildID) String() string { return Snowflake(s).String() }
func (s GuildID) Valid() bool { return Snowflake(s).Valid() }
func (s GuildID) IsNull() bool { return Snowflake(s).IsNull() }
func (s GuildID) Time() time.Time { return Snowflake(s).Time() }
func (s GuildID) Worker() uint8 { return Snowflake(s).Worker() }
func (s GuildID) PID() uint8 { return Snowflake(s).PID() }
func (s GuildID) Increment() uint16 { return Snowflake(s).Increment() }
type MessageID Snowflake
func (s MessageID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *MessageID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s MessageID) String() string { return Snowflake(s).String() }
func (s MessageID) Valid() bool { return Snowflake(s).Valid() }
func (s MessageID) IsNull() bool { return Snowflake(s).IsNull() }
func (s MessageID) Time() time.Time { return Snowflake(s).Time() }
func (s MessageID) Worker() uint8 { return Snowflake(s).Worker() }
func (s MessageID) PID() uint8 { return Snowflake(s).PID() }
func (s MessageID) Increment() uint16 { return Snowflake(s).Increment() }
type RoleID Snowflake
func (s RoleID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *RoleID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s RoleID) String() string { return Snowflake(s).String() }
func (s RoleID) Valid() bool { return Snowflake(s).Valid() }
func (s RoleID) IsNull() bool { return Snowflake(s).IsNull() }
func (s RoleID) Time() time.Time { return Snowflake(s).Time() }
func (s RoleID) Worker() uint8 { return Snowflake(s).Worker() }
func (s RoleID) PID() uint8 { return Snowflake(s).PID() }
func (s RoleID) Increment() uint16 { return Snowflake(s).Increment() }
type UserID Snowflake
func (s UserID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *UserID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s UserID) String() string { return Snowflake(s).String() }
func (s UserID) Valid() bool { return Snowflake(s).Valid() }
func (s UserID) IsNull() bool { return Snowflake(s).IsNull() }
func (s UserID) Time() time.Time { return Snowflake(s).Time() }
func (s UserID) Worker() uint8 { return Snowflake(s).Worker() }
func (s UserID) PID() uint8 { return Snowflake(s).PID() }
func (s UserID) Increment() uint16 { return Snowflake(s).Increment() }
type WebhookID Snowflake
func (s WebhookID) MarshalJSON() ([]byte, error) { return Snowflake(s).MarshalJSON() }
func (s *WebhookID) UnmarshalJSON(v []byte) error { return (*Snowflake)(s).UnmarshalJSON(v) }
func (s WebhookID) String() string { return Snowflake(s).String() }
func (s WebhookID) Valid() bool { return Snowflake(s).Valid() }
func (s WebhookID) IsNull() bool { return Snowflake(s).IsNull() }
func (s WebhookID) Time() time.Time { return Snowflake(s).Time() }
func (s WebhookID) Worker() uint8 { return Snowflake(s).Worker() }
func (s WebhookID) PID() uint8 { return Snowflake(s).PID() }
func (s WebhookID) Increment() uint16 { return Snowflake(s).Increment() }

View File

@ -5,10 +5,10 @@ import (
) )
type User struct { type User struct {
ID Snowflake `json:"id,string"` ID UserID `json:"id,string"`
Username string `json:"username"` Username string `json:"username"`
Discriminator string `json:"discriminator"` Discriminator string `json:"discriminator"`
Avatar Hash `json:"avatar"` Avatar Hash `json:"avatar"`
// These fields may be omitted // These fields may be omitted
@ -93,9 +93,9 @@ const (
) )
type Connection struct { type Connection struct {
ID Snowflake `json:"id"` ID string `json:"id"`
Name string `json:"name"` Name string `json:"name"`
Type Service `json:"type"` Type Service `json:"type"`
Revoked bool `json:"revoked"` Revoked bool `json:"revoked"`
Verified bool `json:"verified"` Verified bool `json:"verified"`
@ -136,10 +136,10 @@ type Activity struct {
CreatedAt UnixTimestamp `json:"created_at,omitempty"` CreatedAt UnixTimestamp `json:"created_at,omitempty"`
Timestamps *ActivityTimestamp `json:"timestamps,omitempty"` Timestamps *ActivityTimestamp `json:"timestamps,omitempty"`
ApplicationID Snowflake `json:"application_id,omitempty"` ApplicationID AppID `json:"application_id,omitempty"`
Details string `json:"details,omitempty"` Details string `json:"details,omitempty"`
State string `json:"state,omitempty"` // party status State string `json:"state,omitempty"` // party status
Emoji *Emoji `json:"emoji,omitempty"` Emoji *Emoji `json:"emoji,omitempty"`
Party *ActivityParty `json:"party,omitempty"` Party *ActivityParty `json:"party,omitempty"`
Assets *ActivityAssets `json:"assets,omitempty"` Assets *ActivityAssets `json:"assets,omitempty"`
@ -204,7 +204,7 @@ type ActivitySecrets struct {
// A Relationship between the logged in user and the user in the struct. This // A Relationship between the logged in user and the user in the struct. This
// struct is undocumented. // struct is undocumented.
type Relationship struct { type Relationship struct {
UserID Snowflake `json:"id"` UserID UserID `json:"id"`
User User `json:"user"` User User `json:"user"`
Type RelationshipType `json:"type"` Type RelationshipType `json:"type"`
} }

View File

@ -2,10 +2,10 @@ package discord
type VoiceState struct { type VoiceState struct {
// GuildID isn't available from the Guild struct. // GuildID isn't available from the Guild struct.
GuildID Snowflake `json:"guild_id,string"` GuildID GuildID `json:"guild_id,string"`
ChannelID Snowflake `json:"channel_id,string"` ChannelID ChannelID `json:"channel_id,string"`
UserID Snowflake `json:"user_id,string"` UserID UserID `json:"user_id,string"`
Member *Member `json:"member,omitempty"` Member *Member `json:"member,omitempty"`
SessionID string `json:"session_id"` SessionID string `json:"session_id"`

View File

@ -1,12 +1,12 @@
package discord package discord
type Webhook struct { type Webhook struct {
ID Snowflake `json:"id"` ID WebhookID `json:"id"`
Type WebhookType `json:"type"` Type WebhookType `json:"type"`
User User `json:"user"` // creator User User `json:"user"` // creator
GuildID Snowflake `json:"guild_id,omitempty"` GuildID GuildID `json:"guild_id,omitempty"`
ChannelID Snowflake `json:"channel_id"` ChannelID ChannelID `json:"channel_id"`
Name string `json:"name"` Name string `json:"name"`
Avatar Hash `json:"avatar"` Avatar Hash `json:"avatar"`

View File

@ -78,8 +78,8 @@ func (g *Gateway) HeartbeatCtx(ctx context.Context) error {
} }
type RequestGuildMembersData struct { type RequestGuildMembersData struct {
GuildID []discord.Snowflake `json:"guild_id"` GuildID []discord.GuildID `json:"guild_id"`
UserIDs []discord.Snowflake `json:"user_ids,omitempty"` UserIDs []discord.UserID `json:"user_ids,omitempty"`
Query string `json:"query,omitempty"` Query string `json:"query,omitempty"`
Limit uint `json:"limit"` Limit uint `json:"limit"`
@ -101,8 +101,8 @@ func (g *Gateway) RequestGuildMembersCtx(
} }
type UpdateVoiceStateData struct { type UpdateVoiceStateData struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
ChannelID discord.Snowflake `json:"channel_id"` // nullable ChannelID discord.ChannelID `json:"channel_id"` // nullable
SelfMute bool `json:"self_mute"` SelfMute bool `json:"self_mute"`
SelfDeaf bool `json:"self_deaf"` SelfDeaf bool `json:"self_deaf"`
} }
@ -144,12 +144,12 @@ func (g *Gateway) UpdateStatusCtx(ctx context.Context, data UpdateStatusData) er
// Undocumented // Undocumented
type GuildSubscribeData struct { type GuildSubscribeData struct {
Typing bool `json:"typing"` Typing bool `json:"typing"`
Activities bool `json:"activities"` Activities bool `json:"activities"`
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
// Channels is not documented. It's used to fetch the right members sidebar. // Channels is not documented. It's used to fetch the right members sidebar.
Channels map[discord.Snowflake][][2]int `json:"channels"` Channels map[discord.ChannelID][][2]int `json:"channels"`
} }
func (g *Gateway) GuildSubscribe(data GuildSubscribeData) error { func (g *Gateway) GuildSubscribe(data GuildSubscribeData) error {

View File

@ -30,17 +30,17 @@ type (
discord.Channel discord.Channel
} }
ChannelPinsUpdateEvent struct { ChannelPinsUpdateEvent struct {
GuildID discord.Snowflake `json:"guild_id,omitempty"` GuildID discord.GuildID `json:"guild_id,omitempty"`
ChannelID discord.Snowflake `json:"channel_id,omitempty"` ChannelID discord.ChannelID `json:"channel_id,omitempty"`
LastPin discord.Timestamp `json:"timestamp,omitempty"` LastPin discord.Timestamp `json:"timestamp,omitempty"`
} }
ChannelUnreadUpdateEvent struct { ChannelUnreadUpdateEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
ChannelUnreadUpdates []struct { ChannelUnreadUpdates []struct {
ID discord.Snowflake `json:"id"` ID discord.ChannelID `json:"id"`
LastMessageID discord.Snowflake `json:"last_message_id"` LastMessageID discord.MessageID `json:"last_message_id"`
} }
} }
) )
@ -64,48 +64,48 @@ type (
discord.Guild discord.Guild
} }
GuildDeleteEvent struct { GuildDeleteEvent struct {
ID discord.Snowflake `json:"id"` ID discord.GuildID `json:"id"`
// Unavailable if false == removed // Unavailable if false == removed
Unavailable bool `json:"unavailable"` Unavailable bool `json:"unavailable"`
} }
GuildBanAddEvent struct { GuildBanAddEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
User discord.User `json:"user"` User discord.User `json:"user"`
} }
GuildBanRemoveEvent struct { GuildBanRemoveEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
User discord.User `json:"user"` User discord.User `json:"user"`
} }
GuildEmojisUpdateEvent struct { GuildEmojisUpdateEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
Emojis []discord.Emoji `json:"emoji"` Emojis []discord.Emoji `json:"emoji"`
} }
GuildIntegrationsUpdateEvent struct { GuildIntegrationsUpdateEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
} }
GuildMemberAddEvent struct { GuildMemberAddEvent struct {
discord.Member discord.Member
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
} }
GuildMemberRemoveEvent struct { GuildMemberRemoveEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
User discord.User `json:"user"` User discord.User `json:"user"`
} }
GuildMemberUpdateEvent struct { GuildMemberUpdateEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
RoleIDs []discord.Snowflake `json:"roles"` RoleIDs []discord.RoleID `json:"roles"`
User discord.User `json:"user"` User discord.User `json:"user"`
Nick string `json:"nick"` Nick string `json:"nick"`
} }
// GuildMembersChunkEvent is sent when Guild Request Members is called. // GuildMembersChunkEvent is sent when Guild Request Members is called.
GuildMembersChunkEvent struct { GuildMembersChunkEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
Members []discord.Member `json:"members"` Members []discord.Member `json:"members"`
ChunkIndex int `json:"chunk_index"` ChunkIndex int `json:"chunk_index"`
ChunkCount int `json:"chunk_count"` ChunkCount int `json:"chunk_count"`
@ -122,10 +122,10 @@ type (
// client sends over GuildSubscriptions with the Channels field used. // client sends over GuildSubscriptions with the Channels field used.
// The State package does not handle this event. // The State package does not handle this event.
GuildMemberListUpdate struct { GuildMemberListUpdate struct {
ID string `json:"id"` ID string `json:"id"`
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
MemberCount uint64 `json:"member_count"` MemberCount uint64 `json:"member_count"`
OnlineCount uint64 `json:"online_count"` OnlineCount uint64 `json:"online_count"`
// Groups is all the visible role sections. // Groups is all the visible role sections.
Groups []GuildMemberListGroup `json:"groups"` Groups []GuildMemberListGroup `json:"groups"`
@ -133,7 +133,7 @@ type (
Ops []GuildMemberListOp `json:"ops"` Ops []GuildMemberListOp `json:"ops"`
} }
GuildMemberListGroup struct { GuildMemberListGroup struct {
ID string `json:"id"` // either discord.Snowflake Role IDs or "online" ID string `json:"id"` // either discord.RoleID or "online"
Count uint64 `json:"count"` Count uint64 `json:"count"`
} }
GuildMemberListOp struct { GuildMemberListOp struct {
@ -164,16 +164,16 @@ type (
} }
GuildRoleCreateEvent struct { GuildRoleCreateEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
Role discord.Role `json:"role"` Role discord.Role `json:"role"`
} }
GuildRoleUpdateEvent struct { GuildRoleUpdateEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
Role discord.Role `json:"role"` Role discord.Role `json:"role"`
} }
GuildRoleDeleteEvent struct { GuildRoleDeleteEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
RoleID discord.Snowflake `json:"role_id"` RoleID discord.RoleID `json:"role_id"`
} }
) )
@ -188,8 +188,8 @@ type (
InviteCreateEvent struct { InviteCreateEvent struct {
Code string `json:"code"` Code string `json:"code"`
CreatedAt discord.Timestamp `json:"created_at"` CreatedAt discord.Timestamp `json:"created_at"`
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
GuildID discord.Snowflake `json:"guild_id,omitempty"` GuildID discord.GuildID `json:"guild_id,omitempty"`
// Similar to discord.Invite // Similar to discord.Invite
Inviter *discord.User `json:"inviter,omitempty"` Inviter *discord.User `json:"inviter,omitempty"`
@ -200,8 +200,8 @@ type (
} }
InviteDeleteEvent struct { InviteDeleteEvent struct {
Code string `json:"code"` Code string `json:"code"`
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
GuildID discord.Snowflake `json:"guild_id,omitempty"` GuildID discord.GuildID `json:"guild_id,omitempty"`
} }
) )
@ -216,48 +216,48 @@ type (
Member *discord.Member `json:"member,omitempty"` Member *discord.Member `json:"member,omitempty"`
} }
MessageDeleteEvent struct { MessageDeleteEvent struct {
ID discord.Snowflake `json:"id"` ID discord.MessageID `json:"id"`
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
GuildID discord.Snowflake `json:"guild_id,omitempty"` GuildID discord.GuildID `json:"guild_id,omitempty"`
} }
MessageDeleteBulkEvent struct { MessageDeleteBulkEvent struct {
IDs []discord.Snowflake `json:"ids"` IDs []discord.MessageID `json:"ids"`
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
GuildID discord.Snowflake `json:"guild_id,omitempty"` GuildID discord.GuildID `json:"guild_id,omitempty"`
} }
MessageReactionAddEvent struct { MessageReactionAddEvent struct {
UserID discord.Snowflake `json:"user_id"` UserID discord.UserID `json:"user_id"`
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
MessageID discord.Snowflake `json:"message_id"` MessageID discord.MessageID `json:"message_id"`
Emoji discord.Emoji `json:"emoji,omitempty"` Emoji discord.Emoji `json:"emoji,omitempty"`
GuildID discord.Snowflake `json:"guild_id,omitempty"` GuildID discord.GuildID `json:"guild_id,omitempty"`
Member *discord.Member `json:"member,omitempty"` Member *discord.Member `json:"member,omitempty"`
} }
MessageReactionRemoveEvent struct { MessageReactionRemoveEvent struct {
UserID discord.Snowflake `json:"user_id"` UserID discord.UserID `json:"user_id"`
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
MessageID discord.Snowflake `json:"message_id"` MessageID discord.MessageID `json:"message_id"`
Emoji discord.Emoji `json:"emoji"` Emoji discord.Emoji `json:"emoji"`
GuildID discord.Snowflake `json:"guild_id,omitempty"` GuildID discord.GuildID `json:"guild_id,omitempty"`
} }
MessageReactionRemoveAllEvent struct { MessageReactionRemoveAllEvent struct {
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
MessageID discord.Snowflake `json:"message_id"` MessageID discord.MessageID `json:"message_id"`
GuildID discord.Snowflake `json:"guild_id,omitempty"` GuildID discord.GuildID `json:"guild_id,omitempty"`
} }
MessageReactionRemoveEmoji struct { MessageReactionRemoveEmoji struct {
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
MessageID discord.Snowflake `json:"message_id"` MessageID discord.MessageID `json:"message_id"`
Emoji discord.Emoji `json:"emoji"` Emoji discord.Emoji `json:"emoji"`
GuildID discord.Snowflake `json:"guild_id,omitempty"` GuildID discord.GuildID `json:"guild_id,omitempty"`
} }
MessageAckEvent struct { MessageAckEvent struct {
MessageID discord.Snowflake `json:"message_id"` MessageID discord.MessageID `json:"message_id"`
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
} }
) )
@ -288,12 +288,12 @@ type (
} }
TypingStartEvent struct { TypingStartEvent struct {
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
UserID discord.Snowflake `json:"user_id"` UserID discord.UserID `json:"user_id"`
Timestamp discord.UnixTimestamp `json:"timestamp"` Timestamp discord.UnixTimestamp `json:"timestamp"`
GuildID discord.Snowflake `json:"guild_id,omitempty"` GuildID discord.GuildID `json:"guild_id,omitempty"`
Member *discord.Member `json:"member,omitempty"` Member *discord.Member `json:"member,omitempty"`
} }
UserUpdateEvent struct { UserUpdateEvent struct {
@ -307,17 +307,17 @@ type (
discord.VoiceState discord.VoiceState
} }
VoiceServerUpdateEvent struct { VoiceServerUpdateEvent struct {
Token string `json:"token"` Token string `json:"token"`
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
Endpoint string `json:"endpoint"` Endpoint string `json:"endpoint"`
} }
) )
// https://discordapp.com/developers/docs/topics/gateway#webhooks // https://discordapp.com/developers/docs/topics/gateway#webhooks
type ( type (
WebhooksUpdateEvent struct { WebhooksUpdateEvent struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
} }
) )
@ -330,8 +330,8 @@ type (
UserSettings UserSettings
} }
UserNoteUpdateEvent struct { UserNoteUpdateEvent struct {
ID discord.Snowflake `json:"id"` ID discord.UserID `json:"id"`
Note string `json:"note"` Note string `json:"note"`
} }
) )

View File

@ -20,8 +20,8 @@ type ReadyEvent struct {
ReadState []ReadState `json:"read_state,omitempty"` ReadState []ReadState `json:"read_state,omitempty"`
Presences []discord.Presence `json:"presences,omitempty"` Presences []discord.Presence `json:"presences,omitempty"`
Relationships []discord.Relationship `json:"relationships,omitempty"` Relationships []discord.Relationship `json:"relationships,omitempty"`
Notes map[discord.Snowflake]string `json:"notes,omitempty"` Notes map[discord.UserID]string `json:"notes,omitempty"`
} }
type UserSettings struct { type UserSettings struct {
@ -48,9 +48,9 @@ type UserSettings struct {
Locale string `json:"locale"` Locale string `json:"locale"`
Theme string `json:"theme"` Theme string `json:"theme"`
GuildPositions []discord.Snowflake `json:"guild_positions"` GuildPositions []discord.GuildID `json:"guild_positions"`
GuildFolders []GuildFolder `json:"guild_folders"` GuildFolders []GuildFolder `json:"guild_folders"`
RestrictedGuilds []discord.Snowflake `json:"restricted_guilds"` RestrictedGuilds []discord.GuildID `json:"restricted_guilds"`
FriendSourceFlags struct { FriendSourceFlags struct {
All bool `json:"all"` All bool `json:"all"`
@ -62,14 +62,14 @@ type UserSettings struct {
CustomStatus struct { CustomStatus struct {
Text string `json:"text"` Text string `json:"text"`
ExpiresAt discord.Timestamp `json:"expires_at,omitempty"` ExpiresAt discord.Timestamp `json:"expires_at,omitempty"`
EmojiID discord.Snowflake `json:"emoji_id,string"` EmojiID discord.EmojiID `json:"emoji_id,string"`
EmojiName string `json:"emoji_name"` EmojiName string `json:"emoji_name"`
} `json:"custom_status"` } `json:"custom_status"`
} }
// A UserGuildSettings stores data for a users guild settings. // A UserGuildSettings stores data for a users guild settings.
type UserGuildSettings struct { type UserGuildSettings struct {
GuildID discord.Snowflake `json:"guild_id"` GuildID discord.GuildID `json:"guild_id"`
SupressEveryone bool `json:"suppress_everyone"` SupressEveryone bool `json:"suppress_everyone"`
SupressRoles bool `json:"suppress_roles"` SupressRoles bool `json:"suppress_roles"`
@ -91,8 +91,8 @@ const (
) )
type ReadState struct { type ReadState struct {
ChannelID discord.Snowflake `json:"id"` ChannelID discord.ChannelID `json:"id"`
LastMessageID discord.Snowflake `json:"last_message_id"` LastMessageID discord.MessageID `json:"last_message_id"`
MentionCount int `json:"mention_count"` MentionCount int `json:"mention_count"`
} }
@ -102,13 +102,13 @@ type SettingsChannelOverride struct {
Muted bool `json:"muted"` Muted bool `json:"muted"`
MessageNotifications UserNotification `json:"message_notifications"` MessageNotifications UserNotification `json:"message_notifications"`
ChannelID discord.Snowflake `json:"channel_id"` ChannelID discord.ChannelID `json:"channel_id"`
} }
// GuildFolder holds a single folder that you see in the left guild panel. // GuildFolder holds a single folder that you see in the left guild panel.
type GuildFolder struct { type GuildFolder struct {
Name string `json:"name"` Name string `json:"name"`
ID discord.Snowflake `json:"id"` ID string `json:"id"`
GuildIDs []discord.Snowflake `json:"guild_ids"` GuildIDs []discord.GuildID `json:"guild_ids"`
Color discord.Color `json:"color"` Color discord.Color `json:"color"`
} }

View File

@ -84,17 +84,17 @@ type State struct {
// List of channels with few messages, so it doesn't bother hitting the API // List of channels with few messages, so it doesn't bother hitting the API
// again. // again.
fewMessages map[discord.Snowflake]struct{} fewMessages map[discord.ChannelID]struct{}
fewMutex *sync.Mutex fewMutex *sync.Mutex
// unavailableGuilds is a set of discord.Snowflakes of guilds that became // unavailableGuilds is a set of discord.GuildIDs of guilds that became
// unavailable when already connected to the gateway, i.e. sent in a // unavailable when already connected to the gateway, i.e. sent in a
// GuildUnavailableEvent. // GuildUnavailableEvent.
unavailableGuilds *moreatomic.SnowflakeSet unavailableGuilds *moreatomic.GuildIDSet
// unreadyGuilds is a set of discord.Snowflakes of guilds that were // unreadyGuilds is a set of discord.GuildIDs of guilds that were
// unavailable when connecting to the gateway, i.e. they had Unavailable // unavailable when connecting to the gateway, i.e. they had Unavailable
// set to true during Ready. // set to true during Ready.
unreadyGuilds *moreatomic.SnowflakeSet unreadyGuilds *moreatomic.GuildIDSet
} }
// New creates a new state. // New creates a new state.
@ -130,10 +130,10 @@ func NewFromSession(s *session.Session, store Store) (*State, error) {
Store: store, Store: store,
Handler: handler.New(), Handler: handler.New(),
StateLog: func(err error) {}, StateLog: func(err error) {},
fewMessages: map[discord.Snowflake]struct{}{}, fewMessages: map[discord.ChannelID]struct{}{},
fewMutex: new(sync.Mutex), fewMutex: new(sync.Mutex),
unavailableGuilds: moreatomic.NewSnowflakeSet(), unavailableGuilds: moreatomic.NewGuildIDSet(),
unreadyGuilds: moreatomic.NewSnowflakeSet(), unreadyGuilds: moreatomic.NewGuildIDSet(),
} }
state.hookSession() state.hookSession()
return state, nil return state, nil
@ -171,7 +171,7 @@ func (s *State) AuthorDisplayName(message *gateway.MessageCreateEvent) string {
return n return n
} }
func (s *State) MemberDisplayName(guildID, userID discord.Snowflake) (string, error) { func (s *State) MemberDisplayName(guildID discord.GuildID, userID discord.UserID) (string, error) {
member, err := s.Member(guildID, userID) member, err := s.Member(guildID, userID)
if err != nil { if err != nil {
return "", err return "", err
@ -200,7 +200,7 @@ func (s *State) AuthorColor(message *gateway.MessageCreateEvent) (discord.Color,
return s.MemberColor(message.GuildID, message.Author.ID) return s.MemberColor(message.GuildID, message.Author.ID)
} }
func (s *State) MemberColor(guildID, userID discord.Snowflake) (discord.Color, error) { func (s *State) MemberColor(guildID discord.GuildID, userID discord.UserID) (discord.Color, error) {
var wg sync.WaitGroup var wg sync.WaitGroup
g, gerr := s.Store.Guild(guildID) g, gerr := s.Store.Guild(guildID)
@ -235,7 +235,7 @@ func (s *State) MemberColor(guildID, userID discord.Snowflake) (discord.Color, e
//// ////
func (s *State) Permissions(channelID, userID discord.Snowflake) (discord.Permissions, error) { func (s *State) Permissions(channelID discord.ChannelID, userID discord.UserID) (discord.Permissions, error) {
ch, err := s.Channel(channelID) ch, err := s.Channel(channelID)
if err != nil { if err != nil {
return 0, errors.Wrap(err, "failed to get channel") return 0, errors.Wrap(err, "failed to get channel")
@ -291,7 +291,7 @@ func (s *State) Me() (*discord.User, error) {
//// ////
func (s *State) Channel(id discord.Snowflake) (*discord.Channel, error) { func (s *State) Channel(id discord.ChannelID) (*discord.Channel, error) {
c, err := s.Store.Channel(id) c, err := s.Store.Channel(id)
if err == nil { if err == nil {
return c, nil return c, nil
@ -305,7 +305,7 @@ func (s *State) Channel(id discord.Snowflake) (*discord.Channel, error) {
return c, s.Store.ChannelSet(c) return c, s.Store.ChannelSet(c)
} }
func (s *State) Channels(guildID discord.Snowflake) ([]discord.Channel, error) { func (s *State) Channels(guildID discord.GuildID) ([]discord.Channel, error) {
c, err := s.Store.Channels(guildID) c, err := s.Store.Channels(guildID)
if err == nil { if err == nil {
return c, nil return c, nil
@ -327,7 +327,7 @@ func (s *State) Channels(guildID discord.Snowflake) ([]discord.Channel, error) {
return c, nil return c, nil
} }
func (s *State) CreatePrivateChannel(recipient discord.Snowflake) (*discord.Channel, error) { func (s *State) CreatePrivateChannel(recipient discord.UserID) (*discord.Channel, error) {
c, err := s.Store.CreatePrivateChannel(recipient) c, err := s.Store.CreatePrivateChannel(recipient)
if err == nil { if err == nil {
return c, nil return c, nil
@ -366,7 +366,7 @@ func (s *State) PrivateChannels() ([]discord.Channel, error) {
//// ////
func (s *State) Emoji( func (s *State) Emoji(
guildID, emojiID discord.Snowflake) (*discord.Emoji, error) { guildID discord.GuildID, emojiID discord.EmojiID) (*discord.Emoji, error) {
e, err := s.Store.Emoji(guildID, emojiID) e, err := s.Store.Emoji(guildID, emojiID)
if err == nil { if err == nil {
@ -391,7 +391,7 @@ func (s *State) Emoji(
return nil, ErrStoreNotFound return nil, ErrStoreNotFound
} }
func (s *State) Emojis(guildID discord.Snowflake) ([]discord.Emoji, error) { func (s *State) Emojis(guildID discord.GuildID) ([]discord.Emoji, error) {
e, err := s.Store.Emojis(guildID) e, err := s.Store.Emojis(guildID)
if err == nil { if err == nil {
return e, nil return e, nil
@ -407,7 +407,7 @@ func (s *State) Emojis(guildID discord.Snowflake) ([]discord.Emoji, error) {
//// ////
func (s *State) Guild(id discord.Snowflake) (*discord.Guild, error) { func (s *State) Guild(id discord.GuildID) (*discord.Guild, error) {
c, err := s.Store.Guild(id) c, err := s.Store.Guild(id)
if err == nil { if err == nil {
return c, nil return c, nil
@ -441,7 +441,7 @@ func (s *State) Guilds() ([]discord.Guild, error) {
//// ////
func (s *State) Member(guildID, userID discord.Snowflake) (*discord.Member, error) { func (s *State) Member(guildID discord.GuildID, userID discord.UserID) (*discord.Member, error) {
m, err := s.Store.Member(guildID, userID) m, err := s.Store.Member(guildID, userID)
if err == nil { if err == nil {
return m, nil return m, nil
@ -450,7 +450,7 @@ func (s *State) Member(guildID, userID discord.Snowflake) (*discord.Member, erro
return s.fetchMember(guildID, userID) return s.fetchMember(guildID, userID)
} }
func (s *State) Members(guildID discord.Snowflake) ([]discord.Member, error) { func (s *State) Members(guildID discord.GuildID) ([]discord.Member, error) {
ms, err := s.Store.Members(guildID) ms, err := s.Store.Members(guildID)
if err == nil { if err == nil {
return ms, nil return ms, nil
@ -468,14 +468,14 @@ func (s *State) Members(guildID discord.Snowflake) ([]discord.Member, error) {
} }
return ms, s.Gateway.RequestGuildMembers(gateway.RequestGuildMembersData{ return ms, s.Gateway.RequestGuildMembers(gateway.RequestGuildMembersData{
GuildID: []discord.Snowflake{guildID}, GuildID: []discord.GuildID{guildID},
Presences: true, Presences: true,
}) })
} }
//// ////
func (s *State) Message(channelID, messageID discord.Snowflake) (*discord.Message, error) { func (s *State) Message(channelID discord.ChannelID, messageID discord.MessageID) (*discord.Message, error) {
m, err := s.Store.Message(channelID, messageID) m, err := s.Store.Message(channelID, messageID)
if err == nil { if err == nil {
return m, nil return m, nil
@ -515,7 +515,7 @@ func (s *State) Message(channelID, messageID discord.Snowflake) (*discord.Messag
// Messages fetches maximum 100 messages from the API, if it has to. There is no // Messages fetches maximum 100 messages from the API, if it has to. There is no
// limit if it's from the State storage. // limit if it's from the State storage.
func (s *State) Messages(channelID discord.Snowflake) ([]discord.Message, error) { func (s *State) Messages(channelID discord.ChannelID) ([]discord.Message, error) {
// TODO: Think of a design that doesn't rely on MaxMessages(). // TODO: Think of a design that doesn't rely on MaxMessages().
var maxMsgs = s.MaxMessages() var maxMsgs = s.MaxMessages()
@ -544,7 +544,7 @@ func (s *State) Messages(channelID discord.Snowflake) ([]discord.Message, error)
// New messages fetched weirdly does not have GuildID filled. We'll try and // New messages fetched weirdly does not have GuildID filled. We'll try and
// get it for consistency with incoming message creates. // get it for consistency with incoming message creates.
var guildID discord.Snowflake var guildID discord.GuildID
// A bit too convoluted, but whatever. // A bit too convoluted, but whatever.
c, err := s.Channel(channelID) c, err := s.Channel(channelID)
@ -582,7 +582,7 @@ func (s *State) Messages(channelID discord.Snowflake) ([]discord.Message, error)
// Presence checks the state for user presences. If no guildID is given, it will // Presence checks the state for user presences. If no guildID is given, it will
// look for the presence in all guilds. // look for the presence in all guilds.
func (s *State) Presence(guildID, userID discord.Snowflake) (*discord.Presence, error) { func (s *State) Presence(guildID discord.GuildID, userID discord.UserID) (*discord.Presence, error) {
p, err := s.Store.Presence(guildID, userID) p, err := s.Store.Presence(guildID, userID)
if err == nil { if err == nil {
return p, nil return p, nil
@ -607,7 +607,7 @@ func (s *State) Presence(guildID, userID discord.Snowflake) (*discord.Presence,
//// ////
func (s *State) Role(guildID, roleID discord.Snowflake) (*discord.Role, error) { func (s *State) Role(guildID discord.GuildID, roleID discord.RoleID) (*discord.Role, error) {
r, err := s.Store.Role(guildID, roleID) r, err := s.Store.Role(guildID, roleID)
if err == nil { if err == nil {
return r, nil return r, nil
@ -635,7 +635,7 @@ func (s *State) Role(guildID, roleID discord.Snowflake) (*discord.Role, error) {
return role, nil return role, nil
} }
func (s *State) Roles(guildID discord.Snowflake) ([]discord.Role, error) { func (s *State) Roles(guildID discord.GuildID) ([]discord.Role, error) {
rs, err := s.Store.Roles(guildID) rs, err := s.Store.Roles(guildID)
if err == nil { if err == nil {
return rs, nil return rs, nil
@ -657,7 +657,7 @@ func (s *State) Roles(guildID discord.Snowflake) ([]discord.Role, error) {
return rs, nil return rs, nil
} }
func (s *State) fetchGuild(id discord.Snowflake) (g *discord.Guild, err error) { func (s *State) fetchGuild(id discord.GuildID) (g *discord.Guild, err error) {
g, err = s.Session.Guild(id) g, err = s.Session.Guild(id)
if err == nil { if err == nil {
err = s.Store.GuildSet(g) err = s.Store.GuildSet(g)
@ -666,7 +666,7 @@ func (s *State) fetchGuild(id discord.Snowflake) (g *discord.Guild, err error) {
return return
} }
func (s *State) fetchMember(guildID, userID discord.Snowflake) (m *discord.Member, err error) { func (s *State) fetchMember(guildID discord.GuildID, userID discord.UserID) (m *discord.Member, err error) {
m, err = s.Session.Member(guildID, userID) m, err = s.Session.Member(guildID, userID)
if err == nil { if err == nil {
err = s.Store.MemberSet(guildID, m) err = s.Store.MemberSet(guildID, m)

View File

@ -308,7 +308,7 @@ func (s *State) batchLog(errors ...error) {
// Helper functions // Helper functions
func (s *State) editMessage(ch, msg discord.Snowflake, fn func(m *discord.Message) bool) { func (s *State) editMessage(ch discord.ChannelID, msg discord.MessageID, fn func(m *discord.Message) bool) {
m, err := s.Store.Message(ch, msg) m, err := s.Store.Message(ch, msg)
if err != nil { if err != nil {
return return

View File

@ -25,36 +25,36 @@ type StoreGetter interface {
Me() (*discord.User, error) Me() (*discord.User, error)
// Channel should check for both DM and guild channels. // Channel should check for both DM and guild channels.
Channel(id discord.Snowflake) (*discord.Channel, error) Channel(id discord.ChannelID) (*discord.Channel, error)
Channels(guildID discord.Snowflake) ([]discord.Channel, error) Channels(guildID discord.GuildID) ([]discord.Channel, error)
// same API as (*api.Client) // same API as (*api.Client)
CreatePrivateChannel(recipient discord.Snowflake) (*discord.Channel, error) CreatePrivateChannel(recipient discord.UserID) (*discord.Channel, error)
PrivateChannels() ([]discord.Channel, error) PrivateChannels() ([]discord.Channel, error)
Emoji(guildID, emojiID discord.Snowflake) (*discord.Emoji, error) Emoji(guildID discord.GuildID, emojiID discord.EmojiID) (*discord.Emoji, error)
Emojis(guildID discord.Snowflake) ([]discord.Emoji, error) Emojis(guildID discord.GuildID) ([]discord.Emoji, error)
Guild(id discord.Snowflake) (*discord.Guild, error) Guild(id discord.GuildID) (*discord.Guild, error)
Guilds() ([]discord.Guild, error) Guilds() ([]discord.Guild, error)
Member(guildID, userID discord.Snowflake) (*discord.Member, error) Member(guildID discord.GuildID, userID discord.UserID) (*discord.Member, error)
Members(guildID discord.Snowflake) ([]discord.Member, error) Members(guildID discord.GuildID) ([]discord.Member, error)
Message(channelID, messageID discord.Snowflake) (*discord.Message, error) Message(channelID discord.ChannelID, messageID discord.MessageID) (*discord.Message, error)
// Messages should return messages ordered from latest to earliest. // Messages should return messages ordered from latest to earliest.
Messages(channelID discord.Snowflake) ([]discord.Message, error) Messages(channelID discord.ChannelID) ([]discord.Message, error)
MaxMessages() int // used to know if the state is filled or not. MaxMessages() int // used to know if the state is filled or not.
// These don't get fetched from the API, it's Gateway only. // These don't get fetched from the API, it's Gateway only.
Presence(guildID, userID discord.Snowflake) (*discord.Presence, error) Presence(guildID discord.GuildID, userID discord.UserID) (*discord.Presence, error)
Presences(guildID discord.Snowflake) ([]discord.Presence, error) Presences(guildID discord.GuildID) ([]discord.Presence, error)
Role(guildID, roleID discord.Snowflake) (*discord.Role, error) Role(guildID discord.GuildID, roleID discord.RoleID) (*discord.Role, error)
Roles(guildID discord.Snowflake) ([]discord.Role, error) Roles(guildID discord.GuildID) ([]discord.Role, error)
VoiceState(guildID discord.Snowflake, userID discord.Snowflake) (*discord.VoiceState, error) VoiceState(guildID discord.GuildID, userID discord.UserID) (*discord.VoiceState, error)
VoiceStates(guildID discord.Snowflake) ([]discord.VoiceState, error) VoiceStates(guildID discord.GuildID) ([]discord.VoiceState, error)
} }
type StoreModifier interface { type StoreModifier interface {
@ -66,27 +66,27 @@ type StoreModifier interface {
ChannelRemove(*discord.Channel) error ChannelRemove(*discord.Channel) error
// EmojiSet should delete all old emojis before setting new ones. // EmojiSet should delete all old emojis before setting new ones.
EmojiSet(guildID discord.Snowflake, emojis []discord.Emoji) error EmojiSet(guildID discord.GuildID, emojis []discord.Emoji) error
GuildSet(*discord.Guild) error GuildSet(*discord.Guild) error
GuildRemove(id discord.Snowflake) error GuildRemove(id discord.GuildID) error
MemberSet(guildID discord.Snowflake, member *discord.Member) error MemberSet(guildID discord.GuildID, member *discord.Member) error
MemberRemove(guildID, userID discord.Snowflake) error MemberRemove(guildID discord.GuildID, userID discord.UserID) error
// MessageSet should prepend messages into the slice, the latest being in // MessageSet should prepend messages into the slice, the latest being in
// front. // front.
MessageSet(*discord.Message) error MessageSet(*discord.Message) error
MessageRemove(channelID, messageID discord.Snowflake) error MessageRemove(channelID discord.ChannelID, messageID discord.MessageID) error
PresenceSet(guildID discord.Snowflake, presence *discord.Presence) error PresenceSet(guildID discord.GuildID, presence *discord.Presence) error
PresenceRemove(guildID, userID discord.Snowflake) error PresenceRemove(guildID discord.GuildID, userID discord.UserID) error
RoleSet(guildID discord.Snowflake, role *discord.Role) error RoleSet(guildID discord.GuildID, role *discord.Role) error
RoleRemove(guildID, roleID discord.Snowflake) error RoleRemove(guildID discord.GuildID, roleID discord.RoleID) error
VoiceStateSet(guildID discord.Snowflake, voiceState *discord.VoiceState) error VoiceStateSet(guildID discord.GuildID, voiceState *discord.VoiceState) error
VoiceStateRemove(guildID discord.Snowflake, userID discord.Snowflake) error VoiceStateRemove(guildID discord.GuildID, userID discord.UserID) error
} }
// ErrStoreNotFound is an error that a store can use to return when something // ErrStoreNotFound is an error that a store can use to return when something

View File

@ -15,14 +15,14 @@ type DefaultStore struct {
self discord.User self discord.User
// includes normal and private // includes normal and private
privates map[discord.Snowflake]*discord.Channel // channelID:channel privates map[discord.ChannelID]*discord.Channel
guilds map[discord.Snowflake]*discord.Guild // guildID:guild guilds map[discord.GuildID]*discord.Guild
channels map[discord.Snowflake][]discord.Channel // guildID:channels channels map[discord.GuildID][]discord.Channel
members map[discord.Snowflake][]discord.Member // guildID:members members map[discord.GuildID][]discord.Member
presences map[discord.Snowflake][]discord.Presence // guildID:presences presences map[discord.GuildID][]discord.Presence
messages map[discord.Snowflake][]discord.Message // channelID:messages messages map[discord.ChannelID][]discord.Message
voiceStates map[discord.Snowflake][]discord.VoiceState // guildID:voiceStates voiceStates map[discord.GuildID][]discord.VoiceState
mut sync.Mutex mut sync.Mutex
} }
@ -54,14 +54,14 @@ func (s *DefaultStore) Reset() error {
s.self = discord.User{} s.self = discord.User{}
s.privates = map[discord.Snowflake]*discord.Channel{} s.privates = map[discord.ChannelID]*discord.Channel{}
s.guilds = map[discord.Snowflake]*discord.Guild{} s.guilds = map[discord.GuildID]*discord.Guild{}
s.channels = map[discord.Snowflake][]discord.Channel{} s.channels = map[discord.GuildID][]discord.Channel{}
s.members = map[discord.Snowflake][]discord.Member{} s.members = map[discord.GuildID][]discord.Member{}
s.presences = map[discord.Snowflake][]discord.Presence{} s.presences = map[discord.GuildID][]discord.Presence{}
s.messages = map[discord.Snowflake][]discord.Message{} s.messages = map[discord.ChannelID][]discord.Message{}
s.voiceStates = map[discord.Snowflake][]discord.VoiceState{} s.voiceStates = map[discord.GuildID][]discord.VoiceState{}
return nil return nil
} }
@ -89,7 +89,7 @@ func (s *DefaultStore) MyselfSet(me *discord.User) error {
//// ////
func (s *DefaultStore) Channel(id discord.Snowflake) (*discord.Channel, error) { func (s *DefaultStore) Channel(id discord.ChannelID) (*discord.Channel, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -108,7 +108,7 @@ func (s *DefaultStore) Channel(id discord.Snowflake) (*discord.Channel, error) {
return nil, ErrStoreNotFound return nil, ErrStoreNotFound
} }
func (s *DefaultStore) Channels(guildID discord.Snowflake) ([]discord.Channel, error) { func (s *DefaultStore) Channels(guildID discord.GuildID) ([]discord.Channel, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -122,7 +122,7 @@ func (s *DefaultStore) Channels(guildID discord.Snowflake) ([]discord.Channel, e
// CreatePrivateChannel searches in the cache for a private channel. It makes no // CreatePrivateChannel searches in the cache for a private channel. It makes no
// API calls. // API calls.
func (s *DefaultStore) CreatePrivateChannel(recipient discord.Snowflake) (*discord.Channel, error) { func (s *DefaultStore) CreatePrivateChannel(recipient discord.UserID) (*discord.Channel, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -205,7 +205,7 @@ func (s *DefaultStore) ChannelRemove(channel *discord.Channel) error {
//// ////
func (s *DefaultStore) Emoji(guildID, emojiID discord.Snowflake) (*discord.Emoji, error) { func (s *DefaultStore) Emoji(guildID discord.GuildID, emojiID discord.EmojiID) (*discord.Emoji, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -223,7 +223,7 @@ func (s *DefaultStore) Emoji(guildID, emojiID discord.Snowflake) (*discord.Emoji
return nil, ErrStoreNotFound return nil, ErrStoreNotFound
} }
func (s *DefaultStore) Emojis(guildID discord.Snowflake) ([]discord.Emoji, error) { func (s *DefaultStore) Emojis(guildID discord.GuildID) ([]discord.Emoji, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -235,7 +235,7 @@ func (s *DefaultStore) Emojis(guildID discord.Snowflake) ([]discord.Emoji, error
return append([]discord.Emoji{}, gd.Emojis...), nil return append([]discord.Emoji{}, gd.Emojis...), nil
} }
func (s *DefaultStore) EmojiSet(guildID discord.Snowflake, emojis []discord.Emoji) error { func (s *DefaultStore) EmojiSet(guildID discord.GuildID, emojis []discord.Emoji) error {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -269,7 +269,7 @@ Main:
//// ////
func (s *DefaultStore) Guild(id discord.Snowflake) (*discord.Guild, error) { func (s *DefaultStore) Guild(id discord.GuildID) (*discord.Guild, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -321,7 +321,7 @@ func (s *DefaultStore) GuildSet(guild *discord.Guild) error {
return nil return nil
} }
func (s *DefaultStore) GuildRemove(id discord.Snowflake) error { func (s *DefaultStore) GuildRemove(id discord.GuildID) error {
s.mut.Lock() s.mut.Lock()
delete(s.guilds, id) delete(s.guilds, id)
s.mut.Unlock() s.mut.Unlock()
@ -331,7 +331,7 @@ func (s *DefaultStore) GuildRemove(id discord.Snowflake) error {
//// ////
func (s *DefaultStore) Member(guildID, userID discord.Snowflake) (*discord.Member, error) { func (s *DefaultStore) Member(guildID discord.GuildID, userID discord.UserID) (*discord.Member, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -349,7 +349,7 @@ func (s *DefaultStore) Member(guildID, userID discord.Snowflake) (*discord.Membe
return nil, ErrStoreNotFound return nil, ErrStoreNotFound
} }
func (s *DefaultStore) Members(guildID discord.Snowflake) ([]discord.Member, error) { func (s *DefaultStore) Members(guildID discord.GuildID) ([]discord.Member, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -361,7 +361,7 @@ func (s *DefaultStore) Members(guildID discord.Snowflake) ([]discord.Member, err
return append([]discord.Member{}, ms...), nil return append([]discord.Member{}, ms...), nil
} }
func (s *DefaultStore) MemberSet(guildID discord.Snowflake, member *discord.Member) error { func (s *DefaultStore) MemberSet(guildID discord.GuildID, member *discord.Member) error {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -385,7 +385,7 @@ func (s *DefaultStore) MemberSet(guildID discord.Snowflake, member *discord.Memb
return nil return nil
} }
func (s *DefaultStore) MemberRemove(guildID, userID discord.Snowflake) error { func (s *DefaultStore) MemberRemove(guildID discord.GuildID, userID discord.UserID) error {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -409,7 +409,7 @@ func (s *DefaultStore) MemberRemove(guildID, userID discord.Snowflake) error {
//// ////
func (s *DefaultStore) Message(channelID, messageID discord.Snowflake) (*discord.Message, error) { func (s *DefaultStore) Message(channelID discord.ChannelID, messageID discord.MessageID) (*discord.Message, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -427,7 +427,7 @@ func (s *DefaultStore) Message(channelID, messageID discord.Snowflake) (*discord
return nil, ErrStoreNotFound return nil, ErrStoreNotFound
} }
func (s *DefaultStore) Messages(channelID discord.Snowflake) ([]discord.Message, error) { func (s *DefaultStore) Messages(channelID discord.ChannelID) ([]discord.Message, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -486,7 +486,7 @@ func (s *DefaultStore) MessageSet(message *discord.Message) error {
return nil return nil
} }
func (s *DefaultStore) MessageRemove(channelID, messageID discord.Snowflake) error { func (s *DefaultStore) MessageRemove(channelID discord.ChannelID, messageID discord.MessageID) error {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -508,7 +508,7 @@ func (s *DefaultStore) MessageRemove(channelID, messageID discord.Snowflake) err
//// ////
func (s *DefaultStore) Presence(guildID, userID discord.Snowflake) (*discord.Presence, error) { func (s *DefaultStore) Presence(guildID discord.GuildID, userID discord.UserID) (*discord.Presence, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -526,7 +526,7 @@ func (s *DefaultStore) Presence(guildID, userID discord.Snowflake) (*discord.Pre
return nil, ErrStoreNotFound return nil, ErrStoreNotFound
} }
func (s *DefaultStore) Presences(guildID discord.Snowflake) ([]discord.Presence, error) { func (s *DefaultStore) Presences(guildID discord.GuildID) ([]discord.Presence, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -538,7 +538,7 @@ func (s *DefaultStore) Presences(guildID discord.Snowflake) ([]discord.Presence,
return ps, nil return ps, nil
} }
func (s *DefaultStore) PresenceSet(guildID discord.Snowflake, presence *discord.Presence) error { func (s *DefaultStore) PresenceSet(guildID discord.GuildID, presence *discord.Presence) error {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -558,7 +558,7 @@ func (s *DefaultStore) PresenceSet(guildID discord.Snowflake, presence *discord.
return nil return nil
} }
func (s *DefaultStore) PresenceRemove(guildID, userID discord.Snowflake) error { func (s *DefaultStore) PresenceRemove(guildID discord.GuildID, userID discord.UserID) error {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -581,7 +581,7 @@ func (s *DefaultStore) PresenceRemove(guildID, userID discord.Snowflake) error {
//// ////
func (s *DefaultStore) Role(guildID, roleID discord.Snowflake) (*discord.Role, error) { func (s *DefaultStore) Role(guildID discord.GuildID, roleID discord.RoleID) (*discord.Role, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -599,7 +599,7 @@ func (s *DefaultStore) Role(guildID, roleID discord.Snowflake) (*discord.Role, e
return nil, ErrStoreNotFound return nil, ErrStoreNotFound
} }
func (s *DefaultStore) Roles(guildID discord.Snowflake) ([]discord.Role, error) { func (s *DefaultStore) Roles(guildID discord.GuildID) ([]discord.Role, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -611,7 +611,7 @@ func (s *DefaultStore) Roles(guildID discord.Snowflake) ([]discord.Role, error)
return append([]discord.Role{}, gd.Roles...), nil return append([]discord.Role{}, gd.Roles...), nil
} }
func (s *DefaultStore) RoleSet(guildID discord.Snowflake, role *discord.Role) error { func (s *DefaultStore) RoleSet(guildID discord.GuildID, role *discord.Role) error {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -631,7 +631,7 @@ func (s *DefaultStore) RoleSet(guildID discord.Snowflake, role *discord.Role) er
return nil return nil
} }
func (s *DefaultStore) RoleRemove(guildID, roleID discord.Snowflake) error { func (s *DefaultStore) RoleRemove(guildID discord.GuildID, roleID discord.RoleID) error {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -652,7 +652,7 @@ func (s *DefaultStore) RoleRemove(guildID, roleID discord.Snowflake) error {
//// ////
func (s *DefaultStore) VoiceState(guildID, userID discord.Snowflake) (*discord.VoiceState, error) { func (s *DefaultStore) VoiceState(guildID discord.GuildID, userID discord.UserID) (*discord.VoiceState, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -670,7 +670,7 @@ func (s *DefaultStore) VoiceState(guildID, userID discord.Snowflake) (*discord.V
return nil, ErrStoreNotFound return nil, ErrStoreNotFound
} }
func (s *DefaultStore) VoiceStates(guildID discord.Snowflake) ([]discord.VoiceState, error) { func (s *DefaultStore) VoiceStates(guildID discord.GuildID) ([]discord.VoiceState, error) {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -682,7 +682,7 @@ func (s *DefaultStore) VoiceStates(guildID discord.Snowflake) ([]discord.VoiceSt
return append([]discord.VoiceState{}, states...), nil return append([]discord.VoiceState{}, states...), nil
} }
func (s *DefaultStore) VoiceStateSet(guildID discord.Snowflake, voiceState *discord.VoiceState) error { func (s *DefaultStore) VoiceStateSet(guildID discord.GuildID, voiceState *discord.VoiceState) error {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -702,7 +702,7 @@ func (s *DefaultStore) VoiceStateSet(guildID discord.Snowflake, voiceState *disc
return nil return nil
} }
func (s *DefaultStore) VoiceStateRemove(guildID, userID discord.Snowflake) error { func (s *DefaultStore) VoiceStateRemove(guildID discord.GuildID, userID discord.UserID) error {
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()

View File

@ -27,15 +27,15 @@ func (NoopStore) MyselfSet(*discord.User) error {
return nil return nil
} }
func (NoopStore) Channel(discord.Snowflake) (*discord.Channel, error) { func (NoopStore) Channel(discord.ChannelID) (*discord.Channel, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) Channels(discord.Snowflake) ([]discord.Channel, error) { func (NoopStore) Channels(discord.GuildID) ([]discord.Channel, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) CreatePrivateChannel(discord.Snowflake) (*discord.Channel, error) { func (NoopStore) CreatePrivateChannel(discord.UserID) (*discord.Channel, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
@ -51,19 +51,19 @@ func (NoopStore) ChannelRemove(*discord.Channel) error {
return nil return nil
} }
func (NoopStore) Emoji(_, _ discord.Snowflake) (*discord.Emoji, error) { func (NoopStore) Emoji(discord.GuildID, discord.EmojiID) (*discord.Emoji, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) Emojis(discord.Snowflake) ([]discord.Emoji, error) { func (NoopStore) Emojis(discord.GuildID) ([]discord.Emoji, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) EmojiSet(discord.Snowflake, []discord.Emoji) error { func (NoopStore) EmojiSet(discord.GuildID, []discord.Emoji) error {
return nil return nil
} }
func (NoopStore) Guild(discord.Snowflake) (*discord.Guild, error) { func (NoopStore) Guild(discord.GuildID) (*discord.Guild, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
@ -75,31 +75,31 @@ func (NoopStore) GuildSet(*discord.Guild) error {
return nil return nil
} }
func (NoopStore) GuildRemove(discord.Snowflake) error { func (NoopStore) GuildRemove(discord.GuildID) error {
return nil return nil
} }
func (NoopStore) Member(_, _ discord.Snowflake) (*discord.Member, error) { func (NoopStore) Member(discord.GuildID, discord.UserID) (*discord.Member, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) Members(discord.Snowflake) ([]discord.Member, error) { func (NoopStore) Members(discord.GuildID) ([]discord.Member, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) MemberSet(discord.Snowflake, *discord.Member) error { func (NoopStore) MemberSet(discord.GuildID, *discord.Member) error {
return nil return nil
} }
func (NoopStore) MemberRemove(_, _ discord.Snowflake) error { func (NoopStore) MemberRemove(discord.GuildID, discord.UserID) error {
return nil return nil
} }
func (NoopStore) Message(_, _ discord.Snowflake) (*discord.Message, error) { func (NoopStore) Message(discord.ChannelID, discord.MessageID) (*discord.Message, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) Messages(discord.Snowflake) ([]discord.Message, error) { func (NoopStore) Messages(discord.ChannelID) ([]discord.Message, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
@ -113,54 +113,54 @@ func (NoopStore) MessageSet(*discord.Message) error {
return nil return nil
} }
func (NoopStore) MessageRemove(_, _ discord.Snowflake) error { func (NoopStore) MessageRemove(discord.ChannelID, discord.MessageID) error {
return nil return nil
} }
func (NoopStore) Presence(_, _ discord.Snowflake) (*discord.Presence, error) { func (NoopStore) Presence(discord.GuildID, discord.UserID) (*discord.Presence, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) Presences(discord.Snowflake) ([]discord.Presence, error) { func (NoopStore) Presences(discord.GuildID) ([]discord.Presence, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) PresenceSet(discord.Snowflake, *discord.Presence) error { func (NoopStore) PresenceSet(discord.GuildID, *discord.Presence) error {
return nil return nil
} }
func (NoopStore) PresenceRemove(_, _ discord.Snowflake) error { func (NoopStore) PresenceRemove(discord.GuildID, discord.UserID) error {
return nil return nil
} }
func (NoopStore) Role(_, _ discord.Snowflake) (*discord.Role, error) { func (NoopStore) Role(discord.GuildID, discord.RoleID) (*discord.Role, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) Roles(discord.Snowflake) ([]discord.Role, error) { func (NoopStore) Roles(discord.GuildID) ([]discord.Role, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) RoleSet(discord.Snowflake, *discord.Role) error { func (NoopStore) RoleSet(discord.GuildID, *discord.Role) error {
return nil return nil
} }
func (NoopStore) RoleRemove(_, _ discord.Snowflake) error { func (NoopStore) RoleRemove(discord.GuildID, discord.RoleID) error {
return nil return nil
} }
func (NoopStore) VoiceState(_, _ discord.Snowflake) (*discord.VoiceState, error) { func (NoopStore) VoiceState(discord.GuildID, discord.UserID) (*discord.VoiceState, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) VoiceStates(_ discord.Snowflake) ([]discord.VoiceState, error) { func (NoopStore) VoiceStates(discord.GuildID) ([]discord.VoiceState, error) {
return nil, ErrNotImplemented return nil, ErrNotImplemented
} }
func (NoopStore) VoiceStateSet(discord.Snowflake, *discord.VoiceState) error { func (NoopStore) VoiceStateSet(discord.GuildID, *discord.VoiceState) error {
return ErrNotImplemented return ErrNotImplemented
} }
func (NoopStore) VoiceStateRemove(_, _ discord.Snowflake) error { func (NoopStore) VoiceStateRemove(discord.GuildID, discord.UserID) error {
return ErrNotImplemented return ErrNotImplemented
} }

View File

@ -0,0 +1,51 @@
package moreatomic
import (
"sync"
"github.com/diamondburned/arikawa/discord"
)
type GuildIDSet struct {
set map[discord.GuildID]struct{}
mut sync.Mutex
}
// NewGuildIDSet creates a new GuildIDSet.
func NewGuildIDSet() *GuildIDSet {
return &GuildIDSet{
set: make(map[discord.GuildID]struct{}),
}
}
// Add adds the passed discord.GuildID to the set.
func (s *GuildIDSet) Add(flake discord.GuildID) {
s.mut.Lock()
s.set[flake] = struct{}{}
s.mut.Unlock()
}
// Contains checks whether the passed discord.GuildID is present in the set.
func (s *GuildIDSet) Contains(flake discord.GuildID) (ok bool) {
s.mut.Lock()
defer s.mut.Unlock()
_, ok = s.set[flake]
return
}
// Delete deletes the passed discord.GuildID from the set and returns true if
// the element is present. If not, Delete is a no-op and returns false.
func (s *GuildIDSet) Delete(flake discord.GuildID) bool {
s.mut.Lock()
defer s.mut.Unlock()
if _, ok := s.set[flake]; ok {
delete(s.set, flake)
return true
}
return false
}

View File

@ -20,7 +20,7 @@ import (
type testConfig struct { type testConfig struct {
BotToken string BotToken string
VoiceChID discord.Snowflake VoiceChID discord.ChannelID
} }
func mustConfig(t *testing.T) testConfig { func mustConfig(t *testing.T) testConfig {
@ -41,7 +41,7 @@ func mustConfig(t *testing.T) testConfig {
return testConfig{ return testConfig{
BotToken: token, BotToken: token,
VoiceChID: id, VoiceChID: discord.ChannelID(id),
} }
} }

View File

@ -52,7 +52,7 @@ type Session struct {
speaking bool speaking bool
} }
func NewSession(ses *session.Session, userID discord.Snowflake) *Session { func NewSession(ses *session.Session, userID discord.UserID) *Session {
return &Session{ return &Session{
session: ses, session: ses,
state: voicegateway.State{ state: voicegateway.State{
@ -109,17 +109,14 @@ func (s *Session) UpdateState(ev *gateway.VoiceStateUpdateEvent) {
} }
} }
func (s *Session) JoinChannel(gID, cID discord.Snowflake, muted, deafened bool) error { func (s *Session) JoinChannel(gID discord.GuildID, cID discord.ChannelID, muted, deafened bool) error {
ctx, cancel := context.WithTimeout(context.Background(), WSTimeout) ctx, cancel := context.WithTimeout(context.Background(), WSTimeout)
defer cancel() defer cancel()
return s.JoinChannelCtx(ctx, gID, cID, muted, deafened) return s.JoinChannelCtx(ctx, gID, cID, muted, deafened)
} }
func (s *Session) JoinChannelCtx( func (s *Session) JoinChannelCtx(ctx context.Context, gID discord.GuildID, cID discord.ChannelID, muted, deafened bool) error {
ctx context.Context,
gID, cID discord.Snowflake, muted, deafened bool) error {
// Acquire the mutex during join, locking during IO as well. // Acquire the mutex during join, locking during IO as well.
s.mut.Lock() s.mut.Lock()
defer s.mut.Unlock() defer s.mut.Unlock()
@ -140,7 +137,7 @@ func (s *Session) JoinChannelCtx(
s.speaking = false s.speaking = false
// Ensure that if `cID` is zero that it passes null to the update event. // Ensure that if `cID` is zero that it passes null to the update event.
var channelID discord.Snowflake = -1 var channelID discord.ChannelID = -1
if cID.Valid() { if cID.Valid() {
channelID = cID channelID = cID
} }
@ -278,7 +275,7 @@ func (s *Session) DisconnectCtx(ctx context.Context) error {
err := s.session.Gateway.UpdateVoiceStateCtx(ctx, gateway.UpdateVoiceStateData{ err := s.session.Gateway.UpdateVoiceStateCtx(ctx, gateway.UpdateVoiceStateData{
GuildID: s.state.GuildID, GuildID: s.state.GuildID,
ChannelID: discord.NullSnowflake, ChannelID: discord.ChannelID(discord.NullSnowflake),
SelfMute: true, SelfMute: true,
SelfDeaf: true, SelfDeaf: true,
}) })

View File

@ -29,7 +29,7 @@ type Voice struct {
// Session holds all of the active voice sessions. // Session holds all of the active voice sessions.
mapmutex sync.Mutex mapmutex sync.Mutex
sessions map[discord.Snowflake]*Session // guildID:Session sessions map[discord.GuildID]*Session
// Callbacks to remove the handlers. // Callbacks to remove the handlers.
closers []func() closers []func()
@ -53,7 +53,7 @@ func NewVoiceFromToken(token string) (*Voice, error) {
func NewVoice(s *state.State) *Voice { func NewVoice(s *state.State) *Voice {
v := &Voice{ v := &Voice{
State: s, State: s,
sessions: make(map[discord.Snowflake]*Session), sessions: make(map[discord.GuildID]*Session),
ErrorLog: defaultErrorHandler, ErrorLog: defaultErrorHandler,
} }
@ -110,7 +110,7 @@ func (v *Voice) onVoiceServerUpdate(e *gateway.VoiceServerUpdateEvent) {
} }
// GetSession gets a session for a guild with a read lock. // GetSession gets a session for a guild with a read lock.
func (v *Voice) GetSession(guildID discord.Snowflake) (*Session, bool) { func (v *Voice) GetSession(guildID discord.GuildID) (*Session, bool) {
v.mapmutex.Lock() v.mapmutex.Lock()
defer v.mapmutex.Unlock() defer v.mapmutex.Unlock()
@ -120,7 +120,7 @@ func (v *Voice) GetSession(guildID discord.Snowflake) (*Session, bool) {
} }
// RemoveSession removes a session. // RemoveSession removes a session.
func (v *Voice) RemoveSession(guildID discord.Snowflake) { func (v *Voice) RemoveSession(guildID discord.GuildID) {
v.mapmutex.Lock() v.mapmutex.Lock()
defer v.mapmutex.Unlock() defer v.mapmutex.Unlock()
@ -133,7 +133,7 @@ func (v *Voice) RemoveSession(guildID discord.Snowflake) {
} }
// JoinChannel joins the specified channel in the specified guild. // JoinChannel joins the specified channel in the specified guild.
func (v *Voice) JoinChannel(gID, cID discord.Snowflake, muted, deafened bool) (*Session, error) { func (v *Voice) JoinChannel(gID discord.GuildID, cID discord.ChannelID, muted, deafened bool) (*Session, error) {
// Get the stored voice session for the given guild. // Get the stored voice session for the given guild.
conn, ok := v.GetSession(gID) conn, ok := v.GetSession(gID)
@ -158,7 +158,7 @@ func (v *Voice) JoinChannel(gID, cID discord.Snowflake, muted, deafened bool) (*
func (v *Voice) Close() error { func (v *Voice) Close() error {
err := &CloseError{ err := &CloseError{
SessionErrors: make(map[discord.Snowflake]error), SessionErrors: make(map[discord.GuildID]error),
} }
v.mapmutex.Lock() v.mapmutex.Lock()
@ -184,7 +184,7 @@ func (v *Voice) Close() error {
} }
type CloseError struct { type CloseError struct {
SessionErrors map[discord.Snowflake]error SessionErrors map[discord.GuildID]error
StateErr error StateErr error
} }

View File

@ -19,10 +19,10 @@ var (
// OPCode 0 // OPCode 0
// https://discordapp.com/developers/docs/topics/voice-connections#establishing-a-voice-websocket-connection-example-voice-identify-payload // https://discordapp.com/developers/docs/topics/voice-connections#establishing-a-voice-websocket-connection-example-voice-identify-payload
type IdentifyData struct { type IdentifyData struct {
GuildID discord.Snowflake `json:"server_id"` // yes, this should be "server_id" GuildID discord.GuildID `json:"server_id"` // yes, this should be "server_id"
UserID discord.Snowflake `json:"user_id"` UserID discord.UserID `json:"user_id"`
SessionID string `json:"session_id"` SessionID string `json:"session_id"`
Token string `json:"token"` Token string `json:"token"`
} }
// Identify sends an Identify operation (opcode 0) to the Gateway Gateway. // Identify sends an Identify operation (opcode 0) to the Gateway Gateway.
@ -135,9 +135,9 @@ func (c *Gateway) SpeakingCtx(ctx context.Context, flag SpeakingFlag) error {
// OPCode 7 // OPCode 7
// https://discordapp.com/developers/docs/topics/voice-connections#resuming-voice-connection-example-resume-connection-payload // https://discordapp.com/developers/docs/topics/voice-connections#resuming-voice-connection-example-resume-connection-payload
type ResumeData struct { type ResumeData struct {
GuildID discord.Snowflake `json:"server_id"` // yes, this should be "server_id" GuildID discord.GuildID `json:"server_id"` // yes, this should be "server_id"
SessionID string `json:"session_id"` SessionID string `json:"session_id"`
Token string `json:"token"` Token string `json:"token"`
} }
// Resume sends a Resume operation (opcode 7) to the Gateway Gateway. // Resume sends a Resume operation (opcode 7) to the Gateway Gateway.

View File

@ -34,9 +34,9 @@ var (
// State contains state information of a voice gateway. // State contains state information of a voice gateway.
type State struct { type State struct {
GuildID discord.Snowflake GuildID discord.GuildID
ChannelID discord.Snowflake ChannelID discord.ChannelID
UserID discord.Snowflake UserID discord.UserID
SessionID string SessionID string
Token string Token string