Allow keeping proxy tags when proxying messages.

Required database migration:

Closes #75.
This commit is contained in:
Ske 2019-10-30 09:26:50 +01:00
parent 8604d25ffe
commit 49dc25ee02
7 changed files with 38 additions and 4 deletions

View File

@ -68,6 +68,7 @@ namespace PluralKit.API.Controllers
member.Pronouns = newMember.Pronouns; member.Pronouns = newMember.Pronouns;
member.Description = newMember.Description; member.Description = newMember.Description;
member.ProxyTags = newMember.ProxyTags; member.ProxyTags = newMember.ProxyTags;
member.KeepProxy = newMember.KeepProxy;
await _data.SaveMember(member); await _data.SaveMember(member);
return Ok(member); return Ok(member);
@ -107,6 +108,7 @@ namespace PluralKit.API.Controllers
member.Pronouns = newMember.Pronouns; member.Pronouns = newMember.Pronouns;
member.Description = newMember.Description; member.Description = newMember.Description;
member.ProxyTags = newMember.ProxyTags; member.ProxyTags = newMember.ProxyTags;
member.KeepProxy = newMember.KeepProxy;
await _data.SaveMember(member); await _data.SaveMember(member);
return Ok(member); return Ok(member);

View File

@ -32,6 +32,7 @@ namespace PluralKit.Bot.Commands
public static Command MemberDelete = new Command("member delete", "member <member> delete", "uwu"); public static Command MemberDelete = new Command("member delete", "member <member> delete", "uwu");
public static Command MemberAvatar = new Command("member avatar", "member <member> avatar [url|@mention]", "uwu"); public static Command MemberAvatar = new Command("member avatar", "member <member> avatar [url|@mention]", "uwu");
public static Command MemberDisplayName = new Command("member displayname", "member <member> displayname [display name]", "uwu"); public static Command MemberDisplayName = new Command("member displayname", "member <member> displayname [display name]", "uwu");
public static Command MemberKeepProxy = new Command("member keepproxy", "member <member> keepproxy [on|off]", "uwu");
public static Command Switch = new Command("switch", "switch <member> [member 2] [member 3...]", "uwu"); public static Command Switch = new Command("switch", "switch <member> [member 2] [member 3...]", "uwu");
public static Command SwitchOut = new Command("switch out", "switch out", "uwu"); public static Command SwitchOut = new Command("switch out", "switch out", "uwu");
public static Command SwitchMove = new Command("switch move", "switch move <date/time>", "uwu"); public static Command SwitchMove = new Command("switch move", "switch move <date/time>", "uwu");
@ -226,6 +227,8 @@ namespace PluralKit.Bot.Commands
await ctx.Execute<MemberCommands>(MemberAvatar, m => m.MemberAvatar(ctx, target)); await ctx.Execute<MemberCommands>(MemberAvatar, m => m.MemberAvatar(ctx, target));
else if (ctx.Match("displayname", "dn", "dname", "nick", "nickname")) else if (ctx.Match("displayname", "dn", "dname", "nick", "nickname"))
await ctx.Execute<MemberCommands>(MemberDisplayName, m => m.MemberDisplayName(ctx, target)); await ctx.Execute<MemberCommands>(MemberDisplayName, m => m.MemberDisplayName(ctx, target));
else if (ctx.Match("keepproxy", "keeptags", "showtags"))
await ctx.Execute<MemberCommands>(MemberKeepProxy, m => m.MemberKeepProxy(ctx, target));
else if (!ctx.HasNext()) // Bare command else if (!ctx.HasNext()) // Bare command
await ctx.Execute<MemberCommands>(MemberInfo, m => m.ViewMember(ctx, target)); await ctx.Execute<MemberCommands>(MemberInfo, m => m.ViewMember(ctx, target));
else else

View File

@ -310,6 +310,27 @@ namespace PluralKit.Bot.Commands
await _proxyCache.InvalidateResultsForSystem(ctx.System); await _proxyCache.InvalidateResultsForSystem(ctx.System);
} }
public async Task MemberKeepProxy(Context ctx, PKMember target)
{
if (ctx.System == null) throw Errors.NoSystemError;
if (target.System != ctx.System.Id) throw Errors.NotOwnMemberError;
bool newValue;
if (ctx.Match("on", "enabled", "true", "yes")) newValue = true;
else if (ctx.Match("off", "disabled", "false", "no")) newValue = false;
else if (ctx.HasNext()) throw new PKSyntaxError("You must pass either \"on\" or \"off\".");
else newValue = !target.KeepProxy;
target.KeepProxy = newValue;
await _data.SaveMember(target);
if (newValue)
await ctx.Reply($"{Emojis.Success} Member proxy tags will now be included in the resulting message when proxying.");
else
await ctx.Reply($"{Emojis.Success} Member proxy tags will now not be included in the resulting message when proxying.");
await _proxyCache.InvalidateResultsForSystem(ctx.System);
}
public async Task ViewMember(Context ctx, PKMember target) public async Task ViewMember(Context ctx, PKMember target)
{ {
var system = await _data.GetSystemById(target.System); var system = await _data.GetSystemById(target.System);

View File

@ -17,6 +17,7 @@ namespace PluralKit.Bot
class ProxyMatch { class ProxyMatch {
public PKMember Member; public PKMember Member;
public PKSystem System; public PKSystem System;
public ProxyTag ProxyTags;
public string InnerText; public string InnerText;
} }
@ -69,7 +70,7 @@ namespace PluralKit.Bot
if (message.Length >= prefix.Length + suffix.Length && message.StartsWith(prefix) && message.EndsWith(suffix)) { if (message.Length >= prefix.Length + suffix.Length && message.StartsWith(prefix) && message.EndsWith(suffix)) {
var inner = message.Substring(prefix.Length, message.Length - prefix.Length - suffix.Length); var inner = message.Substring(prefix.Length, message.Length - prefix.Length - suffix.Length);
if (leadingMention != null) inner = $"{leadingMention} {inner}"; if (leadingMention != null) inner = $"{leadingMention} {inner}";
return new ProxyMatch { Member = match.Member, System = match.System, InnerText = inner }; return new ProxyMatch { Member = match.Member, System = match.System, InnerText = inner, ProxyTags = tag};
} }
} }
@ -102,9 +103,14 @@ namespace PluralKit.Bot
// If the name's too long (or short), bail // If the name's too long (or short), bail
if (proxyName.Length < 2) throw Errors.ProxyNameTooShort(proxyName); if (proxyName.Length < 2) throw Errors.ProxyNameTooShort(proxyName);
if (proxyName.Length > Limits.MaxProxyNameLength) throw Errors.ProxyNameTooLong(proxyName); if (proxyName.Length > Limits.MaxProxyNameLength) throw Errors.ProxyNameTooLong(proxyName);
// Add the proxy tags into the proxied message if that option is enabled
var messageContents = match.Member.KeepProxy
? $"{match.ProxyTags.Prefix}{match.InnerText}{match.ProxyTags.Suffix}"
: match.InnerText;
// Sanitize @everyone, but only if the original user wouldn't have permission to // Sanitize @everyone, but only if the original user wouldn't have permission to
var messageContents = SanitizeEveryoneMaybe(message, match.InnerText); messageContents = SanitizeEveryoneMaybe(message, messageContents);
// Execute the webhook itself // Execute the webhook itself
var hookMessageId = await _webhookExecutor.ExecuteWebhook( var hookMessageId = await _webhookExecutor.ExecuteWebhook(

View File

@ -66,6 +66,7 @@ namespace PluralKit
[JsonProperty("pronouns")] public string Pronouns { get; set; } [JsonProperty("pronouns")] public string Pronouns { get; set; }
[JsonProperty("description")] public string Description { get; set; } [JsonProperty("description")] public string Description { get; set; }
[JsonProperty("proxy_tags")] public ICollection<ProxyTag> ProxyTags { get; set; } [JsonProperty("proxy_tags")] public ICollection<ProxyTag> ProxyTags { get; set; }
[JsonProperty("keep_proxy")] public bool KeepProxy { get; set; }
[JsonProperty("created")] public Instant Created { get; set; } [JsonProperty("created")] public Instant Created { get; set; }
// These are deprecated as fuck, and are kinda hacky // These are deprecated as fuck, and are kinda hacky

View File

@ -495,7 +495,7 @@ namespace PluralKit {
public async Task SaveMember(PKMember member) { public async Task SaveMember(PKMember member) {
using (var conn = await _conn.Obtain()) using (var conn = await _conn.Obtain())
await conn.ExecuteAsync("update members set name = @Name, display_name = @DisplayName, description = @Description, color = @Color, avatar_url = @AvatarUrl, birthday = @Birthday, pronouns = @Pronouns, proxy_tags = @ProxyTags where id = @Id", member); await conn.ExecuteAsync("update members set name = @Name, display_name = @DisplayName, description = @Description, color = @Color, avatar_url = @AvatarUrl, birthday = @Birthday, pronouns = @Pronouns, proxy_tags = @ProxyTags, keep_proxy = @KeepProxy where id = @Id", member);
_logger.Information("Updated member {@Member}", member); _logger.Information("Updated member {@Member}", member);
} }

View File

@ -32,7 +32,8 @@ create table if not exists members
birthday date, birthday date,
pronouns text, pronouns text,
description text, description text,
proxy_tags proxy_tag[] not null default array[], -- Rationale on making this an array rather than a separate table - we never need to query them individually, only access them as part of a selected Member struct proxy_tags proxy_tag[] not null default array[], -- Rationale on making this an array rather than a separate table - we never need to query them individually, only access them as part of a selected Member struct
keep_proxy bool not null default false,
created timestamp not null default (current_timestamp at time zone 'utc') created timestamp not null default (current_timestamp at time zone 'utc')
); );