diff --git a/PluralKit.Bot/Commands/GroupMember.cs b/PluralKit.Bot/Commands/GroupMember.cs index 658f75fc..0b3c1e51 100644 --- a/PluralKit.Bot/Commands/GroupMember.cs +++ b/PluralKit.Bot/Commands/GroupMember.cs @@ -54,7 +54,7 @@ public class GroupMember public async Task ListMemberGroups(Context ctx, PKMember target) { var targetSystem = await ctx.Repository.GetSystem(target.System); - var opts = ctx.ParseListOptions(ctx.DirectLookupContextFor(target.System)); + var opts = ctx.ParseListOptions(ctx.DirectLookupContextFor(target.System), ctx.LookupContextFor(target.System)); opts.MemberFilter = target.Id; var title = new StringBuilder($"Groups containing {target.Name} (`{target.DisplayHid(ctx.Config)}`) in "); @@ -141,7 +141,7 @@ public class GroupMember var targetSystem = await GetGroupSystem(ctx, target); ctx.CheckSystemPrivacy(targetSystem.Id, target.ListPrivacy); - var opts = ctx.ParseListOptions(ctx.DirectLookupContextFor(target.System)); + var opts = ctx.ParseListOptions(ctx.DirectLookupContextFor(target.System), ctx.LookupContextFor(target.System)); opts.GroupFilter = target.Id; var title = new StringBuilder($"Members of {target.DisplayName ?? target.Name} (`{target.DisplayHid(ctx.Config)}`) in "); diff --git a/PluralKit.Bot/Commands/Groups.cs b/PluralKit.Bot/Commands/Groups.cs index 0fe078e3..05cc0a54 100644 --- a/PluralKit.Bot/Commands/Groups.cs +++ b/PluralKit.Bot/Commands/Groups.cs @@ -468,7 +468,7 @@ public class Groups // - ParseListOptions checks list access privacy and sets the privacy filter (which members show up in list) // - RenderGroupList checks the indivual privacy for each member (NameFor, etc) // the own system is always allowed to look up their list - var opts = ctx.ParseListOptions(ctx.DirectLookupContextFor(system.Id)); + var opts = ctx.ParseListOptions(ctx.DirectLookupContextFor(system.Id), ctx.LookupContextFor(system.Id)); await ctx.RenderGroupList( ctx.LookupContextFor(system.Id), system.Id, diff --git a/PluralKit.Bot/Commands/Lists/ContextListExt.cs b/PluralKit.Bot/Commands/Lists/ContextListExt.cs index 2821cf57..1c23cc40 100644 --- a/PluralKit.Bot/Commands/Lists/ContextListExt.cs +++ b/PluralKit.Bot/Commands/Lists/ContextListExt.cs @@ -11,7 +11,7 @@ namespace PluralKit.Bot; public static class ContextListExt { - public static ListOptions ParseListOptions(this Context ctx, LookupContext lookupCtx) + public static ListOptions ParseListOptions(this Context ctx, LookupContext directLookupCtx, LookupContext lookupContext) { var p = new ListOptions(); @@ -55,10 +55,13 @@ public static class ContextListExt if (ctx.MatchFlag("private-only", "po")) p.PrivacyFilter = PrivacyLevel.Private; // PERM CHECK: If we're trying to access non-public members of another system, error - if (p.PrivacyFilter != PrivacyLevel.Public && lookupCtx != LookupContext.ByOwner) + if (p.PrivacyFilter != PrivacyLevel.Public && directLookupCtx != LookupContext.ByOwner) // TODO: should this just return null instead of throwing or something? >.> throw Errors.NotOwnInfo; + //this is for searching + p.Context = lookupContext; + // Additional fields to include in the search results if (ctx.MatchFlag("with-last-switch", "with-last-fronted", "with-last-front", "wls", "wlf")) p.IncludeLastSwitch = true; diff --git a/PluralKit.Bot/Commands/Lists/ListOptions.cs b/PluralKit.Bot/Commands/Lists/ListOptions.cs index 82aa0d67..991b0a8e 100644 --- a/PluralKit.Bot/Commands/Lists/ListOptions.cs +++ b/PluralKit.Bot/Commands/Lists/ListOptions.cs @@ -28,6 +28,7 @@ public class ListOptions public bool Reverse { get; set; } public PrivacyLevel? PrivacyFilter { get; set; } = PrivacyLevel.Public; + public LookupContext Context { get; set; } = LookupContext.ByNonOwner; public GroupId? GroupFilter { get; set; } public MemberId? MemberFilter { get; set; } public string? Search { get; set; } @@ -99,7 +100,8 @@ public class ListOptions GroupFilter = GroupFilter, MemberFilter = MemberFilter, Search = Search, - SearchDescription = SearchDescription + SearchDescription = SearchDescription, + Context = Context }; } diff --git a/PluralKit.Bot/Commands/Random.cs b/PluralKit.Bot/Commands/Random.cs index 933ec7e1..8f0c07b2 100644 --- a/PluralKit.Bot/Commands/Random.cs +++ b/PluralKit.Bot/Commands/Random.cs @@ -67,7 +67,7 @@ public class Random { ctx.CheckSystemPrivacy(group.System, group.ListPrivacy); - var opts = ctx.ParseListOptions(ctx.DirectLookupContextFor(group.System)); + var opts = ctx.ParseListOptions(ctx.DirectLookupContextFor(group.System), ctx.LookupContextFor(group.System)); opts.GroupFilter = group.Id; var members = await ctx.Database.Execute(conn => conn.QueryMemberList(group.System, opts.ToQueryOptions())); diff --git a/PluralKit.Bot/Commands/SystemList.cs b/PluralKit.Bot/Commands/SystemList.cs index beb81eda..af0b4cbe 100644 --- a/PluralKit.Bot/Commands/SystemList.cs +++ b/PluralKit.Bot/Commands/SystemList.cs @@ -17,7 +17,7 @@ public class SystemList // - ParseListOptions checks list access privacy and sets the privacy filter (which members show up in list) // - RenderMemberList checks the indivual privacy for each member (NameFor, etc) // the own system is always allowed to look up their list - var opts = ctx.ParseListOptions(ctx.DirectLookupContextFor(target.Id)); + var opts = ctx.ParseListOptions(ctx.DirectLookupContextFor(target.Id), ctx.LookupContextFor(target.Id)); await ctx.RenderMemberList( ctx.LookupContextFor(target.Id), target.Id, diff --git a/PluralKit.Core/Database/Views/DatabaseViewsExt.cs b/PluralKit.Core/Database/Views/DatabaseViewsExt.cs index 761fc3d9..877c767d 100644 --- a/PluralKit.Core/Database/Views/DatabaseViewsExt.cs +++ b/PluralKit.Core/Database/Views/DatabaseViewsExt.cs @@ -24,7 +24,8 @@ public static class DatabaseViewsExt static string Filter(string column) => $"(position(lower(@filter) in lower(coalesce({column}, ''))) > 0)"; - query.Append($" and ({Filter("name")} or {Filter("display_name")}"); + var nameColumn = opts.Context == LookupContext.ByOwner ? "name" : "public_name"; + query.Append($" and ({Filter(nameColumn)} or {Filter("display_name")}"); if (opts.SearchDescription) { // We need to account for the possibility of description privacy when searching @@ -60,7 +61,8 @@ public static class DatabaseViewsExt static string Filter(string column) => $"(position(lower(@filter) in lower(coalesce({column}, ''))) > 0)"; - query.Append($" and ({Filter("name")} or {Filter("display_name")}"); + var nameColumn = opts.Context == LookupContext.ByOwner ? "name" : "public_name"; + query.Append($" and ({Filter(nameColumn)} or {Filter("display_name")}"); if (opts.SearchDescription) { // We need to account for the possibility of description privacy when searching diff --git a/PluralKit.Core/Database/Views/views.sql b/PluralKit.Core/Database/Views/views.sql index e23ebb6f..6fe08b73 100644 --- a/PluralKit.Core/Database/Views/views.sql +++ b/PluralKit.Core/Database/Views/views.sql @@ -30,7 +30,15 @@ select members.*, -- Privacy '1' = public; just return description as normal when members.description_privacy = 1 then members.description -- Any other privacy (rn just '2'), return null description (missing case = null in SQL) - end as public_description + end as public_description, + + -- Extract member name as seen by "the public" + case + -- Privacy '1' = public; just return name as normal + when members.name_privacy = 1 then members.name + -- Any other privacy (rn just '2'), return display name + else members.display_name + end as public_name from members; create view group_list as @@ -48,5 +56,20 @@ select groups.*, inner join members on group_members.member_id = members.id where group_members.group_id = groups.id - ) as total_member_count + ) as total_member_count, + + -- Extract group description as seen by "the public" + case + -- Privacy '1' = public; just return description as normal + when groups.description_privacy = 1 then groups.description + -- Any other privacy (rn just '2'), return null description (missing case = null in SQL) + end as public_description, + + -- Extract member name as seen by "the public" + case + -- Privacy '1' = public; just return name as normal + when groups.name_privacy = 1 then groups.name + -- Any other privacy (rn just '2'), return display name + else groups.display_name + end as public_name from groups; \ No newline at end of file