This release contains a lot of added functionality, minor-scale rewrites,
bugfixes, documentation work, and the beginning of a rewrite to use the tokio
ecosystem.
The release was delayed due to a fairly majour bug
in rust-websocket that we have forked over to temporarily fix.
This release was lead in development by @acdenisSK.
Thanks to the following for their contributions this release:
- @acdenisSK
- @Arcterus
- @Bond-009
- @blaenk
- @hsiW
- @imnotbad
- @joek13
- @Lakelezz
- @Roughsketch
- @xentec
- @zeyla
Upgrade Path
Per commits c:af1061b, c:cdedf36, and c:aa307b1, Direct Messaging other
bot users is now disallowed by the API. To fix this, simply don't do it.
Per commit c:ebc4e51, deprecated functions were finally removed. The following
can simply have their usage renamed:
Cache::get_channel
-->Cache::channel
Cache::get_guild
-->Cache::guild
Cache::get_guild_channel
-->Cache::guild_channel
Cache::get_member
-->Cache::member
Cache::get_private_channel
-->Cache::private_channel
Cache::get_role
-->Cache::role
Cache::get_user
-->Cache::user
ChannelId::get_invites
-->ChannelId::invites
ChannelId::get_message
-->ChannelId::message
ChannelId::get_messages
-->ChannelId::messages
ChannelId::get_reaction_users
-->ChannelId::get_reaction_users
ChannelId::get_webhooks
-->ChannelId::webhooks
Channel::get_message
-->Channel::message
Channel::get_messages
-->Channel::messages
Channel::get_reaction_users
-->Channel::reaction_users
Client::login_bot
-->Client::new
Client::login
-->Client::new
Colour::get_b
-->Colour::b
Colour::get_g
-->Colour::g
Colour::get_r
-->Colour::r
Colour::get_tuple
-->Colour::tuple
CurrentUser::distinct
-->CurrentUser::tag
Group::get_message
-->Group::message
Group::get_messages
-->Group::messages
Group::get_reaction_users
-->Group::reaction_users
Guild::get_bans
-->Guild::bans
Guild::get_channels
-->Guild::channels
Guild::get_emoji
-->Guild::emoji
Guild::get_emojis
-->Guild::emojis
Guild::get_integrations
-->Guild::integrations
Guild::get_invites
-->Guild::invites
Guild::get_member
-->Guild::member
Guild::get_members
-->Guild::members
Guild::get_member_named
-->Guild::member_named
Guild::get_prune_count
-->Guild::prune_count
Guild::get_webhooks
-->Guild::webhooks
GuildId::get_bans
-->GuildId::bans
GuildId::get_channels
-->GuildId::channels
GuildId::get_emoji
-->GuildId::emoji
GuildId::get_emojis
-->GuildId::emojis
GuildId::get_integrations
-->GuildId::integrations
GuildId::get_invites
-->GuildId::invites
GuildId::get_member
-->GuildId::member
GuildId::get_members
-->GuildId::members
GuildId::get_prune_count
-->GuildId::prune_count
GuildId::get_webhooks
-->GuildId::webhooks
Message::get_reaction_users
-->Message::reaction_users
PartialGuild::get_bans
-->PartialGuild::bans
PartialGuild::get_channels
-->PartialGuild::channels
PartialGuild::get_emoji
-->PartialGuild::emoji
PartialGuild::get_emojis
-->PartialGuild::emojis
PartialGuild::get_integrations
-->PartialGuild::integrations
PartialGuild::get_invites
-->PartialGuild::invites
PartialGuild::get_member
-->PartialGuild::member
PartialGuild::get_members
-->PartialGuild::members
PartialGuild::get_prune_count
-->PartialGuild::prune_count
PartialGuild::get_webhooks
-->PartialGuild::webhooks
PrivateChannel::get_message
-->PrivateChannel::message
PrivateChannel::get_messages
-->PrivateChannel::messages
PrivateChannel::get_reaction_users
-->PrivateChannel::reaction_users
Role::edit_role
-->Role::edit
User::distinct
-->User::tag
http::send_file
has been replaced by http::send_files
. Instead of using http::send_file
like so:
use serde_json::Map;
use serenity::http;
use serenity::model::ChannelId;
use std::fs::File;
let channel_id = ChannelId(253635665344987136);
let filename = "mr-sakamoto.png";
let file = File::open(&format!("./img/{}", filename))?;
let map = Map::<String, Value>::new();
http::send_file(channel_id, file, filename, map)?;
Instead send an attachment of files, such as:
use serde_json::Map;
use serenity::http;
use serenity::model::ChannelId;
use std::fs::File;
let channel_id = ChannelId(253635665344987136);
let files = vec![
(File::open(&format!("./img/{}", filename))?, filename),
];
let map = Map::<String, Value>::new();
http::send_files(channel_id, files, map)?;
Similar logic can be applied to shortcut methods which have been removed,
namely:
Channel::send_file
(instead useChannel::send_files
)ChannelId::send_file
(instead useChannelId::send_files
)Group::send_file
(instead useGroup::send_files
)GuildChannel::send_file
(instead useGuildChannel::send_files
)PrivateChannel::send_file
(instead usePrivateChannel::send_files
)
Instead of using the now-removed Channel::delete_messages
and
Channel::delete_permission
, use the inner channel's method:
use serenity::model::{Channel, ChannelId};
let channel = ChannelId(253635665344987136).get()?;
let message_ids = vec![
MessageId(359845483356749825),
MessageId(359854838403694592),
];
if let Channel::Guild(c) = channel {
c.delete_messages(&message_ids)?;
}
Similar logic can be applied to Channel::delete_permission
.
Member::find_guild
ended up being only a shortcut to the Member::guild_id
structfield. Instead of calling the find_guild
method like
member.find_guild()
, instead access the structfield directly via
member.guild_id
.
The model::permissions::{general, text, voice}
methods have been removed, as
they ended up being shortcuts to the model::permissions::PRESET_GENERAL
,
model::permissions::PRESET_TEXT
, and model::permissions::PRESET_VOICE
constants, respectively.
Per commit c:ea432af, event handling is now done via implementing a trait.
Instead of passing functions to the client directly like:
use serenity::Client;
use std::env;
let mut client = Client::new(env::var("DISCORD_TOKEN")?);
client.on_message(|ctx, msg| {
// code
});
Instead implement the new EventHandler trait:
use serenity::client::{Client, Context, EventHandler};
use serenity::model::Message;
struct Handler;
impl EventHandler for Handler {
fn on_message(&self, ctx: Context, msg: Message) {
// code
}
}
let client = Client::new(env::var("DISCORD_TOKEN")?);
Per commit c:4f2e47f, the deprecated ext
module (which has recently only
been a series of re-exports for the cache
, framework
, and voice
modules)
was removed. Instead of using serenity::ext::cache
for example, use
serenity::cache
.
Per commit c:878684f, due to the concept of default channels being changed,
GuildId::as_channel_id
has been deprecated due to the fact that the ID of the
default channel of a guild will no longer necessarily be the same as the guild's
ID.
If you require this same exact functionality (the GuildId
as a ChannelId
),
rewrite your code from:
use serenity::model::GuildId;
let channel_id = GuildId(81384788765712384).as_channel_id();
to:
use serenity::model::{ChannelId, GuildId};
let guild_id = GuildId(81384788765712384);
let channel_id = ChannelId(guild_id.0);
Per commits c:2b053ea, c:8cc2300, c:8e29694, and c:948b27c, custom
frameworks can now be implemented, meaning that a built implementation is now
passed instead of a base framework being provided and mutated. To use the old
framework, modify code from:
use serenity::Client;
use std::env;
let mut client = Client::new(&env::var("DISCORD_TOKEN")?);
client.with_framework(|f| f
// method calls to mutate framework here
);
to the new style:
use serenity::client::{Client, EventHandler};
use serenity::framework::standard::StandardFramework;
use std::env;
struct Handler;
impl EventHandler for Handler { }
let mut client = Client::new(&env::var("DISCORD_TOKEN")?, Handler);
client.with_framework(StandardFramework::new()
// method calls here to mutate framework here
);
Per commit [c:fc9eba3d], if you were pattern matching on the
serenity::framework::DispatchError::CheckFailed
variant, instead either use or
ignore the matched data by rewriting code from:
use serenity::framework::DispatchError;
// Code to begin dispatch error handling here.
match dispatch_error {
DispatchError::CheckFailed => {
// Handle operation here.
},
// Other variants.
}
to:
// The standard implementation is now in a "standard" framework module, but
// that's unrelated.
use serenity::framework::standard::DispatchError;
match dispatch_error {
DispatchError::CheckFailed(_) => {
// Handle operation here.
},
// Other variants.
}
Per commits c:45d72ef, c:03b6d78, and c:d35d719, the framework's
command!
macro no longer parses arguments' types for you. You are now given an
Args
struct that you can retrieve arguments from and parse from to a requested
type that implements FromStr
.
For example, a simple sum function that looked like:
#[macro_use] extern crate serenity;
command!(sum(_ctx, msg, _args, x: i64, y: i64) {
let _ = msg.reply(&format!("Result: {}", x + y));
});
Now looks like:
use serenity::client::Context;
use serenity::framework::standard::Args;
use serenity::model::Message;
fn sum(_: &mut Context, msg: &Message, args: Args) -> Result<(), String> {
let x = match args.single::<i64>() {
Ok(x) => x,
Err(_) => return Ok(()),
};
let y = match args.single::<i64>() {
Ok(y) => y,
Err(_) => return Ok(()),
};
let _ = msg.reply(&format!("Result: {}", x + y));
}
Per commit c:562ce49, serenity::model::User
's FromStr
implementation can
now hit the REST API. No code changes required, but do note the possibility.
Per commit c:40031d9, the following routes have been removed for being userbot
routes, which are leftovers from when serenity supported them and had them
removed:
http::get_application_info
http::get_applications
http::get_emoji
http::get_emojis
model::Guild::emoji
model::Guild::emojis
model::GuildId::emoji
model::GuildId::emojis
model::PartialGuild::emoji
model::PartialGuild::emojis
Per commit c:092f288, bitflags has been upgraded, which introduces a minor
change in how to use permissions.
Update code from:
use serenity::model::permissions::{ADD_REACTIONS, MANAGE_MESSAGES};
foo(vec![ADD_REACTIONS, MANAGE_MESSAGES]);
to:
use serenity::model::Permissions;
foo(vec![Permissions::ADD_REACTIONS, Permissions::MANAGE_MESSAGES]);
Added
- [framework] Make
CommandOrAlias
andCommandGroup.commands
public (@joek13) c:3db42c9 - [builder] Add support for sending attachments in embeds (@acdenisSK)
c:c68d4d5 - [client] Add an
on_cached
event (@acdenisSK) c:6d6063f - [framework] Add reaction actions
- [client] Add shard shutdown shortcut to the context (@acdenisSK) c:561b0e3
- [client] Add
is_new
paramenter to theguild_create
handler (@acdenisSK)
c:3017f6d - [http, model] Add ban reasons (@acdenisSK) c:420f9bd, c:8a33329,
c:710fa02, c:421c709 - [model] Add
Guild::members_with_status
(@acdenisSK) [c:a7a0945],
c:29ee627 - [model] Make
Ban
andUser
implEq
,Hash
, andPartialEq
(@acdenisSK) c:64bfc54 - [model] Return error if user exceeds reason limit (@acdenisSK) c:60c33db,
c:25d4931 - [builder] Add method to add multiple embed fields (@acdenisSK) c:dbd6727
- [model] Make
BanOptions
take and return an&str
(@acdenisSK) c:1ab8b31 - [framework] Provide the command to checks (@acdenisSK) c:eb47559
- [model] Add
{ChannelId, GuildChannel, PrivateChannel}::name
functions
(@acdenisSK) c:ca0f113 - [client] Switch to tokio for events (@Arcterus) c:88765d0
- [client] Add method to close all shards explicitly (@acdenisSK) c:4d4e9dc,
c:c2cf691, c:c7b8ab8, c:9900b20, c:d8027d7, c:051d23d - [framework] Implement adding checks to buckets (@acdenisSK) c:dc3a4df
- [client] Handle the closing of shards (@blaenk) c:5fd3509
- [client] Make
CloseHandle
deriveCopy
(@blaenk) c:b249c82 - [model] Add
nsfw
property to channels (@acdenisSK, @Bond-009)
c:b602805, c:fd89d09, c:fd47b86 - [http, model] Add audit log support (@acdenisSK) c:6a101c4, c:4532e4a,
c:9ccf388, c:1fad3dd, c:e2053dd - [model] Add
Message::is_own
(@acdenisSK, @zeyla) c:5a96724,
c:fdbfbe0, c:6572580 - [utils] Implement
From<(u8, u8, u8)> for Colour
(@acdenisSK) c:6f147e1 - [builder, model] Make some functions accept a
Display
bound instead of
&str
(@acdenisSK) c:7e913b6, c:05162aa, c:0810ab7 - [model] Add simulated default channel methods (@acdenisSK) c:878684f
- [framework] Add support for custom delimiters (@acdenisSK) c:125c1b8,
c:fdfb184 - [framework] Provide Args to checks (@acdenisSK, @Roughsketch) c:005437f,
c:68c5be8, c:26919cf, c:25e91da, c:ab67c1d, c:caf69d6 - [model] Use cache when possible in
UserId::get
(@Roughsketch) c:bfdb57c - [utils] Add
with_config{,_mut}
(@acdenisSK) c:1a08904 - [voice] Add ability to play DCA and Opus (@Roughsketch) c:3e0b103,
c:e1a8fe3 - [model] Add `{Guild,PartialGuild}::role_by_name (@Lakelezz) c:f6fcf32
- [framework] Add
CreateCommand::num_args
(@Roughsketch) c:aace5fd - [framework] Add case insensitive command name support (@acdenisSK)
c:deee38d - [framework] Allow commands to be limited to roles (@Lakelezz) c:d925f92
- [client] Add a way for users to get shards (@zeyla) c:619a91d
- [cache, client, model] Add channel category support (@acdenisSK, @zeyla)
c:4be6b9d, c:870a2a5, c:192ac8a, c:485ad29, c:52b8e29 - [client] Add
Context::handle
(@acdenisSK) c:97e84fe - [framework] Copy some functionality from Command to Group (@Roughsketch)
c:8e1435f
Fixed
- [client] Return websocket pings with a pong (@acdenisSK) c:824f8cb,
c:e218ce0, c:e72e25c, c:bd05bda - [utils] Fix
MessageBuilder::push_mono_safe
- [framework] Fix args when
use_quotes
is active (@acdenisSK) c:e7a5ba3 - [model] Make
Reaction::name
optional (@acdenisSK) c:8f37f78 - [gateway] Fix presence updates due to API change (@Roughsketch) c:16a5828
- [model] Fix
permissions::PRESET_GENERAL
bits (@zeyla) c:9f02720 - [http] Update deprecated bulk delete endpoint (@zeyla) c:dbcb351
- [client] Fix subtraction overflow on guild cached dispatch (@Roughsketch)
c:f830f31 - [framework] Fix admin permission check (@Lakelezz) c:2fb12e2
- [general] Fix compiles of a variety of feature combinations (@zeyla)
c:8e3b4d6 - [client] Fix spawning of multiple events (non-v0.3 bug) (@zeyla) c:7c4b052
- [framework] Add Send/Sync to framework items (non-v0.3 bug) (@zeyla)
c:50d7f00
Changed
- [model] Prevent Direct Messaging other bot users (@zeyla) c:af1061b,
c:266411c - [cache, client] Apply API changes for bot DMs (@acdenisSK) c:cdedf36,
c:aa307b1 - [client] Switch to a trait-based event handler (@acdenisSK) c:ea432af
- [cache, client, http, model, utils] Remove deprecated functions (@acdenisSK)
c:ebc4e51 - [framework] Allow custom framework implementations (@acdenisSK, @zeyla)
c:2b053ea, c:8cc2300, c:8e29694, c:948b27c - [general] Remove the BC-purposed
ext
module (@acdenisSK) c:4f2e47f - [model] Deprecate
GuildId::as_channel_id
(@acdenisSK) c:878684f - [utils] Remove
I
bound for MessageBuilder language params (@acdenisSK)
c:f16af97 - [cache] Split event handling to a trait (@acdenisSK) c:eee857a,
c:32de2cb, c:bc3491c - [framework] Provide command to
DispatchError::CheckFailed
(@Lakelezz)
c:fc9eba3 - [framework] Provide arguments as an iterable struct
(@acdenisSK, @Roughsketch) c:106a4d5, c:428cbb9, c:45d72ef,
c:03b6d78, c:d35d719 - [model] Provide useful user/role/channel id
FromStr
parsing errors
(@acdenisSK) c:8bf77fa, c:8d51ead - [model] Allow
User
'sFromStr
impl to hit REST (@Roughsketch) c:562ce49 - [http] Remove remaining userbot endpoints (@zeyla) c:40031d9
- [general] Update bitflags, other dependencies (@zeyla) c:092f288
Misc.
- [model] Fix a
ModelError
doctest (@zeyla) c:bd9fcf7 - [docs] Various docs fixes (@hsiW) c:f05efce
- [docs] Update links to docs (@zeyla) c:78e7b1b
- [general] Fix clippy warnings (@imnotbad) c:e1912c2
- [docs] Update to add
EventHandler
(@acdenisSK) c:fdfd5bc - [examples] Update examples (@acdenisSK, @Roughsketch) c:3582691,
c:4e360cf - [docs] Fix doctests from
EventHandler
changes (@acdenisSK) c:511ec87 - [docs] Update readme to use correct docs link (@acdenisSK) c:0240717
- [client] Add a macro for reaction dispatching (@acdenisSK) c:4efe1d1
- [framework] Simplify an iterator usage (@acdenisSK) c:fbc1ac7
- [general] Fix clippy warnings (@imnotbad) c:b6af867
- [docs] Fix the doc on
PrivateChannel::name
(@acdenisSK) c:14fd41b - [model, voice] Use stabilized loop-with-break-value (@acdenisSK) c:f5a97d4
- [model] Change a
match
to anand_then
(@acdenisSK) c:5e5f161 - [framework] Make bucket checks less cache dependent (@acdenisSK) c:ea1eba8
- [framework] Remove unnecessary
Send + Sync
bounds (@acdenisSK) c:3c2716b - [client, framework, http, utils] Remove some clones (@acdenisSK) c:0d6965f
- [cache] Remove an unnecessary map (@acdenisSK) c:924c447
- [general] Make Travis test on osx (@Arcterus) c:fb2a1a9
- [cache] Ignore private channels on create if already cached (@acdenisSK,
@Lakelezz) c:7e8da0c, c:e5889ed, c:069df4f - [examples] Document example 05 more heavily (@Lakelezz) c:0186754
- [examples] Fix listed feature requirements in examples (@zeyla) c:078947e
- [http] Document and un-hide
http::set_token
(@zeyla) c:cb18d42 - [model] Refactor Display impl for Ids (@acdenisSK) c:47ea8f7
- [client] Add a sharding manager base (@zeyla) c:6c43fed