calendar 14
This commit is contained in:
parent
7dab3da369
commit
0d78cc4e6a
@ -149,31 +149,29 @@ export async function DELETE(
|
||||
}
|
||||
|
||||
try {
|
||||
// Vérifier que le calendrier existe et appartient à l'utilisateur
|
||||
const existingCalendar = await prisma.calendar.findUnique({
|
||||
// Verify calendar ownership
|
||||
const calendar = await prisma.calendar.findFirst({
|
||||
where: {
|
||||
id: params.id,
|
||||
userId: session.user.username,
|
||||
},
|
||||
});
|
||||
|
||||
if (!existingCalendar) {
|
||||
if (!calendar) {
|
||||
return NextResponse.json(
|
||||
{ error: "Calendrier non trouvé" },
|
||||
{ error: "Calendrier non trouvé ou non autorisé" },
|
||||
{ status: 404 }
|
||||
);
|
||||
}
|
||||
|
||||
if (existingCalendar.userId !== session.user.username) {
|
||||
return NextResponse.json({ error: "Non autorisé" }, { status: 403 });
|
||||
}
|
||||
|
||||
// Delete the calendar (this will also delete all associated events due to the cascade delete)
|
||||
await prisma.calendar.delete({
|
||||
where: {
|
||||
id: params.id,
|
||||
},
|
||||
});
|
||||
|
||||
return new NextResponse(null, { status: 204 });
|
||||
return NextResponse.json({ success: true });
|
||||
} catch (error) {
|
||||
console.error("Erreur lors de la suppression du calendrier:", error);
|
||||
return NextResponse.json({ error: "Erreur serveur" }, { status: 500 });
|
||||
|
||||
@ -14,15 +14,17 @@ export async function DELETE(
|
||||
}
|
||||
|
||||
try {
|
||||
// Verify event ownership
|
||||
// Verify event ownership through calendar
|
||||
const event = await prisma.event.findFirst({
|
||||
where: {
|
||||
id: params.id,
|
||||
userId: session.user.username,
|
||||
},
|
||||
include: {
|
||||
calendar: true
|
||||
}
|
||||
});
|
||||
|
||||
if (!event) {
|
||||
if (!event || event.calendar.userId !== session.user.username) {
|
||||
return NextResponse.json(
|
||||
{ error: "Événement non trouvé ou non autorisé" },
|
||||
{ status: 404 }
|
||||
|
||||
@ -44,8 +44,11 @@ export async function POST(req: NextRequest) {
|
||||
end: new Date(end),
|
||||
isAllDay: allDay || false,
|
||||
location,
|
||||
calendarId,
|
||||
userId: session.user.username,
|
||||
calendar: {
|
||||
connect: {
|
||||
id: calendarId
|
||||
}
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
@ -74,15 +77,22 @@ export async function PUT(req: NextRequest) {
|
||||
);
|
||||
}
|
||||
|
||||
// Verify event ownership
|
||||
const existingEvent = await prisma.event.findFirst({
|
||||
// Verify calendar ownership
|
||||
const calendar = await prisma.calendar.findFirst({
|
||||
where: {
|
||||
id,
|
||||
id: calendarId,
|
||||
userId: session.user.username,
|
||||
},
|
||||
include: {
|
||||
events: {
|
||||
where: {
|
||||
id
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
if (!existingEvent) {
|
||||
if (!calendar || calendar.events.length === 0) {
|
||||
return NextResponse.json(
|
||||
{ error: "Événement non trouvé ou non autorisé" },
|
||||
{ status: 404 }
|
||||
@ -98,7 +108,11 @@ export async function PUT(req: NextRequest) {
|
||||
end: new Date(end),
|
||||
isAllDay: allDay || false,
|
||||
location,
|
||||
calendarId,
|
||||
calendar: {
|
||||
connect: {
|
||||
id: calendarId
|
||||
}
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
|
||||
@ -79,10 +79,11 @@ interface CalendarDialogProps {
|
||||
open: boolean;
|
||||
onClose: () => void;
|
||||
onSave: (calendarData: Partial<Calendar>) => Promise<void>;
|
||||
onDelete?: (calendarId: string) => Promise<void>;
|
||||
initialData?: Partial<Calendar>;
|
||||
}
|
||||
|
||||
function CalendarDialog({ open, onClose, onSave, initialData }: CalendarDialogProps) {
|
||||
function CalendarDialog({ open, onClose, onSave, onDelete, initialData }: CalendarDialogProps) {
|
||||
const [name, setName] = useState(initialData?.name || "");
|
||||
const [color, setColor] = useState(initialData?.color || "#4f46e5");
|
||||
const [description, setDescription] = useState(initialData?.description || "");
|
||||
@ -117,6 +118,20 @@ function CalendarDialog({ open, onClose, onSave, initialData }: CalendarDialogPr
|
||||
}
|
||||
};
|
||||
|
||||
const handleDelete = async () => {
|
||||
if (!initialData?.id || !onDelete) return;
|
||||
|
||||
setIsSubmitting(true);
|
||||
try {
|
||||
await onDelete(initialData.id);
|
||||
resetForm();
|
||||
} catch (error) {
|
||||
console.error("Erreur lors de la suppression du calendrier:", error);
|
||||
} finally {
|
||||
setIsSubmitting(false);
|
||||
}
|
||||
};
|
||||
|
||||
const resetForm = () => {
|
||||
setName("");
|
||||
setColor("#4f46e5");
|
||||
@ -229,30 +244,41 @@ function CalendarDialog({ open, onClose, onSave, initialData }: CalendarDialogPr
|
||||
</div>
|
||||
|
||||
<DialogFooter className="mt-6 border-t border-gray-100 pt-4">
|
||||
<div className="flex gap-3 w-full sm:justify-end">
|
||||
<Button
|
||||
type="button"
|
||||
variant="outline"
|
||||
onClick={onClose}
|
||||
disabled={isSubmitting}
|
||||
className="rounded-lg border-gray-300 text-gray-700 hover:bg-gray-50"
|
||||
>
|
||||
<X className="w-4 h-4 mr-2" />
|
||||
Annuler
|
||||
</Button>
|
||||
<Button
|
||||
type="submit"
|
||||
disabled={!name || isSubmitting}
|
||||
className="rounded-lg bg-indigo-600 hover:bg-indigo-700 text-white"
|
||||
>
|
||||
<Check className="w-4 h-4 mr-2" />
|
||||
{isSubmitting
|
||||
? "Enregistrement..."
|
||||
: initialData?.id
|
||||
? "Mettre à jour"
|
||||
: "Créer"
|
||||
}
|
||||
</Button>
|
||||
<div className="flex justify-between w-full">
|
||||
{initialData?.id && (
|
||||
<Button
|
||||
type="button"
|
||||
variant="destructive"
|
||||
onClick={handleDelete}
|
||||
disabled={isSubmitting}
|
||||
>
|
||||
<X className="w-4 h-4 mr-2" />
|
||||
Supprimer
|
||||
</Button>
|
||||
)}
|
||||
<div className="flex gap-3">
|
||||
<Button
|
||||
type="button"
|
||||
variant="outline"
|
||||
onClick={onClose}
|
||||
disabled={isSubmitting}
|
||||
className="rounded-lg border-gray-300 text-gray-700 hover:bg-gray-50"
|
||||
>
|
||||
Annuler
|
||||
</Button>
|
||||
<Button
|
||||
type="submit"
|
||||
disabled={!name || isSubmitting}
|
||||
className="rounded-lg bg-indigo-600 hover:bg-indigo-700 text-white"
|
||||
>
|
||||
{isSubmitting
|
||||
? "Enregistrement..."
|
||||
: initialData?.id
|
||||
? "Mettre à jour"
|
||||
: "Créer"
|
||||
}
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
</DialogFooter>
|
||||
</form>
|
||||
@ -494,6 +520,33 @@ export function CalendarClient({ initialCalendars, userId, userProfile }: Calend
|
||||
}
|
||||
};
|
||||
|
||||
const handleCalendarDelete = async (calendarId: string) => {
|
||||
try {
|
||||
setLoading(true);
|
||||
const response = await fetch(`/api/calendars/${calendarId}`, {
|
||||
method: "DELETE",
|
||||
});
|
||||
|
||||
if (!response.ok) {
|
||||
throw new Error("Failed to delete calendar");
|
||||
}
|
||||
|
||||
await fetchCalendars();
|
||||
setIsCalendarModalOpen(false);
|
||||
|
||||
// If the deleted calendar was selected, select another one
|
||||
if (selectedCalendarId === calendarId) {
|
||||
const remainingCalendars = calendars.filter(cal => cal.id !== calendarId);
|
||||
setSelectedCalendarId(remainingCalendars[0]?.id || "");
|
||||
}
|
||||
} catch (error) {
|
||||
console.error("Error deleting calendar:", error);
|
||||
setError(error instanceof Error ? error.message : "Failed to delete calendar");
|
||||
} finally {
|
||||
setLoading(false);
|
||||
}
|
||||
};
|
||||
|
||||
const handleDateSelect = (selectInfo: any) => {
|
||||
const startDate = new Date(selectInfo.start);
|
||||
const endDate = new Date(selectInfo.end);
|
||||
@ -730,6 +783,7 @@ export function CalendarClient({ initialCalendars, userId, userProfile }: Calend
|
||||
open={isCalendarModalOpen}
|
||||
onClose={() => setIsCalendarModalOpen(false)}
|
||||
onSave={handleCalendarSave}
|
||||
onDelete={handleCalendarDelete}
|
||||
initialData={selectedCalendar || undefined}
|
||||
/>
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user