117 lines
3.3 KiB
TypeScript
117 lines
3.3 KiB
TypeScript
/**
|
|
* Helpers admin Carbets — listing avec filtres, lookup pour formulaires.
|
|
*/
|
|
|
|
import "server-only";
|
|
import { Prisma } from "@/generated/prisma/client";
|
|
import { prisma } from "@/lib/prisma";
|
|
import { AccessType, CarbetStatus, UserRole } from "@/generated/prisma/enums";
|
|
|
|
export type AdminCarbetListItem = {
|
|
id: string;
|
|
slug: string;
|
|
title: string;
|
|
river: string;
|
|
capacity: number;
|
|
status: CarbetStatus;
|
|
accessType: AccessType;
|
|
ownerName: string;
|
|
ownerEmail: string;
|
|
mediaCount: number;
|
|
bookingsCount: number;
|
|
updatedAt: Date;
|
|
};
|
|
|
|
export type AdminCarbetFilters = {
|
|
q?: string;
|
|
river?: string;
|
|
status?: CarbetStatus;
|
|
accessType?: AccessType;
|
|
};
|
|
|
|
export async function listCarbetsAdmin(filters: AdminCarbetFilters = {}): Promise<AdminCarbetListItem[]> {
|
|
const where: Prisma.CarbetWhereInput = {};
|
|
if (filters.q) {
|
|
where.OR = [
|
|
{ title: { contains: filters.q, mode: "insensitive" } },
|
|
{ slug: { contains: filters.q, mode: "insensitive" } },
|
|
{ river: { contains: filters.q, mode: "insensitive" } },
|
|
];
|
|
}
|
|
if (filters.river) where.river = filters.river;
|
|
if (filters.status) where.status = filters.status;
|
|
if (filters.accessType) where.accessType = filters.accessType;
|
|
|
|
const rows = await prisma.carbet.findMany({
|
|
where,
|
|
orderBy: { updatedAt: "desc" },
|
|
take: 100,
|
|
select: {
|
|
id: true,
|
|
slug: true,
|
|
title: true,
|
|
river: true,
|
|
capacity: true,
|
|
status: true,
|
|
accessType: true,
|
|
updatedAt: true,
|
|
owner: { select: { firstName: true, lastName: true, email: true } },
|
|
_count: { select: { media: true, bookings: true } },
|
|
},
|
|
});
|
|
|
|
return rows.map((r) => ({
|
|
id: r.id,
|
|
slug: r.slug,
|
|
title: r.title,
|
|
river: r.river,
|
|
capacity: r.capacity,
|
|
status: r.status,
|
|
accessType: r.accessType,
|
|
ownerName: `${r.owner.firstName} ${r.owner.lastName}`.trim() || r.owner.email,
|
|
ownerEmail: r.owner.email,
|
|
mediaCount: r._count.media,
|
|
bookingsCount: r._count.bookings,
|
|
updatedAt: r.updatedAt,
|
|
}));
|
|
}
|
|
|
|
export async function listDistinctRivers(): Promise<string[]> {
|
|
const rows = await prisma.carbet.findMany({
|
|
distinct: ["river"],
|
|
orderBy: { river: "asc" },
|
|
select: { river: true },
|
|
});
|
|
return rows.map((r) => r.river);
|
|
}
|
|
|
|
export async function listOwners() {
|
|
return await prisma.user.findMany({
|
|
where: { role: UserRole.OWNER, isActive: true },
|
|
orderBy: [{ firstName: "asc" }, { lastName: "asc" }],
|
|
select: { id: true, firstName: true, lastName: true, email: true },
|
|
});
|
|
}
|
|
|
|
export async function listPirogueProviders() {
|
|
return await prisma.pirogueProvider.findMany({
|
|
where: { active: true },
|
|
orderBy: { name: "asc" },
|
|
select: { id: true, name: true, rivers: true },
|
|
});
|
|
}
|
|
|
|
export async function getCarbetForEdit(id: string) {
|
|
return await prisma.carbet.findUnique({
|
|
where: { id },
|
|
include: {
|
|
owner: { select: { id: true, firstName: true, lastName: true, email: true } },
|
|
pirogueProvider: { select: { id: true, name: true } },
|
|
media: { orderBy: { sortOrder: "asc" } },
|
|
_count: { select: { bookings: true, reviews: true } },
|
|
},
|
|
});
|
|
}
|
|
|
|
// Options enum déplacées dans `./carbet-options.ts` pour être importables
|
|
// depuis les composants client (ce fichier-ci est server-only).
|