style: format code with prettier
Local Build and Deploy / deploy (push) Successful in 49s

This commit is contained in:
openhands committed 2026-07-12 21:07:34 +02:00
1 parent e85e4d74ea
commit 2e4ed76121
378 files changed
+22404 -20686

No files matched your search

+73 -73
View File
@@ -1,18 +1,18 @@
'use server'
"use server";
import { PERMS } from '@/lib/permissions'
import { prisma } from '@/lib/prisma'
import { adminAction, authAction } from '@/lib/safe-action'
import { ActionError, actionOk } from '@/lib/safe-action-shared'
import { logAudit } from '@/lib/services/audit'
import { notify } from '@/lib/services/webhook'
import { PERMS } from "@/lib/permissions";
import { prisma } from "@/lib/prisma";
import { adminAction, authAction } from "@/lib/safe-action";
import { ActionError, actionOk } from "@/lib/safe-action-shared";
import { logAudit } from "@/lib/services/audit";
import { notify } from "@/lib/services/webhook";
import {
assignTicketSchema,
createTicketSchema,
replyTicketSchema,
updateTicketPrioritySchema,
updateTicketStatusSchema,
} from '@/lib/validators/ticket'
} from "@/lib/validators/ticket";
// ── User actions (authenticated, no admin perms needed) ──────────────
@@ -23,7 +23,7 @@ export const createTicket = authAction({ schema: createTicketSchema }, async (ct
category: ctx.data.category,
creatorId: ctx.session.user.id,
},
})
});
// Create the first message
await prisma.websiteTicketMessage.create({
@@ -33,26 +33,26 @@ export const createTicket = authAction({ schema: createTicketSchema }, async (ct
message: ctx.data.message,
isStaff: 0,
},
})
});
notify({
action: 'ticket_create',
action: "ticket_create",
actor: ctx.session.user.username,
target: `#${ticket.id} - ${ticket.subject}`,
details: `Category: ${ticket.category}`,
})
});
return actionOk({ id: ticket.id })
})
return actionOk({ id: ticket.id });
});
export const userReplyTicket = authAction({ schema: replyTicketSchema }, async (ctx) => {
const ticket = await prisma.websiteTicket.findUnique({
where: { id: ctx.data.ticketId },
})
});
if (!ticket) throw new ActionError('Ticket not found')
if (ticket.creatorId !== ctx.session.user.id) throw new ActionError('Unauthorized')
if (ticket.status === 'closed') throw new ActionError('Ticket is closed')
if (!ticket) throw new ActionError("Ticket not found");
if (ticket.creatorId !== ctx.session.user.id) throw new ActionError("Unauthorized");
if (ticket.status === "closed") throw new ActionError("Ticket is closed");
await prisma.websiteTicketMessage.create({
data: {
@@ -61,38 +61,38 @@ export const userReplyTicket = authAction({ schema: replyTicketSchema }, async (
message: ctx.data.message,
isStaff: 0,
},
})
});
// If ticket was in "waiting" (waiting for user), move back to open
if (ticket.status === 'waiting') {
if (ticket.status === "waiting") {
await prisma.websiteTicket.update({
where: { id: ctx.data.ticketId },
data: { status: 'open' },
})
data: { status: "open" },
});
}
return actionOk()
})
return actionOk();
});
export const closeTicketByUser = authAction(
{ schema: replyTicketSchema.pick({ ticketId: true }) },
async (ctx) => {
const ticket = await prisma.websiteTicket.findUnique({
where: { id: ctx.data.ticketId },
})
});
if (!ticket) throw new ActionError('Ticket not found')
if (ticket.creatorId !== ctx.session.user.id) throw new ActionError('Unauthorized')
if (ticket.status === 'closed') throw new ActionError('Ticket is already closed')
if (!ticket) throw new ActionError("Ticket not found");
if (ticket.creatorId !== ctx.session.user.id) throw new ActionError("Unauthorized");
if (ticket.status === "closed") throw new ActionError("Ticket is already closed");
await prisma.websiteTicket.update({
where: { id: ctx.data.ticketId },
data: { status: 'closed', closedAt: new Date() },
})
data: { status: "closed", closedAt: new Date() },
});
return actionOk()
return actionOk();
},
)
);
// ── Admin actions ────────────────────────────────────────────────────
@@ -101,9 +101,9 @@ export const adminReplyTicket = adminAction(
async (ctx) => {
const ticket = await prisma.websiteTicket.findUnique({
where: { id: ctx.data.ticketId },
})
});
if (!ticket) throw new ActionError('Ticket not found')
if (!ticket) throw new ActionError("Ticket not found");
await prisma.websiteTicketMessage.create({
data: {
@@ -112,118 +112,118 @@ export const adminReplyTicket = adminAction(
message: ctx.data.message,
isStaff: 1,
},
})
});
// Auto-assign if not assigned yet
const updates: Record<string, unknown> = { status: 'waiting' }
const updates: Record<string, unknown> = { status: "waiting" };
if (!ticket.assigneeId) {
updates.assigneeId = ctx.session.user.id
updates.assigneeId = ctx.session.user.id;
}
await prisma.websiteTicket.update({
where: { id: ctx.data.ticketId },
data: updates,
})
});
logAudit({
userId: ctx.session.user.id,
action: 'ticket_reply',
target: 'WebsiteTicket',
action: "ticket_reply",
target: "WebsiteTicket",
targetId: ctx.data.ticketId,
})
});
return actionOk()
return actionOk();
},
)
);
export const updateTicketStatus = adminAction(
{ permission: PERMS.TICKETS_EDIT, schema: updateTicketStatusSchema },
async (ctx) => {
const ticket = await prisma.websiteTicket.findUnique({
where: { id: ctx.data.ticketId },
})
});
if (!ticket) throw new ActionError('Ticket not found')
if (!ticket) throw new ActionError("Ticket not found");
const data: Record<string, unknown> = { status: ctx.data.status }
if (ctx.data.status === 'closed') {
data.closedAt = new Date()
const data: Record<string, unknown> = { status: ctx.data.status };
if (ctx.data.status === "closed") {
data.closedAt = new Date();
}
if (ctx.data.status === 'in_progress' && !ticket.assigneeId) {
data.assigneeId = ctx.session.user.id
if (ctx.data.status === "in_progress" && !ticket.assigneeId) {
data.assigneeId = ctx.session.user.id;
}
await prisma.websiteTicket.update({
where: { id: ctx.data.ticketId },
data,
})
});
logAudit({
userId: ctx.session.user.id,
action: 'ticket_status_change',
target: 'WebsiteTicket',
action: "ticket_status_change",
target: "WebsiteTicket",
targetId: ctx.data.ticketId,
before: { status: ticket.status },
after: { status: ctx.data.status },
})
});
return actionOk()
return actionOk();
},
)
);
export const assignTicket = adminAction(
{ permission: PERMS.TICKETS_EDIT, schema: assignTicketSchema },
async (ctx) => {
const ticket = await prisma.websiteTicket.findUnique({
where: { id: ctx.data.ticketId },
})
});
if (!ticket) throw new ActionError('Ticket not found')
if (!ticket) throw new ActionError("Ticket not found");
await prisma.websiteTicket.update({
where: { id: ctx.data.ticketId },
data: {
assigneeId: ctx.data.assigneeId,
status: ctx.data.assigneeId ? 'in_progress' : 'open',
status: ctx.data.assigneeId ? "in_progress" : "open",
},
})
});
logAudit({
userId: ctx.session.user.id,
action: 'ticket_assign',
target: 'WebsiteTicket',
action: "ticket_assign",
target: "WebsiteTicket",
targetId: ctx.data.ticketId,
before: { assigneeId: ticket.assigneeId },
after: { assigneeId: ctx.data.assigneeId },
})
});
return actionOk()
return actionOk();
},
)
);
export const updateTicketPriority = adminAction(
{ permission: PERMS.TICKETS_EDIT, schema: updateTicketPrioritySchema },
async (ctx) => {
const ticket = await prisma.websiteTicket.findUnique({
where: { id: ctx.data.ticketId },
})
});
if (!ticket) throw new ActionError('Ticket not found')
if (!ticket) throw new ActionError("Ticket not found");
await prisma.websiteTicket.update({
where: { id: ctx.data.ticketId },
data: { priority: ctx.data.priority },
})
});
logAudit({
userId: ctx.session.user.id,
action: 'ticket_priority_change',
target: 'WebsiteTicket',
action: "ticket_priority_change",
target: "WebsiteTicket",
targetId: ctx.data.ticketId,
before: { priority: ticket.priority },
after: { priority: ctx.data.priority },
})
});
return actionOk()
return actionOk();
},
)
);