diff --git a/src/Discord.Net.Commands/CommandParser.cs b/src/Discord.Net.Commands/CommandParser.cs
index c77b56042..88698cda5 100644
--- a/src/Discord.Net.Commands/CommandParser.cs
+++ b/src/Discord.Net.Commands/CommandParser.cs
@@ -103,7 +103,7 @@ namespace Discord.Commands
argBuilder.Append(c);
continue;
}
-
+
if (IsOpenQuote(aliasMap, c))
{
curPart = ParserPart.QuotedParameter;
@@ -136,7 +136,7 @@ namespace Discord.Commands
else
argBuilder.Append(c);
}
-
+
if (argString != null)
{
if (curParam == null)
@@ -149,7 +149,7 @@ namespace Discord.Commands
var typeReaderResult = await curParam.ParseAsync(context, argString, services).ConfigureAwait(false);
if (!typeReaderResult.IsSuccess && typeReaderResult.Error != CommandError.MultipleMatches)
- return ParseResult.FromError(typeReaderResult);
+ return ParseResult.FromError(typeReaderResult, curParam);
if (curParam.IsMultiple)
{
@@ -172,7 +172,7 @@ namespace Discord.Commands
{
var typeReaderResult = await curParam.ParseAsync(context, argBuilder.ToString(), services).ConfigureAwait(false);
if (!typeReaderResult.IsSuccess)
- return ParseResult.FromError(typeReaderResult);
+ return ParseResult.FromError(typeReaderResult, curParam);
argList.Add(typeReaderResult);
}
@@ -180,7 +180,7 @@ namespace Discord.Commands
return ParseResult.FromError(CommandError.ParseFailed, "Input text may not end on an incomplete escape.");
if (curPart == ParserPart.QuotedParameter)
return ParseResult.FromError(CommandError.ParseFailed, "A quoted parameter is incomplete.");
-
+
//Add missing optionals
for (int i = argList.Count; i < command.Parameters.Count; i++)
{
@@ -191,7 +191,7 @@ namespace Discord.Commands
return ParseResult.FromError(CommandError.BadArgCount, "The input text has too few parameters.");
argList.Add(TypeReaderResult.FromSuccess(param.DefaultValue));
}
-
+
return ParseResult.FromSuccess(argList.ToImmutable(), paramList.ToImmutable());
}
}
diff --git a/src/Discord.Net.Commands/Results/ParseResult.cs b/src/Discord.Net.Commands/Results/ParseResult.cs
index 8e10dc66c..43351b6bf 100644
--- a/src/Discord.Net.Commands/Results/ParseResult.cs
+++ b/src/Discord.Net.Commands/Results/ParseResult.cs
@@ -18,30 +18,40 @@ namespace Discord.Commands
///
public string ErrorReason { get; }
+ ///
+ /// Provides information about the parameter that caused the parsing error.
+ ///
+ ///
+ /// A indicating the parameter info of the error that may have occurred during parsing;
+ /// null if the parsing was successful or the parsing error is not specific to a single parameter.
+ ///
+ public ParameterInfo ErrorParameter { get; }
+
///
public bool IsSuccess => !Error.HasValue;
- private ParseResult(IReadOnlyList argValues, IReadOnlyList paramValues, CommandError? error, string errorReason)
+ private ParseResult(IReadOnlyList argValues, IReadOnlyList paramValues, CommandError? error, string errorReason, ParameterInfo errorParamInfo)
{
ArgValues = argValues;
ParamValues = paramValues;
Error = error;
ErrorReason = errorReason;
+ ErrorParameter = errorParamInfo;
}
-
+
public static ParseResult FromSuccess(IReadOnlyList argValues, IReadOnlyList paramValues)
{
for (int i = 0; i < argValues.Count; i++)
{
if (argValues[i].Values.Count > 1)
- return new ParseResult(argValues, paramValues, CommandError.MultipleMatches, "Multiple matches found.");
+ return new ParseResult(argValues, paramValues, CommandError.MultipleMatches, "Multiple matches found.", null);
}
for (int i = 0; i < paramValues.Count; i++)
{
if (paramValues[i].Values.Count > 1)
- return new ParseResult(argValues, paramValues, CommandError.MultipleMatches, "Multiple matches found.");
+ return new ParseResult(argValues, paramValues, CommandError.MultipleMatches, "Multiple matches found.", null);
}
- return new ParseResult(argValues, paramValues, null, null);
+ return new ParseResult(argValues, paramValues, null, null, null);
}
public static ParseResult FromSuccess(IReadOnlyList argValues, IReadOnlyList paramValues)
{
@@ -55,15 +65,19 @@ namespace Discord.Commands
for (int i = 0; i < paramValues.Count; i++)
paramList[i] = TypeReaderResult.FromSuccess(paramValues[i]);
}
- return new ParseResult(argList, paramList, null, null);
+ return new ParseResult(argList, paramList, null, null, null);
}
public static ParseResult FromError(CommandError error, string reason)
- => new ParseResult(null, null, error, reason);
+ => new ParseResult(null, null, error, reason, null);
+ public static ParseResult FromError(CommandError error, string reason, ParameterInfo parameterInfo)
+ => new ParseResult(null, null, error, reason, parameterInfo);
public static ParseResult FromError(Exception ex)
=> FromError(CommandError.Exception, ex.Message);
public static ParseResult FromError(IResult result)
- => new ParseResult(null, null, result.Error, result.ErrorReason);
+ => new ParseResult(null, null, result.Error, result.ErrorReason, null);
+ public static ParseResult FromError(IResult result, ParameterInfo parameterInfo)
+ => new ParseResult(null, null, result.Error, result.ErrorReason, parameterInfo);
public override string ToString() => IsSuccess ? "Success" : $"{Error}: {ErrorReason}";
private string DebuggerDisplay => IsSuccess ? $"Success ({ArgValues.Count}{(ParamValues.Count > 0 ? $" +{ParamValues.Count} Values" : "")})" : $"{Error}: {ErrorReason}";
diff --git a/src/Discord.Net.Core/Entities/Permissions/ChannelPermission.cs b/src/Discord.Net.Core/Entities/Permissions/ChannelPermission.cs
index e3cfc0e19..e1f78373e 100644
--- a/src/Discord.Net.Core/Entities/Permissions/ChannelPermission.cs
+++ b/src/Discord.Net.Core/Entities/Permissions/ChannelPermission.cs
@@ -90,6 +90,10 @@ namespace Discord
///
UseVAD = 0x02_00_00_00,
PrioritySpeaker = 0x00_00_01_00,
+ ///
+ /// Allows video streaming in a voice channel.
+ ///
+ Stream = 0x00_00_02_00,
// More General
///
diff --git a/src/Discord.Net.Core/Entities/Permissions/ChannelPermissions.cs b/src/Discord.Net.Core/Entities/Permissions/ChannelPermissions.cs
index 7bef3251a..99885b070 100644
--- a/src/Discord.Net.Core/Entities/Permissions/ChannelPermissions.cs
+++ b/src/Discord.Net.Core/Entities/Permissions/ChannelPermissions.cs
@@ -13,7 +13,7 @@ namespace Discord
/// Gets a that grants all permissions for text channels.
public static readonly ChannelPermissions Text = new ChannelPermissions(0b01100_0000000_1111111110001_010001);
/// Gets a that grants all permissions for voice channels.
- public static readonly ChannelPermissions Voice = new ChannelPermissions(0b00100_1111110_0000000010100_010001);
+ public static readonly ChannelPermissions Voice = new ChannelPermissions(0b00100_1111110_0000000011100_010001);
/// Gets a that grants all permissions for category channels.
public static readonly ChannelPermissions Category = new ChannelPermissions(0b01100_1111110_1111111110001_010001);
/// Gets a that grants all permissions for direct message channels.
@@ -82,6 +82,8 @@ namespace Discord
public bool UseVAD => Permissions.GetValue(RawValue, ChannelPermission.UseVAD);
/// If true, a user may use priority speaker in a voice channel.
public bool PrioritySpeaker => Permissions.GetValue(RawValue, ChannelPermission.PrioritySpeaker);
+ /// If true, a user may stream video in a voice channel.
+ public bool Stream => Permissions.GetValue(RawValue, ChannelPermission.Stream);
/// If true, a user may adjust role permissions. This also implictly grants all other permissions.
public bool ManageRoles => Permissions.GetValue(RawValue, ChannelPermission.ManageRoles);
@@ -111,6 +113,7 @@ namespace Discord
bool? moveMembers = null,
bool? useVoiceActivation = null,
bool? prioritySpeaker = null,
+ bool? stream = null,
bool? manageRoles = null,
bool? manageWebhooks = null)
{
@@ -135,6 +138,7 @@ namespace Discord
Permissions.SetValue(ref value, moveMembers, ChannelPermission.MoveMembers);
Permissions.SetValue(ref value, useVoiceActivation, ChannelPermission.UseVAD);
Permissions.SetValue(ref value, prioritySpeaker, ChannelPermission.PrioritySpeaker);
+ Permissions.SetValue(ref value, stream, ChannelPermission.Stream);
Permissions.SetValue(ref value, manageRoles, ChannelPermission.ManageRoles);
Permissions.SetValue(ref value, manageWebhooks, ChannelPermission.ManageWebhooks);
@@ -162,11 +166,12 @@ namespace Discord
bool moveMembers = false,
bool useVoiceActivation = false,
bool prioritySpeaker = false,
+ bool stream = false,
bool manageRoles = false,
bool manageWebhooks = false)
: this(0, createInstantInvite, manageChannel, addReactions, viewChannel, sendMessages, sendTTSMessages, manageMessages,
embedLinks, attachFiles, readMessageHistory, mentionEveryone, useExternalEmojis, connect,
- speak, muteMembers, deafenMembers, moveMembers, useVoiceActivation, prioritySpeaker, manageRoles, manageWebhooks)
+ speak, muteMembers, deafenMembers, moveMembers, useVoiceActivation, prioritySpeaker, stream, manageRoles, manageWebhooks)
{ }
/// Creates a new from this one, changing the provided non-null permissions.
@@ -190,6 +195,7 @@ namespace Discord
bool? moveMembers = null,
bool? useVoiceActivation = null,
bool? prioritySpeaker = null,
+ bool? stream = null,
bool? manageRoles = null,
bool? manageWebhooks = null)
=> new ChannelPermissions(RawValue,
@@ -212,6 +218,7 @@ namespace Discord
moveMembers,
useVoiceActivation,
prioritySpeaker,
+ stream,
manageRoles,
manageWebhooks);
diff --git a/src/Discord.Net.Core/Entities/Permissions/GuildPermission.cs b/src/Discord.Net.Core/Entities/Permissions/GuildPermission.cs
index c010d90b1..3c8a5e810 100644
--- a/src/Discord.Net.Core/Entities/Permissions/GuildPermission.cs
+++ b/src/Discord.Net.Core/Entities/Permissions/GuildPermission.cs
@@ -126,6 +126,10 @@ namespace Discord
///
UseVAD = 0x02_00_00_00,
PrioritySpeaker = 0x00_00_01_00,
+ ///
+ /// Allows video streaming in a voice channel.
+ ///
+ Stream = 0x00_00_02_00,
// General 2
///
diff --git a/src/Discord.Net.Core/Entities/Permissions/GuildPermissions.cs b/src/Discord.Net.Core/Entities/Permissions/GuildPermissions.cs
index 2d2a9e56a..a5adad47c 100644
--- a/src/Discord.Net.Core/Entities/Permissions/GuildPermissions.cs
+++ b/src/Discord.Net.Core/Entities/Permissions/GuildPermissions.cs
@@ -12,7 +12,7 @@ namespace Discord
/// Gets a that grants all guild permissions for webhook users.
public static readonly GuildPermissions Webhook = new GuildPermissions(0b00000_0000000_0001101100000_000000);
/// Gets a that grants all guild permissions.
- public static readonly GuildPermissions All = new GuildPermissions(0b11111_1111110_1111111110111_111111);
+ public static readonly GuildPermissions All = new GuildPermissions(0b11111_1111110_1111111111111_111111);
/// Gets a packed value representing all the permissions in this .
public ulong RawValue { get; }
@@ -70,7 +70,9 @@ namespace Discord
/// If true, a user may use voice-activity-detection rather than push-to-talk.
public bool UseVAD => Permissions.GetValue(RawValue, GuildPermission.UseVAD);
/// If True, a user may use priority speaker in a voice channel.
- public bool PrioritySpeaker => Permissions.GetValue(RawValue, ChannelPermission.PrioritySpeaker);
+ public bool PrioritySpeaker => Permissions.GetValue(RawValue, GuildPermission.PrioritySpeaker);
+ /// If True, a user may stream video in a voice channel.
+ public bool Stream => Permissions.GetValue(RawValue, GuildPermission.Stream);
/// If true, a user may change their own nickname.
public bool ChangeNickname => Permissions.GetValue(RawValue, GuildPermission.ChangeNickname);
@@ -111,6 +113,7 @@ namespace Discord
bool? moveMembers = null,
bool? useVoiceActivation = null,
bool? prioritySpeaker = null,
+ bool? stream = null,
bool? changeNickname = null,
bool? manageNicknames = null,
bool? manageRoles = null,
@@ -143,6 +146,7 @@ namespace Discord
Permissions.SetValue(ref value, moveMembers, GuildPermission.MoveMembers);
Permissions.SetValue(ref value, useVoiceActivation, GuildPermission.UseVAD);
Permissions.SetValue(ref value, prioritySpeaker, GuildPermission.PrioritySpeaker);
+ Permissions.SetValue(ref value, stream, GuildPermission.Stream);
Permissions.SetValue(ref value, changeNickname, GuildPermission.ChangeNickname);
Permissions.SetValue(ref value, manageNicknames, GuildPermission.ManageNicknames);
Permissions.SetValue(ref value, manageRoles, GuildPermission.ManageRoles);
@@ -178,6 +182,7 @@ namespace Discord
bool moveMembers = false,
bool useVoiceActivation = false,
bool prioritySpeaker = false,
+ bool stream = false,
bool changeNickname = false,
bool manageNicknames = false,
bool manageRoles = false,
@@ -209,6 +214,7 @@ namespace Discord
moveMembers: moveMembers,
useVoiceActivation: useVoiceActivation,
prioritySpeaker: prioritySpeaker,
+ stream: stream,
changeNickname: changeNickname,
manageNicknames: manageNicknames,
manageWebhooks: manageWebhooks,
@@ -241,6 +247,7 @@ namespace Discord
bool? moveMembers = null,
bool? useVoiceActivation = null,
bool? prioritySpeaker = null,
+ bool? stream = null,
bool? changeNickname = null,
bool? manageNicknames = null,
bool? manageRoles = null,
@@ -249,7 +256,7 @@ namespace Discord
=> new GuildPermissions(RawValue, createInstantInvite, kickMembers, banMembers, administrator, manageChannels, manageGuild, addReactions,
viewAuditLog, viewChannel, sendMessages, sendTTSMessages, manageMessages, embedLinks, attachFiles,
readMessageHistory, mentionEveryone, useExternalEmojis, connect, speak, muteMembers, deafenMembers, moveMembers,
- useVoiceActivation, prioritySpeaker, changeNickname, manageNicknames, manageRoles, manageWebhooks, manageEmojis);
+ useVoiceActivation, prioritySpeaker, stream, changeNickname, manageNicknames, manageRoles, manageWebhooks, manageEmojis);
///
/// Returns a value that indicates if a specific is enabled
diff --git a/src/Discord.Net.Core/Utils/TokenUtils.cs b/src/Discord.Net.Core/Utils/TokenUtils.cs
index 2efb1822a..c3dd39237 100644
--- a/src/Discord.Net.Core/Utils/TokenUtils.cs
+++ b/src/Discord.Net.Core/Utils/TokenUtils.cs
@@ -1,4 +1,5 @@
using System;
+using System.Globalization;
using System.Text;
namespace Discord
@@ -76,7 +77,7 @@ namespace Discord
var bytes = Convert.FromBase64String(encoded);
var idStr = Encoding.UTF8.GetString(bytes);
// try to parse a ulong from the resulting string
- if (ulong.TryParse(idStr, out var id))
+ if (ulong.TryParse(idStr, NumberStyles.None, CultureInfo.InvariantCulture, out var id))
return id;
}
catch (DecoderFallbackException)
diff --git a/src/Discord.Net.Rest/DiscordRestApiClient.cs b/src/Discord.Net.Rest/DiscordRestApiClient.cs
index 30fc39000..8f3a47368 100644
--- a/src/Discord.Net.Rest/DiscordRestApiClient.cs
+++ b/src/Discord.Net.Rest/DiscordRestApiClient.cs
@@ -1492,7 +1492,7 @@ namespace Discord.API
builder.Append(format, lastIndex, leftIndex - lastIndex);
int rightIndex = format.IndexOf("}", leftIndex);
- int argId = int.Parse(format.Substring(leftIndex + 1, rightIndex - leftIndex - 1));
+ int argId = int.Parse(format.Substring(leftIndex + 1, rightIndex - leftIndex - 1), NumberStyles.None, CultureInfo.InvariantCulture);
string fieldName = GetFieldName(methodArgs[argId + 1]);
var mappedId = BucketIds.GetIndex(fieldName);
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelCreateAuditLogData.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelCreateAuditLogData.cs
index a692829f4..f432b4ca5 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelCreateAuditLogData.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelCreateAuditLogData.cs
@@ -11,11 +11,14 @@ namespace Discord.Rest
///
public class ChannelCreateAuditLogData : IAuditLogData
{
- private ChannelCreateAuditLogData(ulong id, string name, ChannelType type, IReadOnlyCollection overwrites)
+ private ChannelCreateAuditLogData(ulong id, string name, ChannelType type, int? rateLimit, bool? nsfw, int? bitrate, IReadOnlyCollection overwrites)
{
ChannelId = id;
ChannelName = name;
ChannelType = type;
+ SlowModeInterval = rateLimit;
+ IsNsfw = nsfw;
+ Bitrate = bitrate;
Overwrites = overwrites;
}
@@ -27,9 +30,15 @@ namespace Discord.Rest
var overwritesModel = changes.FirstOrDefault(x => x.ChangedProperty == "permission_overwrites");
var typeModel = changes.FirstOrDefault(x => x.ChangedProperty == "type");
var nameModel = changes.FirstOrDefault(x => x.ChangedProperty == "name");
+ var rateLimitPerUserModel = changes.FirstOrDefault(x => x.ChangedProperty == "rate_limit_per_user");
+ var nsfwModel = changes.FirstOrDefault(x => x.ChangedProperty == "nsfw");
+ var bitrateModel = changes.FirstOrDefault(x => x.ChangedProperty == "bitrate");
var type = typeModel.NewValue.ToObject(discord.ApiClient.Serializer);
var name = nameModel.NewValue.ToObject(discord.ApiClient.Serializer);
+ int? rateLimitPerUser = rateLimitPerUserModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
+ bool? nsfw = nsfwModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
+ int? bitrate = bitrateModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
foreach (var overwrite in overwritesModel.NewValue)
{
@@ -41,7 +50,7 @@ namespace Discord.Rest
overwrites.Add(new Overwrite(id, permType, new OverwritePermissions(allow, deny)));
}
- return new ChannelCreateAuditLogData(entry.TargetId.Value, name, type, overwrites.ToReadOnlyCollection());
+ return new ChannelCreateAuditLogData(entry.TargetId.Value, name, type, rateLimitPerUser, nsfw, bitrate, overwrites.ToReadOnlyCollection());
}
///
@@ -66,6 +75,32 @@ namespace Discord.Rest
///
public ChannelType ChannelType { get; }
///
+ /// Gets the current slow-mode delay of the created channel.
+ ///
+ ///
+ /// An representing the time in seconds required before the user can send another
+ /// message; 0 if disabled.
+ /// null if this is not mentioned in this entry.
+ ///
+ public int? SlowModeInterval { get; }
+ ///
+ /// Gets the value that indicates whether the created channel is NSFW.
+ ///
+ ///
+ /// true if the created channel has the NSFW flag enabled; otherwise false.
+ /// null if this is not mentioned in this entry.
+ ///
+ public bool? IsNsfw { get; }
+ ///
+ /// Gets the bit-rate that the clients in the created voice channel are requested to use.
+ ///
+ ///
+ /// An representing the bit-rate (bps) that the created voice channel defines and requests the
+ /// client(s) to use.
+ /// null if this is not mentioned in this entry.
+ ///
+ public int? Bitrate { get; }
+ ///
/// Gets a collection of permission overwrites that was assigned to the created channel.
///
///
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelDeleteAuditLogData.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelDeleteAuditLogData.cs
index d09b658cf..390749929 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelDeleteAuditLogData.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelDeleteAuditLogData.cs
@@ -11,11 +11,14 @@ namespace Discord.Rest
///
public class ChannelDeleteAuditLogData : IAuditLogData
{
- private ChannelDeleteAuditLogData(ulong id, string name, ChannelType type, IReadOnlyCollection overwrites)
+ private ChannelDeleteAuditLogData(ulong id, string name, ChannelType type, int? rateLimit, bool? nsfw, int? bitrate, IReadOnlyCollection overwrites)
{
ChannelId = id;
ChannelName = name;
ChannelType = type;
+ SlowModeInterval = rateLimit;
+ IsNsfw = nsfw;
+ Bitrate = bitrate;
Overwrites = overwrites;
}
@@ -26,15 +29,21 @@ namespace Discord.Rest
var overwritesModel = changes.FirstOrDefault(x => x.ChangedProperty == "permission_overwrites");
var typeModel = changes.FirstOrDefault(x => x.ChangedProperty == "type");
var nameModel = changes.FirstOrDefault(x => x.ChangedProperty == "name");
+ var rateLimitPerUserModel = changes.FirstOrDefault(x => x.ChangedProperty == "rate_limit_per_user");
+ var nsfwModel = changes.FirstOrDefault(x => x.ChangedProperty == "nsfw");
+ var bitrateModel = changes.FirstOrDefault(x => x.ChangedProperty == "bitrate");
var overwrites = overwritesModel.OldValue.ToObject(discord.ApiClient.Serializer)
.Select(x => new Overwrite(x.TargetId, x.TargetType, new OverwritePermissions(x.Allow, x.Deny)))
.ToList();
var type = typeModel.OldValue.ToObject(discord.ApiClient.Serializer);
var name = nameModel.OldValue.ToObject(discord.ApiClient.Serializer);
+ int? rateLimitPerUser = rateLimitPerUserModel?.OldValue?.ToObject(discord.ApiClient.Serializer);
+ bool? nsfw = nsfwModel?.OldValue?.ToObject(discord.ApiClient.Serializer);
+ int? bitrate = bitrateModel?.OldValue?.ToObject(discord.ApiClient.Serializer);
var id = entry.TargetId.Value;
- return new ChannelDeleteAuditLogData(id, name, type, overwrites.ToReadOnlyCollection());
+ return new ChannelDeleteAuditLogData(id, name, type, rateLimitPerUser, nsfw, bitrate, overwrites.ToReadOnlyCollection());
}
///
@@ -59,6 +68,31 @@ namespace Discord.Rest
///
public ChannelType ChannelType { get; }
///
+ /// Gets the slow-mode delay of the deleted channel.
+ ///
+ ///
+ /// An representing the time in seconds required before the user can send another
+ /// message; 0 if disabled.
+ /// null if this is not mentioned in this entry.
+ ///
+ public int? SlowModeInterval { get; }
+ ///
+ /// Gets the value that indicates whether the deleted channel was NSFW.
+ ///
+ ///
+ /// true if this channel had the NSFW flag enabled; otherwise false.
+ /// null if this is not mentioned in this entry.
+ ///
+ public bool? IsNsfw { get; }
+ ///
+ /// Gets the bit-rate of this channel if applicable.
+ ///
+ ///
+ /// An representing the bit-rate set of the voice channel.
+ /// null if this is not mentioned in this entry.
+ ///
+ public int? Bitrate { get; }
+ ///
/// Gets a collection of permission overwrites that was assigned to the deleted channel.
///
///
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelInfo.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelInfo.cs
index 6382e8250..d6d2fb4b3 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelInfo.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelInfo.cs
@@ -5,12 +5,13 @@ namespace Discord.Rest
///
public struct ChannelInfo
{
- internal ChannelInfo(string name, string topic, int? bitrate, int? limit)
+ internal ChannelInfo(string name, string topic, int? rateLimit, bool? nsfw, int? bitrate)
{
Name = name;
Topic = topic;
+ SlowModeInterval = rateLimit;
+ IsNsfw = nsfw;
Bitrate = bitrate;
- UserLimit = limit;
}
///
@@ -28,20 +29,29 @@ namespace Discord.Rest
///
public string Topic { get; }
///
- /// Gets the bit-rate of this channel if applicable.
+ /// Gets the current slow-mode delay of this channel.
///
///
- /// An representing the bit-rate set for the voice channel; null if not
- /// applicable.
+ /// An representing the time in seconds required before the user can send another
+ /// message; 0 if disabled.
+ /// null if this is not mentioned in this entry.
///
- public int? Bitrate { get; }
+ public int? SlowModeInterval { get; }
+ ///
+ /// Gets the value that indicates whether this channel is NSFW.
+ ///
+ ///
+ /// true if this channel has the NSFW flag enabled; otherwise false.
+ /// null if this is not mentioned in this entry.
+ ///
+ public bool? IsNsfw { get; }
///
- /// Gets the number of users allowed to be in this channel if applicable.
+ /// Gets the bit-rate of this channel if applicable.
///
///
- /// An representing the number of users allowed to be in this voice channel;
- /// null if not applicable.
+ /// An representing the bit-rate set for the voice channel;
+ /// null if this is not mentioned in this entry.
///
- public int? UserLimit { get; }
+ public int? Bitrate { get; }
}
}
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelUpdateAuditLogData.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelUpdateAuditLogData.cs
index f37404906..fa5233145 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelUpdateAuditLogData.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/ChannelUpdateAuditLogData.cs
@@ -23,20 +23,23 @@ namespace Discord.Rest
var nameModel = changes.FirstOrDefault(x => x.ChangedProperty == "name");
var topicModel = changes.FirstOrDefault(x => x.ChangedProperty == "topic");
+ var rateLimitPerUserModel = changes.FirstOrDefault(x => x.ChangedProperty == "rate_limit_per_user");
+ var nsfwModel = changes.FirstOrDefault(x => x.ChangedProperty == "nsfw");
var bitrateModel = changes.FirstOrDefault(x => x.ChangedProperty == "bitrate");
- var userLimitModel = changes.FirstOrDefault(x => x.ChangedProperty == "user_limit");
string oldName = nameModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
newName = nameModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
string oldTopic = topicModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
newTopic = topicModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
+ int? oldRateLimitPerUser = rateLimitPerUserModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
+ newRateLimitPerUser = rateLimitPerUserModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
+ bool? oldNsfw = nsfwModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
+ newNsfw = nsfwModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
int? oldBitrate = bitrateModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
newBitrate = bitrateModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
- int? oldLimit = userLimitModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
- newLimit = userLimitModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
- var before = new ChannelInfo(oldName, oldTopic, oldBitrate, oldLimit);
- var after = new ChannelInfo(newName, newTopic, newBitrate, newLimit);
+ var before = new ChannelInfo(oldName, oldTopic, oldRateLimitPerUser, oldNsfw, oldBitrate);
+ var after = new ChannelInfo(newName, newTopic, newRateLimitPerUser, newNsfw, newBitrate);
return new ChannelUpdateAuditLogData(entry.TargetId.Value, before, after);
}
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/GuildInfo.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/GuildInfo.cs
index df63251d8..85c7ac438 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/GuildInfo.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/GuildInfo.cs
@@ -7,7 +7,8 @@ namespace Discord.Rest
{
internal GuildInfo(int? afkTimeout, DefaultMessageNotifications? defaultNotifs,
ulong? afkChannel, string name, string region, string icon,
- VerificationLevel? verification, IUser owner, MfaLevel? mfa, int? filter)
+ VerificationLevel? verification, IUser owner, MfaLevel? mfa, ExplicitContentFilterLevel? filter,
+ ulong? systemChannel, ulong? widgetChannel, bool? widget)
{
AfkTimeout = afkTimeout;
DefaultMessageNotifications = defaultNotifs;
@@ -18,7 +19,10 @@ namespace Discord.Rest
VerificationLevel = verification;
Owner = owner;
MfaLevel = mfa;
- ContentFilterLevel = filter;
+ ExplicitContentFilter = filter;
+ SystemChannelId = systemChannel;
+ EmbedChannelId = widgetChannel;
+ IsEmbeddable = widget;
}
///
@@ -28,11 +32,16 @@ namespace Discord.Rest
///
/// An representing the amount of time in seconds for a user to be marked as inactive
/// and moved into the AFK voice channel.
+ /// null if this is not mentioned in this entry.
///
public int? AfkTimeout { get; }
///
/// Gets the default message notifications for users who haven't explicitly set their notification settings.
///
+ ///
+ /// The default message notifications setting of this guild.
+ /// null if this is not mentioned in this entry.
+ ///
public DefaultMessageNotifications? DefaultMessageNotifications { get; }
///
/// Gets the ID of the AFK voice channel for this guild.
@@ -65,6 +74,7 @@ namespace Discord.Rest
///
///
/// The level of requirements.
+ /// null if this is not mentioned in this entry.
///
public VerificationLevel? VerificationLevel { get; }
///
@@ -80,8 +90,39 @@ namespace Discord.Rest
///
///
/// The level of MFA requirement.
+ /// null if this is not mentioned in this entry.
///
public MfaLevel? MfaLevel { get; }
- public int? ContentFilterLevel { get; }
+ ///
+ /// Gets the level of content filtering applied to user's content in a Guild.
+ ///
+ ///
+ /// The level of explicit content filtering.
+ ///
+ public ExplicitContentFilterLevel? ExplicitContentFilter { get; }
+ ///
+ /// Gets the ID of the channel where system messages are sent.
+ ///
+ ///
+ /// A representing the snowflake identifier of the channel where system
+ /// messages are sent; null if none is set.
+ ///
+ public ulong? SystemChannelId { get; }
+ ///
+ /// Gets the ID of the widget embed channel of this guild.
+ ///
+ ///
+ /// A representing the snowflake identifier of the embedded channel found within the
+ /// widget settings of this guild; null if none is set.
+ ///
+ public ulong? EmbedChannelId { get; }
+ ///
+ /// Gets a value that indicates whether this guild is embeddable (i.e. can use widget).
+ ///
+ ///
+ /// true if this guild can be embedded via widgets; otherwise false.
+ /// null if this is not mentioned in this entry.
+ ///
+ public bool? IsEmbeddable { get; }
}
}
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/GuildUpdateAuditLogData.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/GuildUpdateAuditLogData.cs
index 853fa4b4a..80b719a6d 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/GuildUpdateAuditLogData.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/GuildUpdateAuditLogData.cs
@@ -30,6 +30,9 @@ namespace Discord.Rest
var ownerIdModel = changes.FirstOrDefault(x => x.ChangedProperty == "owner_id");
var mfaLevelModel = changes.FirstOrDefault(x => x.ChangedProperty == "mfa_level");
var contentFilterModel = changes.FirstOrDefault(x => x.ChangedProperty == "explicit_content_filter");
+ var systemChannelIdModel = changes.FirstOrDefault(x => x.ChangedProperty == "system_channel_id");
+ var widgetChannelIdModel = changes.FirstOrDefault(x => x.ChangedProperty == "widget_channel_id");
+ var widgetEnabledModel = changes.FirstOrDefault(x => x.ChangedProperty == "widget_enabled");
int? oldAfkTimeout = afkTimeoutModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
newAfkTimeout = afkTimeoutModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
@@ -49,8 +52,14 @@ namespace Discord.Rest
newOwnerId = ownerIdModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
MfaLevel? oldMfaLevel = mfaLevelModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
newMfaLevel = mfaLevelModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
- int? oldContentFilter = contentFilterModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
- newContentFilter = contentFilterModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
+ ExplicitContentFilterLevel? oldContentFilter = contentFilterModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
+ newContentFilter = contentFilterModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
+ ulong? oldSystemChannelId = systemChannelIdModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
+ newSystemChannelId = systemChannelIdModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
+ ulong? oldWidgetChannelId = widgetChannelIdModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
+ newWidgetChannelId = widgetChannelIdModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
+ bool? oldWidgetEnabled = widgetEnabledModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
+ newWidgetEnabled = widgetEnabledModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
IUser oldOwner = null;
if (oldOwnerId != null)
@@ -68,10 +77,10 @@ namespace Discord.Rest
var before = new GuildInfo(oldAfkTimeout, oldDefaultMessageNotifications,
oldAfkChannelId, oldName, oldRegionId, oldIconHash, oldVerificationLevel, oldOwner,
- oldMfaLevel, oldContentFilter);
+ oldMfaLevel, oldContentFilter, oldSystemChannelId, oldWidgetChannelId, oldWidgetEnabled);
var after = new GuildInfo(newAfkTimeout, newDefaultMessageNotifications,
newAfkChannelId, newName, newRegionId, newIconHash, newVerificationLevel, newOwner,
- newMfaLevel, newContentFilter);
+ newMfaLevel, newContentFilter, newSystemChannelId, newWidgetChannelId, newWidgetEnabled);
return new GuildUpdateAuditLogData(before, after);
}
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/MemberInfo.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/MemberInfo.cs
index b0a1a8e5a..ffa316faa 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/MemberInfo.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/MemberInfo.cs
@@ -1,18 +1,41 @@
namespace Discord.Rest
{
+ ///
+ /// Represents information for a member.
+ ///
public struct MemberInfo
{
- internal MemberInfo(string nick, bool? deaf, bool? mute, string avatar_hash)
+ internal MemberInfo(string nick, bool? deaf, bool? mute)
{
Nickname = nick;
Deaf = deaf;
Mute = mute;
- AvatarHash = avatar_hash;
}
+ ///
+ /// Gets the nickname of the updated member.
+ ///
+ ///
+ /// A string representing the nickname of the updated member; null if none is set.
+ ///
public string Nickname { get; }
+ ///
+ /// Gets a value that indicates whether the updated member is deafened by the guild.
+ ///
+ ///
+ /// true if the updated member is deafened (i.e. not permitted to listen to or speak to others) by the guild;
+ /// otherwise false.
+ /// null if this is not mentioned in this entry.
+ ///
public bool? Deaf { get; }
+ ///
+ /// Gets a value that indicates whether the updated member is muted (i.e. not permitted to speak via voice) by the
+ /// guild.
+ ///
+ ///
+ /// true if the updated member is muted by the guild; otherwise false.
+ /// null if this is not mentioned in this entry.
+ ///
public bool? Mute { get; }
- public string AvatarHash { get; }
}
}
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/MemberUpdateAuditLogData.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/MemberUpdateAuditLogData.cs
index 238c79843..f22b83e4c 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/MemberUpdateAuditLogData.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/MemberUpdateAuditLogData.cs
@@ -24,7 +24,6 @@ namespace Discord.Rest
var nickModel = changes.FirstOrDefault(x => x.ChangedProperty == "nick");
var deafModel = changes.FirstOrDefault(x => x.ChangedProperty == "deaf");
var muteModel = changes.FirstOrDefault(x => x.ChangedProperty == "mute");
- var avatarModel = changes.FirstOrDefault(x => x.ChangedProperty == "avatar_hash");
string oldNick = nickModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
newNick = nickModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
@@ -32,14 +31,12 @@ namespace Discord.Rest
newDeaf = deafModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
bool? oldMute = muteModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
newMute = muteModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
- string oldAvatar = avatarModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
- newAvatar = avatarModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
var targetInfo = log.Users.FirstOrDefault(x => x.Id == entry.TargetId);
var user = RestUser.Create(discord, targetInfo);
- var before = new MemberInfo(oldNick, oldDeaf, oldMute, oldAvatar);
- var after = new MemberInfo(newNick, newDeaf, newMute, newAvatar);
+ var before = new MemberInfo(oldNick, oldDeaf, oldMute);
+ var after = new MemberInfo(newNick, newDeaf, newMute);
return new MemberUpdateAuditLogData(user, before, after);
}
@@ -51,7 +48,19 @@ namespace Discord.Rest
/// A user object representing the user who the changes were performed on.
///
public IUser Target { get; }
+ ///
+ /// Gets the member information before the changes.
+ ///
+ ///
+ /// An information object containing the original member information before the changes were made.
+ ///
public MemberInfo Before { get; }
+ ///
+ /// Gets the member information after the changes.
+ ///
+ ///
+ /// An information object containing the member information after the changes were made.
+ ///
public MemberInfo After { get; }
}
}
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteCreateAuditLogData.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteCreateAuditLogData.cs
index a9ccd4db3..3f391187d 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteCreateAuditLogData.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteCreateAuditLogData.cs
@@ -10,8 +10,9 @@ namespace Discord.Rest
///
public class OverwriteCreateAuditLogData : IAuditLogData
{
- private OverwriteCreateAuditLogData(Overwrite overwrite)
+ private OverwriteCreateAuditLogData(ulong channelId, Overwrite overwrite)
{
+ ChannelId = channelId;
Overwrite = overwrite;
}
@@ -30,10 +31,18 @@ namespace Discord.Rest
var id = entry.Options.OverwriteTargetId.Value;
var type = entry.Options.OverwriteType;
- return new OverwriteCreateAuditLogData(new Overwrite(id, type, permissions));
+ return new OverwriteCreateAuditLogData(entry.TargetId.Value, new Overwrite(id, type, permissions));
}
///
+ /// Gets the ID of the channel that the overwrite was created from.
+ ///
+ ///
+ /// A representing the snowflake identifier for the channel that the overwrite was
+ /// created from.
+ ///
+ public ulong ChannelId { get; }
+ ///
/// Gets the permission overwrite object that was created.
///
///
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteDeleteAuditLogData.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteDeleteAuditLogData.cs
index 1e51fa5e3..a193e76ce 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteDeleteAuditLogData.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteDeleteAuditLogData.cs
@@ -10,8 +10,9 @@ namespace Discord.Rest
///
public class OverwriteDeleteAuditLogData : IAuditLogData
{
- private OverwriteDeleteAuditLogData(Overwrite deletedOverwrite)
+ private OverwriteDeleteAuditLogData(ulong channelId, Overwrite deletedOverwrite)
{
+ ChannelId = channelId;
Overwrite = deletedOverwrite;
}
@@ -29,10 +30,18 @@ namespace Discord.Rest
var id = idModel.OldValue.ToObject(discord.ApiClient.Serializer);
var allow = allowModel.OldValue.ToObject(discord.ApiClient.Serializer);
- return new OverwriteDeleteAuditLogData(new Overwrite(id, type, new OverwritePermissions(allow, deny)));
+ return new OverwriteDeleteAuditLogData(entry.TargetId.Value, new Overwrite(id, type, new OverwritePermissions(allow, deny)));
}
///
+ /// Gets the ID of the channel that the overwrite was deleted from.
+ ///
+ ///
+ /// A representing the snowflake identifier for the channel that the overwrite was
+ /// deleted from.
+ ///
+ public ulong ChannelId { get; }
+ ///
/// Gets the permission overwrite object that was deleted.
///
///
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteUpdateAuditLogData.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteUpdateAuditLogData.cs
index ac67c85cf..c2b8d423e 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteUpdateAuditLogData.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/OverwriteUpdateAuditLogData.cs
@@ -10,8 +10,9 @@ namespace Discord.Rest
///
public class OverwriteUpdateAuditLogData : IAuditLogData
{
- private OverwriteUpdateAuditLogData(OverwritePermissions before, OverwritePermissions after, ulong targetId, PermissionTarget targetType)
+ private OverwriteUpdateAuditLogData(ulong channelId, OverwritePermissions before, OverwritePermissions after, ulong targetId, PermissionTarget targetType)
{
+ ChannelId = channelId;
OldPermissions = before;
NewPermissions = after;
OverwriteTargetId = targetId;
@@ -28,17 +29,25 @@ namespace Discord.Rest
var beforeAllow = allowModel?.OldValue?.ToObject(discord.ApiClient.Serializer);
var afterAllow = allowModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
var beforeDeny = denyModel?.OldValue?.ToObject(discord.ApiClient.Serializer);
- var afterDeny = denyModel?.OldValue?.ToObject(discord.ApiClient.Serializer);
+ var afterDeny = denyModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
var beforePermissions = new OverwritePermissions(beforeAllow ?? 0, beforeDeny ?? 0);
var afterPermissions = new OverwritePermissions(afterAllow ?? 0, afterDeny ?? 0);
var type = entry.Options.OverwriteType;
- return new OverwriteUpdateAuditLogData(beforePermissions, afterPermissions, entry.Options.OverwriteTargetId.Value, type);
+ return new OverwriteUpdateAuditLogData(entry.TargetId.Value, beforePermissions, afterPermissions, entry.Options.OverwriteTargetId.Value, type);
}
///
+ /// Gets the ID of the channel that the overwrite was updated from.
+ ///
+ ///
+ /// A representing the snowflake identifier for the channel that the overwrite was
+ /// updated from.
+ ///
+ public ulong ChannelId { get; }
+ ///
/// Gets the overwrite permissions before the changes.
///
///
diff --git a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/RoleUpdateAuditLogData.cs b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/RoleUpdateAuditLogData.cs
index f98fc3e23..094e1e0e0 100644
--- a/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/RoleUpdateAuditLogData.cs
+++ b/src/Discord.Net.Rest/Entities/AuditLogs/DataTypes/RoleUpdateAuditLogData.cs
@@ -36,7 +36,7 @@ namespace Discord.Rest
string oldName = nameModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
newName = nameModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
ulong? oldPermissionsRaw = permissionsModel?.OldValue?.ToObject(discord.ApiClient.Serializer),
- newPermissionsRaw = permissionsModel?.OldValue?.ToObject(discord.ApiClient.Serializer);
+ newPermissionsRaw = permissionsModel?.NewValue?.ToObject(discord.ApiClient.Serializer);
Color? oldColor = null,
newColor = null;
diff --git a/src/Discord.Net.Rest/Entities/Users/RestUser.cs b/src/Discord.Net.Rest/Entities/Users/RestUser.cs
index 37385fb7e..d5fffca94 100644
--- a/src/Discord.Net.Rest/Entities/Users/RestUser.cs
+++ b/src/Discord.Net.Rest/Entities/Users/RestUser.cs
@@ -1,6 +1,7 @@
using System;
using System.Collections.Immutable;
using System.Diagnostics;
+using System.Globalization;
using System.Threading.Tasks;
using Model = Discord.API.User;
@@ -57,7 +58,7 @@ namespace Discord.Rest
if (model.Avatar.IsSpecified)
AvatarId = model.Avatar.Value;
if (model.Discriminator.IsSpecified)
- DiscriminatorValue = ushort.Parse(model.Discriminator.Value);
+ DiscriminatorValue = ushort.Parse(model.Discriminator.Value, NumberStyles.None, CultureInfo.InvariantCulture);
if (model.Bot.IsSpecified)
IsBot = model.Bot.Value;
if (model.Username.IsSpecified)
diff --git a/src/Discord.Net.Rest/Net/Converters/UInt64EntityOrIdConverter.cs b/src/Discord.Net.Rest/Net/Converters/UInt64EntityOrIdConverter.cs
index ae8cf2cb2..e55534833 100644
--- a/src/Discord.Net.Rest/Net/Converters/UInt64EntityOrIdConverter.cs
+++ b/src/Discord.Net.Rest/Net/Converters/UInt64EntityOrIdConverter.cs
@@ -1,6 +1,7 @@
-using Discord.API;
+using Discord.API;
using Newtonsoft.Json;
using System;
+using System.Globalization;
namespace Discord.Net.Converters
{
@@ -23,7 +24,7 @@ namespace Discord.Net.Converters
{
case JsonToken.String:
case JsonToken.Integer:
- return new EntityOrId(ulong.Parse(reader.ReadAsString()));
+ return new EntityOrId(ulong.Parse(reader.ReadAsString(), NumberStyles.None, CultureInfo.InvariantCulture));
default:
T obj;
if (_innerConverter != null)
diff --git a/src/Discord.Net.Rest/Net/RateLimitInfo.cs b/src/Discord.Net.Rest/Net/RateLimitInfo.cs
index 5722b50f2..13e9e39a7 100644
--- a/src/Discord.Net.Rest/Net/RateLimitInfo.cs
+++ b/src/Discord.Net.Rest/Net/RateLimitInfo.cs
@@ -11,7 +11,7 @@ namespace Discord.Net
public int? Remaining { get; }
public int? RetryAfter { get; }
public DateTimeOffset? Reset { get; }
- public TimeSpan? ResetAfter { get; }
+ public TimeSpan? ResetAfter { get; }
public TimeSpan? Lag { get; }
internal RateLimitInfo(Dictionary headers)
@@ -19,17 +19,17 @@ namespace Discord.Net
IsGlobal = headers.TryGetValue("X-RateLimit-Global", out string temp) &&
bool.TryParse(temp, out var isGlobal) && isGlobal;
Limit = headers.TryGetValue("X-RateLimit-Limit", out temp) &&
- int.TryParse(temp, out var limit) ? limit : (int?)null;
+ int.TryParse(temp, NumberStyles.None, CultureInfo.InvariantCulture, out var limit) ? limit : (int?)null;
Remaining = headers.TryGetValue("X-RateLimit-Remaining", out temp) &&
- int.TryParse(temp, out var remaining) ? remaining : (int?)null;
+ int.TryParse(temp, NumberStyles.None, CultureInfo.InvariantCulture, out var remaining) ? remaining : (int?)null;
Reset = headers.TryGetValue("X-RateLimit-Reset", out temp) &&
double.TryParse(temp, NumberStyles.AllowDecimalPoint, CultureInfo.InvariantCulture, out var reset) ? DateTimeOffset.FromUnixTimeMilliseconds((long)(reset * 1000)) : (DateTimeOffset?)null;
RetryAfter = headers.TryGetValue("Retry-After", out temp) &&
- int.TryParse(temp, out var retryAfter) ? retryAfter : (int?)null;
- ResetAfter = headers.TryGetValue("X-RateLimit-Reset-After", out temp) &&
- float.TryParse(temp, out var resetAfter) ? TimeSpan.FromMilliseconds((long)(resetAfter * 1000)) : (TimeSpan?)null;
+ int.TryParse(temp, NumberStyles.None, CultureInfo.InvariantCulture, out var retryAfter) ? retryAfter : (int?)null;
+ ResetAfter = headers.TryGetValue("X-RateLimit-Reset-After", out temp) &&
+ float.TryParse(temp, out var resetAfter) ? TimeSpan.FromMilliseconds((long)(resetAfter * 1000)) : (TimeSpan?)null;
Lag = headers.TryGetValue("Date", out temp) &&
- DateTimeOffset.TryParse(temp, out var date) ? DateTimeOffset.UtcNow - date : (TimeSpan?)null;
+ DateTimeOffset.TryParse(temp, CultureInfo.InvariantCulture, DateTimeStyles.None, out var date) ? DateTimeOffset.UtcNow - date : (TimeSpan?)null;
}
}
}
diff --git a/src/Discord.Net.WebSocket/Entities/Users/SocketUser.cs b/src/Discord.Net.WebSocket/Entities/Users/SocketUser.cs
index eceb071eb..d4798bedd 100644
--- a/src/Discord.Net.WebSocket/Entities/Users/SocketUser.cs
+++ b/src/Discord.Net.WebSocket/Entities/Users/SocketUser.cs
@@ -2,6 +2,7 @@ using System;
using System.Collections.Generic;
using System.Collections.Immutable;
using System.Diagnostics;
+using System.Globalization;
using System.Linq;
using System.Threading.Tasks;
using Discord.Rest;
@@ -60,10 +61,10 @@ namespace Discord.WebSocket
}
if (model.Discriminator.IsSpecified)
{
- var newVal = ushort.Parse(model.Discriminator.Value);
+ var newVal = ushort.Parse(model.Discriminator.Value, NumberStyles.None, CultureInfo.InvariantCulture);
if (newVal != DiscriminatorValue)
{
- DiscriminatorValue = ushort.Parse(model.Discriminator.Value);
+ DiscriminatorValue = ushort.Parse(model.Discriminator.Value, NumberStyles.None, CultureInfo.InvariantCulture);
hasChanges = true;
}
}
diff --git a/src/Discord.Net.Webhook/DiscordWebhookClient.cs b/src/Discord.Net.Webhook/DiscordWebhookClient.cs
index 5dc3d51aa..542ec7997 100644
--- a/src/Discord.Net.Webhook/DiscordWebhookClient.cs
+++ b/src/Discord.Net.Webhook/DiscordWebhookClient.cs
@@ -1,5 +1,6 @@
using System;
using System.Collections.Generic;
+using System.Globalization;
using System.IO;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
@@ -132,7 +133,7 @@ namespace Discord.Webhook
{
// ensure that the first group is a ulong, set the _webhookId
// 0th group is always the entire match, so start at index 1
- if (!(match.Groups[1].Success && ulong.TryParse(match.Groups[1].Value, out webhookId)))
+ if (!(match.Groups[1].Success && ulong.TryParse(match.Groups[1].Value, NumberStyles.None, CultureInfo.InvariantCulture, out webhookId)))
throw ex("The webhook Id could not be parsed.");
if (!match.Groups[2].Success)
diff --git a/test/Discord.Net.Tests.Unit/ChannelPermissionsTests.cs b/test/Discord.Net.Tests.Unit/ChannelPermissionsTests.cs
index 2625c1e9b..a3566590a 100644
--- a/test/Discord.Net.Tests.Unit/ChannelPermissionsTests.cs
+++ b/test/Discord.Net.Tests.Unit/ChannelPermissionsTests.cs
@@ -82,6 +82,7 @@ namespace Discord
AssertFlag(() => new ChannelPermissions(moveMembers: true), ChannelPermission.MoveMembers);
AssertFlag(() => new ChannelPermissions(useVoiceActivation: true), ChannelPermission.UseVAD);
AssertFlag(() => new ChannelPermissions(prioritySpeaker: true), ChannelPermission.PrioritySpeaker);
+ AssertFlag(() => new ChannelPermissions(stream: true), ChannelPermission.Stream);
AssertFlag(() => new ChannelPermissions(manageRoles: true), ChannelPermission.ManageRoles);
AssertFlag(() => new ChannelPermissions(manageWebhooks: true), ChannelPermission.ManageWebhooks);
}
@@ -147,6 +148,7 @@ namespace Discord
AssertUtil(ChannelPermission.ManageRoles, x => x.ManageRoles, (p, enable) => p.Modify(manageRoles: enable));
AssertUtil(ChannelPermission.ManageWebhooks, x => x.ManageWebhooks, (p, enable) => p.Modify(manageWebhooks: enable));
AssertUtil(ChannelPermission.PrioritySpeaker, x => x.PrioritySpeaker, (p, enable) => p.Modify(prioritySpeaker: enable));
+ AssertUtil(ChannelPermission.Stream, x => x.Stream, (p, enable) => p.Modify(stream: enable));
}
///
diff --git a/test/Discord.Net.Tests.Unit/GuildPermissionsTests.cs b/test/Discord.Net.Tests.Unit/GuildPermissionsTests.cs
index 8213a8974..f0611fa24 100644
--- a/test/Discord.Net.Tests.Unit/GuildPermissionsTests.cs
+++ b/test/Discord.Net.Tests.Unit/GuildPermissionsTests.cs
@@ -85,6 +85,7 @@ namespace Discord
AssertFlag(() => new GuildPermissions(moveMembers: true), GuildPermission.MoveMembers);
AssertFlag(() => new GuildPermissions(useVoiceActivation: true), GuildPermission.UseVAD);
AssertFlag(() => new GuildPermissions(prioritySpeaker: true), GuildPermission.PrioritySpeaker);
+ AssertFlag(() => new GuildPermissions(stream: true), GuildPermission.Stream);
AssertFlag(() => new GuildPermissions(changeNickname: true), GuildPermission.ChangeNickname);
AssertFlag(() => new GuildPermissions(manageNicknames: true), GuildPermission.ManageNicknames);
AssertFlag(() => new GuildPermissions(manageRoles: true), GuildPermission.ManageRoles);