PluralKit/PluralKit.Bot/Commands/Token.cs

96 lines
4.0 KiB
C#
Raw Normal View History

2019-06-20 19:15:57 +00:00
using System.Threading.Tasks;
2020-12-25 12:19:35 +00:00
using Myriad.Extensions;
using Myriad.Rest.Exceptions;
2020-12-25 12:19:35 +00:00
using Myriad.Rest.Types.Requests;
using Myriad.Types;
2019-10-05 05:41:00 +00:00
using PluralKit.Core;
2019-06-20 19:15:57 +00:00
namespace PluralKit.Bot
2019-06-20 19:15:57 +00:00
{
2020-02-01 12:03:02 +00:00
public class Token
2019-06-20 19:15:57 +00:00
{
private readonly IDatabase _db;
2020-08-29 11:46:27 +00:00
private readonly ModelRepository _repo;
public Token(IDatabase db, ModelRepository repo)
2019-10-05 05:41:00 +00:00
{
_db = db;
2020-08-29 11:46:27 +00:00
_repo = repo;
2019-10-05 05:41:00 +00:00
}
public async Task GetToken(Context ctx)
2019-06-20 19:15:57 +00:00
{
2019-10-05 05:41:00 +00:00
ctx.CheckSystem();
2019-06-20 19:15:57 +00:00
// Get or make a token
2019-10-05 05:41:00 +00:00
var token = ctx.System.Token ?? await MakeAndSetNewToken(ctx.System);
2021-08-27 15:03:47 +00:00
try
2019-06-20 19:15:57 +00:00
{
// DM the user a security disclaimer, and then the token in a separate message (for easy copying on mobile)
2021-01-31 15:16:52 +00:00
var dm = await ctx.Cache.GetOrCreateDmChannel(ctx.Rest, ctx.Author.Id);
await ctx.Rest.CreateMessage(dm.Id, new MessageRequest
2020-12-25 12:19:35 +00:00
{
Content = $"{Emojis.Warn} Please note that this grants access to modify (and delete!) all your system data, so keep it safe and secure. If it leaks or you need a new one, you can invalidate this one with `pk;token refresh`.\n\nYour token is below:"
});
2021-08-27 15:03:47 +00:00
await ctx.Rest.CreateMessage(dm.Id, new MessageRequest { Content = token });
2019-06-20 19:15:57 +00:00
// If we're not already in a DM, reply with a reminder to check
2021-01-31 15:16:52 +00:00
if (ctx.Channel.Type != Channel.ChannelType.Dm)
2020-12-25 12:19:35 +00:00
await ctx.Reply($"{Emojis.Success} Check your DMs!");
}
2021-03-18 10:38:28 +00:00
catch (ForbiddenException)
{
// Can't check for permission errors beforehand, so have to handle here :/
2021-01-31 15:16:52 +00:00
if (ctx.Channel.Type != Channel.ChannelType.Dm)
2020-12-25 12:19:35 +00:00
await ctx.Reply($"{Emojis.Error} Could not send token in DMs. Are your DMs closed?");
}
2019-06-20 19:15:57 +00:00
}
2019-10-05 05:41:00 +00:00
private async Task<string> MakeAndSetNewToken(PKSystem system)
2019-06-20 19:15:57 +00:00
{
2021-08-27 15:03:47 +00:00
var patch = new SystemPatch { Token = StringUtils.GenerateToken() };
2020-08-29 11:46:27 +00:00
system = await _db.Execute(conn => _repo.UpdateSystem(conn, system.Id, patch));
2019-10-05 05:41:00 +00:00
return system.Token;
2019-06-20 19:15:57 +00:00
}
2021-08-27 15:03:47 +00:00
2019-10-05 05:41:00 +00:00
public async Task RefreshToken(Context ctx)
2019-06-20 19:15:57 +00:00
{
2019-10-05 05:41:00 +00:00
ctx.CheckSystem();
2021-08-27 15:03:47 +00:00
2019-10-05 05:41:00 +00:00
if (ctx.System.Token == null)
2019-06-20 19:15:57 +00:00
{
// If we don't have a token, call the other method instead
// This does pretty much the same thing, except words the messages more appropriately for that :)
2019-10-05 05:41:00 +00:00
await GetToken(ctx);
2019-06-20 19:15:57 +00:00
return;
}
2021-08-27 15:03:47 +00:00
try
{
// DM the user an invalidation disclaimer, and then the token in a separate message (for easy copying on mobile)
2021-01-31 15:16:52 +00:00
var dm = await ctx.Cache.GetOrCreateDmChannel(ctx.Rest, ctx.Author.Id);
await ctx.Rest.CreateMessage(dm.Id, new MessageRequest
2020-12-25 12:19:35 +00:00
{
Content = $"{Emojis.Warn} Your previous API token has been invalidated. You will need to change it anywhere it's currently used.\n\nYour token is below:"
});
2021-08-27 15:03:47 +00:00
// Make the new token after sending the first DM; this ensures if we can't DM, we also don't end up
// breaking their existing token as a side effect :)
var token = await MakeAndSetNewToken(ctx.System);
2021-01-31 15:16:52 +00:00
await ctx.Rest.CreateMessage(dm.Id, new MessageRequest { Content = token });
2021-08-27 15:03:47 +00:00
// If we're not already in a DM, reply with a reminder to check
2021-01-31 15:16:52 +00:00
if (ctx.Channel.Type != Channel.ChannelType.Dm)
2020-12-25 12:19:35 +00:00
await ctx.Reply($"{Emojis.Success} Check your DMs!");
}
2021-03-18 10:38:28 +00:00
catch (ForbiddenException)
2019-06-20 19:15:57 +00:00
{
// Can't check for permission errors beforehand, so have to handle here :/
2021-01-31 15:16:52 +00:00
if (ctx.Channel.Type != Channel.ChannelType.Dm)
2020-12-25 12:19:35 +00:00
await ctx.Reply($"{Emojis.Error} Could not send token in DMs. Are your DMs closed?");
2019-06-20 19:15:57 +00:00
}
}
}
}