normalizePayload($payload); try { $event = DB::transaction(function () use ($data) { return CalendarEvent::query()->create($data); }); } catch (\Throwable $e) { Log::error('SchoolCalendar create failed: '.$e->getMessage()); throw $e; } $emailStatus = $this->notificationService->notify($event->toArray(), $targets); return [ 'event' => $event, 'email_status' => $emailStatus, ]; } public function update(CalendarEvent $event, array $payload, array $targets = []): array { $data = $this->normalizePayload($payload); try { DB::transaction(function () use ($event, $data) { $event->fill($data); $event->save(); }); } catch (\Throwable $e) { Log::error('SchoolCalendar update failed: '.$e->getMessage()); throw $e; } $event->refresh(); $emailStatus = $this->notificationService->notify($event->toArray(), $targets); return [ 'event' => $event, 'email_status' => $emailStatus, ]; } public function delete(CalendarEvent $event): void { try { DB::transaction(function () use ($event) { $event->delete(); }); } catch (\Throwable $e) { Log::error('SchoolCalendar delete failed: '.$e->getMessage()); throw $e; } } private function normalizePayload(array $payload): array { $data = [ 'title' => (string) ($payload['title'] ?? ''), 'description' => $payload['description'] ?? null, 'event_type' => $payload['event_type'] ?? null, 'date' => $payload['date'] ?? $payload['start'] ?? null, 'notify_parent' => ! empty($payload['notify_parent']) ? 1 : 0, 'notify_teacher' => ! empty($payload['notify_teacher']) ? 1 : 0, 'notify_admin' => ! empty($payload['notify_admin']) ? 1 : 0, 'no_school' => ! empty($payload['no_school']) ? 1 : 0, 'school_year' => $payload['school_year'] ?? $this->context->defaultSchoolYear(), 'semester' => $payload['semester'] ?? $this->context->defaultSemester(), ]; if (! CalendarEvent::supportsEventType()) { unset($data['event_type']); } return $data; } }