fix(members): role tabs/filter include users with secondary roles
user.list and user.listInvitableIds filtered on the singular User.role column, so the type tabs (Jury/Mentor/…) omitted users holding that role as a secondary role (User.roles[]). Match the role as primary OR secondary (roles hasSome), combined with search via AND, mirroring userHasRole / hasRole middleware. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -232,19 +232,26 @@ export const userRouter = router({
|
||||
const skip = (page - 1) * perPage
|
||||
|
||||
const where: Record<string, unknown> = {}
|
||||
const and: Record<string, unknown>[] = []
|
||||
|
||||
// Match the role as EITHER the primary role (User.role) or a secondary
|
||||
// role (User.roles[]) so the type tabs include multi-role users, mirroring
|
||||
// the multi-role checks used elsewhere (userHasRole / hasRole middleware).
|
||||
if (roles && roles.length > 0) {
|
||||
where.role = { in: roles }
|
||||
and.push({ OR: [{ role: { in: roles } }, { roles: { hasSome: roles } }] })
|
||||
} else if (role) {
|
||||
where.role = role
|
||||
and.push({ OR: [{ role }, { roles: { has: role } }] })
|
||||
}
|
||||
if (status) where.status = status
|
||||
if (search) {
|
||||
where.OR = [
|
||||
{ email: { contains: search, mode: 'insensitive' } },
|
||||
{ name: { contains: search, mode: 'insensitive' } },
|
||||
]
|
||||
and.push({
|
||||
OR: [
|
||||
{ email: { contains: search, mode: 'insensitive' } },
|
||||
{ name: { contains: search, mode: 'insensitive' } },
|
||||
],
|
||||
})
|
||||
}
|
||||
if (and.length > 0) where.AND = and
|
||||
|
||||
const dir = sortDir ?? 'asc'
|
||||
const orderBy: Record<string, string> = sortBy
|
||||
@@ -373,19 +380,24 @@ export const userRouter = router({
|
||||
const where: Record<string, unknown> = {
|
||||
status: { in: ['NONE', 'INVITED'] },
|
||||
}
|
||||
const and: Record<string, unknown>[] = []
|
||||
|
||||
// Match primary OR secondary role (see user.list for rationale).
|
||||
if (input.roles && input.roles.length > 0) {
|
||||
where.role = { in: input.roles }
|
||||
and.push({ OR: [{ role: { in: input.roles } }, { roles: { hasSome: input.roles } }] })
|
||||
} else if (input.role) {
|
||||
where.role = input.role
|
||||
and.push({ OR: [{ role: input.role }, { roles: { has: input.role } }] })
|
||||
}
|
||||
|
||||
if (input.search) {
|
||||
where.OR = [
|
||||
{ email: { contains: input.search, mode: 'insensitive' } },
|
||||
{ name: { contains: input.search, mode: 'insensitive' } },
|
||||
]
|
||||
and.push({
|
||||
OR: [
|
||||
{ email: { contains: input.search, mode: 'insensitive' } },
|
||||
{ name: { contains: input.search, mode: 'insensitive' } },
|
||||
],
|
||||
})
|
||||
}
|
||||
if (and.length > 0) where.AND = and
|
||||
|
||||
const users = await ctx.prisma.user.findMany({
|
||||
where,
|
||||
|
||||
Reference in New Issue
Block a user