feat: add admin settings page for display name and avatar editing

This commit is contained in:
Kirill
2026-05-21 20:28:35 +05:00
parent 37be5eef08
commit 0dfa428931
5 changed files with 318 additions and 1 deletions
+2
View File
@@ -1,5 +1,6 @@
import { mapProductForApi, parseMaterialsInput, slugify } from './api/_product-helpers.js'
import { registerAdminNotificationRoutes } from './api/admin/notifications.js'
import { registerAdminProfileRoutes } from './api/admin-profile.js'
import { registerAdminCategoryRoutes } from './api/admin-categories.js'
import { registerAdminGalleryRoutes } from './api/admin-gallery.js'
import { registerAdminOrderRoutes } from './api/admin-orders.js'
@@ -26,4 +27,5 @@ export async function registerApiRoutes(fastify) {
await registerAdminReviewRoutes(fastify)
await registerAdminUserRoutes(fastify)
await registerAdminNotificationRoutes(fastify)
await registerAdminProfileRoutes(fastify)
}
+64
View File
@@ -0,0 +1,64 @@
import { prisma } from '../../lib/prisma.js'
export async function registerAdminProfileRoutes(fastify) {
fastify.get('/api/admin/profile', { preHandler: [fastify.verifyAdmin] }, async (request, reply) => {
const userId = request.user.sub
const user = await prisma.user.findUnique({ where: { id: userId } })
if (!user) return reply.code(404).send({ error: 'Пользователь не найден' })
return {
id: user.id,
email: user.email,
displayName: user.displayName,
avatar: user.avatar,
avatarType: user.avatarType,
avatarStyle: user.avatarStyle,
}
})
fastify.patch('/api/admin/profile', { preHandler: [fastify.verifyAdmin] }, async (request, reply) => {
const userId = request.user.sub
const nameRaw = request.body?.displayName
const displayName = nameRaw === null || nameRaw === undefined ? undefined : String(nameRaw).trim()
const avatarRaw = request.body?.avatar
const avatar = avatarRaw === null || avatarRaw === undefined ? undefined : String(avatarRaw).trim()
const avatarTypeRaw = request.body?.avatarType
const avatarType = avatarTypeRaw === null || avatarTypeRaw === undefined ? undefined : String(avatarTypeRaw).trim()
const avatarStyleRaw = request.body?.avatarStyle
const avatarStyle =
avatarStyleRaw === null || avatarStyleRaw === undefined ? undefined : String(avatarStyleRaw).trim()
if (displayName !== undefined && displayName !== null && displayName.length > 40)
return reply.code(400).send({ error: 'Имя/ник максимум 40 символов' })
if (avatarType !== undefined && avatarType !== 'oauth' && avatarType !== 'generated' && avatarType !== '') {
return reply.code(400).send({ error: 'avatarType должен быть oauth | generated | пустая строка' })
}
if (avatar !== undefined && avatar.length > 200000) return reply.code(400).send({ error: 'Аватар слишком большой' })
if (avatarStyle !== undefined && avatarStyle !== '' && avatarStyle.length > 30) {
return reply.code(400).send({ error: 'Стиль аватара слишком длинный' })
}
const data = {}
if (displayName !== undefined) {
data.displayName = displayName && displayName.length ? displayName : null
}
if (avatarType !== undefined) {
data.avatarType = avatarType === '' ? null : avatarType
}
if (avatar !== undefined) {
data.avatar = avatar === '' ? null : avatar
}
if (avatarStyle !== undefined) {
data.avatarStyle = avatarStyle === '' ? null : avatarStyle
}
const updated = await prisma.user.update({ where: { id: userId }, data })
return {
id: updated.id,
email: updated.email,
displayName: updated.displayName,
avatar: updated.avatar,
avatarType: updated.avatarType,
avatarStyle: updated.avatarStyle,
}
})
}