Add image cropping to avatar upload and show avatars platform-wide
- Add react-easy-crop for circular crop + zoom UI on avatar upload - Create server-side getUserAvatarUrl utility for generating pre-signed URLs - Update all nav components (admin, jury, mentor, observer) to show user avatars - Add avatar URLs to user list, mentor list, and project detail API responses - Replace initials-only avatars with UserAvatar component across admin pages Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
@@ -2,6 +2,7 @@ import { z } from 'zod'
|
||||
import { TRPCError } from '@trpc/server'
|
||||
import { Prisma } from '@prisma/client'
|
||||
import { router, protectedProcedure, adminProcedure } from '../trpc'
|
||||
import { getUserAvatarUrl } from '../utils/avatar-url'
|
||||
|
||||
export const projectRouter = router({
|
||||
/**
|
||||
@@ -91,7 +92,7 @@ export const projectRouter = router({
|
||||
teamMembers: {
|
||||
include: {
|
||||
user: {
|
||||
select: { id: true, name: true, email: true },
|
||||
select: { id: true, name: true, email: true, profileImageKey: true, profileImageProvider: true },
|
||||
},
|
||||
},
|
||||
orderBy: { joinedAt: 'asc' },
|
||||
@@ -99,7 +100,7 @@ export const projectRouter = router({
|
||||
mentorAssignment: {
|
||||
include: {
|
||||
mentor: {
|
||||
select: { id: true, name: true, email: true, expertiseTags: true },
|
||||
select: { id: true, name: true, email: true, expertiseTags: true, profileImageKey: true, profileImageProvider: true },
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -123,7 +124,35 @@ export const projectRouter = router({
|
||||
}
|
||||
}
|
||||
|
||||
return project
|
||||
// Attach avatar URLs to team members and mentor
|
||||
const teamMembersWithAvatars = await Promise.all(
|
||||
project.teamMembers.map(async (member) => ({
|
||||
...member,
|
||||
user: {
|
||||
...member.user,
|
||||
avatarUrl: await getUserAvatarUrl(member.user.profileImageKey, member.user.profileImageProvider),
|
||||
},
|
||||
}))
|
||||
)
|
||||
|
||||
const mentorWithAvatar = project.mentorAssignment
|
||||
? {
|
||||
...project.mentorAssignment,
|
||||
mentor: {
|
||||
...project.mentorAssignment.mentor,
|
||||
avatarUrl: await getUserAvatarUrl(
|
||||
project.mentorAssignment.mentor.profileImageKey,
|
||||
project.mentorAssignment.mentor.profileImageProvider
|
||||
),
|
||||
},
|
||||
}
|
||||
: null
|
||||
|
||||
return {
|
||||
...project,
|
||||
teamMembers: teamMembersWithAvatars,
|
||||
mentorAssignment: mentorWithAvatar,
|
||||
}
|
||||
}),
|
||||
|
||||
/**
|
||||
|
||||
Reference in New Issue
Block a user