# Настройка Amazon SES Webhook для обработки событий

## Обзор

Система интегрирована с Amazon SES для обработки событий отправки писем через SNS webhooks. Это позволяет:

- Автоматически блокировать отправку на невалидные email адреса
- Отслеживать жалобы (complaints) и блокировать проблемные адреса
- Логировать все события доставки
- Мониторить complaint rate и получать уведомления

## Компоненты системы

### 1. Таблица `email_events`

Хранит все события от SES:
- `email` - адрес получателя
- `message_id` - SES Message-ID
- `event_type` - тип события (bounce, complaint, delivery, reject, send)
- `raw_payload` - полный JSON payload от SNS
- `created_at` - время создания

### 2. Поля в таблице `users`

- `email_invalid` (boolean) - помечает email как невалидный (permanent bounce)
- `email_complaint` (boolean) - помечает email как имеющий жалобу

### 3. Контроллер `SesWebhookController`

Обрабатывает webhook запросы от Amazon SNS:
- Подтверждает подписку SNS
- Обрабатывает уведомления о событиях SES
- Сохраняет события в базу данных
- Обновляет флаги валидации email в таблице users

### 4. Сервис `EmailValidationService`

Проверяет email перед отправкой:
- Проверяет флаги `email_invalid` и `email_complaint`
- Блокирует отправку на заблокированные адреса
- Логирует попытки отправки на заблокированные адреса

### 5. Listener `LogSesMessageId`

Логирует Message-ID после отправки письма через Laravel Mail facade.

## Настройка в AWS

### Шаг 1: Создать Configuration Set в SES

1. Перейдите в Amazon SES Console
2. Выберите "Configuration sets" → "Create configuration set"
3. Имя: `prod-events`
4. Включите для отправки

### Шаг 2: Создать Event Destination

1. В созданном Configuration Set выберите "Event destinations" → "Add destination"
2. Тип: SNS
3. Выберите события:
   - Send
   - Delivery
   - Bounce
   - Complaint
   - Reject
4. Topic: создайте новый SNS topic (например: `ses-prod-events`)

### Шаг 3: Создать HTTP subscription в SNS

1. Перейдите в SNS Console
2. Выберите созданный topic `ses-prod-events`
3. "Create subscription"
4. Protocol: HTTPS
5. Endpoint: `https://kartulirest.de/api/webhooks/ses`
6. Сохраните

### Шаг 4: Подтвердить подписку

После создания подписки SNS отправит запрос на подтверждение. Система автоматически подтвердит подписку при первом запросе.

## Использование

### Проверка email перед отправкой

Система автоматически проверяет email перед отправкой через `EmailMailerSendService`:

```php
// Автоматически проверяется перед отправкой
$emailService = new EmailMailerSendService();
$emailService->sendEmail($toEmail, $toName, $subject, $htmlContent);
```

Если email заблокирован, отправка не произойдет и будет залогировано предупреждение.

### Использование базового Mailable класса

Для добавления заголовков Reply-To и List-Unsubscribe используйте `BaseMailable`:

```php
use App\Mail\BaseMailable;

class OrderConfirmationMail extends BaseMailable
{
    // ...
}
```

### Мониторинг жалоб

Система автоматически проверяет complaint rate при каждом новом complaint событии. Если rate превышает 0.1%, в лог записывается критическое сообщение.

Для настройки уведомлений администратору (Slack/Email) можно расширить метод `checkComplaintRate()` в `SesWebhookController`.

## Миграции

Выполните миграции для создания таблиц и полей:

```bash
php artisan migrate
```

## Тестирование

### Тест webhook endpoint

```bash
curl -X POST https://kartulirest.de/api/webhooks/ses \
  -H "Content-Type: application/json" \
  -H "User-Agent: Amazon Simple Notification Service" \
  -d '{
    "Type": "SubscriptionConfirmation",
    "SubscribeURL": "https://sns.eu-central-1.amazonaws.com/..."
  }'
```

### Проверка блокировки email

```php
use App\Services\EmailValidationService;

$service = app(EmailValidationService::class);
$canSend = $service->canSendEmail('test@example.com');
```

## Безопасность

- Webhook endpoint проверяет User-Agent (должен содержать "Amazon Simple Notification Service")
- Проверяется структура JSON запроса
- Endpoint исключен из CSRF проверки (как и Stripe webhook)

## Логирование

Все события логируются в Laravel log:
- Подтверждение подписки SNS
- Обработка событий SES
- Блокировка отправки на невалидные email
- Критические события (высокий complaint rate)

## Дополнительные настройки

### Настройка Reply-To и List-Unsubscribe

В `config/mail.php` можно добавить:

```php
'reply_to' => [
    'address' => env('MAIL_REPLY_TO_ADDRESS', 'noreply@kartulirest.de'),
    'name' => env('MAIL_REPLY_TO_NAME', 'KartuliDe Restaurant'),
],
```

### Настройка unsubscribe URL

В `.env`:

```env
APP_URL=https://kartulirest.de
```

Unsubscribe URL будет автоматически формироваться как `{APP_URL}/unsubscribe`.
