# Events & Triggers — Maintenance Guide

**Purpose:** Curated list of what to **keep and maintain** so BvProperty runs smoothly.  
**Not a full catalog** — only events worth wiring, testing, and supporting long-term.

**Stack layers:**

| Layer | Where | Use for |
|-------|--------|---------|
| Messaging events | `MessagingGatewayService` + `config/messaging.php` | SMS, email, push, in-app to residents/guards/staff |
| Automation triggers | `automation_rules` + `AutomationEngineService` | Society-specific rules (notify MC, start workflow) |
| Model hooks | Eloquent `booted()` / `BelongsToTenant` | `tenant_id`, light defaults |
| MySQL triggers | Migrations (minimal) | Audit + financial immutability only |

**Rule:** Business workflows (notifications, approvals, escalations) stay in **app services**. MySQL triggers are for **integrity and audit**, not messaging.

---

## 1. Core messaging events (keep these)

These are the minimum set to maintain per module. Each must have at least one `notification_templates` row (in-app and/or email) for demo/UAT tenants.

### Security & gate (`MOD-SEC-001`)

| Event | When | Priority |
|-------|------|----------|
| `visitor.pending_approval` | Resident must approve visitor | P0 |
| `visitor.approved` | Gate pass issued | P0 |
| `visitor.checked_in` | Visitor entered society | P1 |
| `visitor.overstay` | Visitor past allowed time | P1 |
| `safety.sos` | Resident panic / SOS | P0 |

### Helpdesk (`MOD-OPS-001`)

| Event | When | Priority |
|-------|------|----------|
| `helpdesk.ticket.created` | New complaint / request | P0 |
| `helpdesk.ticket.resolved` | Ticket closed or resolved | P0 |

### Billing & finance (`MOD-FIN-001`)

| Event | When | Priority |
|-------|------|----------|
| `invoice.issued` | Maintenance bill generated | P0 |
| `billing.reminder` | Due-date / overdue reminder | P0 |
| `recovery.notice_sent` | Legal recovery notice | P1 |

### Governance (`MOD-GOV-001`)

| Event | When | Priority |
|-------|------|----------|
| `notice.published` | Society notice posted | P0 |

### Amenities (`MOD-AMN-001`)

| Event | When | Priority |
|-------|------|----------|
| `amenity.booking.confirmed` | Booking approved | P0 |
| `amenity.booking.pending` | Awaiting approval | P1 |
| `amenity.booking.reminder` | Upcoming slot reminder | P1 |

### Parking (`MOD-PARK-001`)

| Event | When | Priority |
|-------|------|----------|
| `parking.pass.issued` | Pass created for unit | P1 |
| `parking.allocation.created` | Slot allocated | P2 |

### Community (optional, low churn)

| Event | When | Priority |
|-------|------|----------|
| `resident.birthday` | Birthday greeting to resident | P2 |
| `safety.general` | Non-SOS safety broadcast | P2 |

---

## 2. Automation triggers (keep these wired)

Automation rules are stored in `automation_rules`. A trigger only works if the **service calls** `AutomationEngineService::dispatch()`.

### All automation triggers (wired in code)

| Trigger | Service | Typical society rule |
|---------|---------|-------------------|
| `helpdesk.ticket.created` | `HelpdeskService` | Notify MC / secretary on new ticket |
| `helpdesk.ticket.resolved` | `HelpdeskService` | FYI when ticket closed |
| `invoice.issued` | `SocietyBillingService` | FYI to treasurer when batch issued |
| `recovery.notice_sent` | `FinanceRecoveryService` | Audit trail to secretary |
| `notice.published` | `NoticeService` | Alert admin that notice went live |
| `visitor.approved` | `VisitorService` | Escalate contractor / VIP visits |
| `visitor.overstay` | `VisitorOverstayMonitorService` | Notify guard supervisor |
| `payment.received` | `PaymentGatewayService` | Notify treasurer on payments |
| `amenity.booking.confirmed` | `AmenityService` | Facility checklist workflow |

### Automation actions to maintain

Only these action types are supported today — keep rules using them:

| Action `type` | Purpose |
|---------------|---------|
| `notify_role` | In-app alert to users with role (`tenant-admin`, `tenant-secretary`, …) |
| `start_workflow` | Kick off workflow on entity (`helpdesk_ticket`, …) |
| `set_ticket_status` | Auto-close or escalate helpdesk ticket |

**Do not** rely on custom action types in production rules until implemented in `AutomationEngineService`.

### ERP UI trigger picker (`AutomationRuleResource`)

Preset dropdown (society can also type custom events):

- `helpdesk.ticket.created`
- `visitor.approved`
- `notice.published`

Expand this list only when `dispatch()` exists for the event.

---

## 3. Model hooks (keep minimal)

Maintain only hooks that prevent bad data — not business logic.

| Hook | Where | Keep because |
|------|-------|--------------|
| `BelongsToTenant` | Most society models | Auto `tenant_id` + query scoping |
| `Visitor::creating` | Visitor model | Pass code / defaults |
| `ParkingPass::creating` | Parking pass | Pass number generation |
| `SocietyResidentProfile::creating/updated` | Resident profile | Profile sync side effects |

**Avoid adding** new model hooks for notifications or workflows — use services + automation instead.

---

## 4. MySQL-level (keep very small)

Do **not** grow a large trigger library. Maintain only:

| Trigger / event | Table(s) | Purpose |
|-----------------|----------|---------|
| `BEFORE UPDATE/DELETE` guard | `gl_journal_entries` (posted) | Financial immutability |
| `BEFORE UPDATE/DELETE` guard | `payments` (settled) | Prevent tampering after settlement |
| `AFTER INSERT/UPDATE` audit | `helpdesk_tickets`, `maintenance_invoices` | Row-level audit if direct SQL bypasses app |
| Scheduled purge | `sms_delivery_logs`, `automation_rule_runs` | Retention (or use Laravel scheduler) |

Everything else (overdue invoices, visitor overstay, birthday reminders) should stay in **Laravel commands + scheduler**, not MySQL `EVENT`.

---

## 5. What to skip (for now)

| Idea | Why skip |
|------|----------|
| MySQL trigger → send SMS/email | No Laravel context, no template engine, hard to debug |
| Trigger on every ERP table | Noise, migration pain, duplicates app logic |
| Per-tenant custom MySQL triggers | Use `automation_rules` instead |
| Denormalized counters in DB triggers | Prefer dashboard queries or cached aggregates |
| Full Zapier-style action catalog | Add actions incrementally in `AutomationEngineService` |

---

## 6. Maintenance checklist (per release)

- [ ] Every **P0** messaging event still listed in `config/messaging.php` `event_module_map`
- [ ] Demo tenant has templates for P0 events (`MessagingEventWireSeeder` / `TenantMessagingDefaultsSeeder`)
- [ ] Every automation trigger in ERP dropdown has a matching `dispatch()` in a service
- [ ] `php artisan` smoke / gate provision still seeds at least one `automation_rules` row
- [ ] No new direct `Mail::` / SMS calls — only `MessagingGatewayService`
- [ ] New features publish **one event name** (documented here) before shipping

---

## 7. File references

| File | Role |
|------|------|
| `apps/cloud/config/messaging.php` | Event → module map |
| `apps/cloud/app/Modules/Automation/Services/AutomationEngineService.php` | Rule execution |
| `apps/cloud/app/Modules/Notification/Services/MessagingGatewayService.php` | Channel dispatch |
| `apps/cloud/database/seeders/MessagingEventWireSeeder.php` | Demo templates + sample rules |
| `apps/cloud/app/Filament/Society/Resources/AutomationRuleResource.php` | Society admin UI |

---

## 8. Summary — minimum viable set

**Messaging (14 events):**  
`visitor.pending_approval`, `visitor.approved`, `visitor.checked_in`, `visitor.overstay`, `safety.sos`, `helpdesk.ticket.created`, `helpdesk.ticket.resolved`, `invoice.issued`, `billing.reminder`, `recovery.notice_sent`, `notice.published`, `amenity.booking.confirmed`, `amenity.booking.reminder`, `parking.pass.issued`

**Automation dispatch (9 triggers):**  
All wired: `helpdesk.ticket.created`, `helpdesk.ticket.resolved`, `invoice.issued`, `recovery.notice_sent`, `notice.published`, `visitor.approved`, `visitor.overstay`, `payment.received`, `amenity.booking.confirmed`

**MySQL:**  
Posted-GL guard + optional audit shadow — nothing else unless compliance requires it.

This set keeps gate, billing, helpdesk, and notices reliable without operational overhead.
