<?php

namespace MintyPHP\Module\Notifications\Listeners;

use MintyPHP\App\Module\Contracts\EventListener;
use MintyPHP\Module\Notifications\Service\NotificationMessage;
use MintyPHP\Module\Notifications\Service\NotificationService;
use MintyPHP\Repository\User\UserReadRepositoryInterface;
use MintyPHP\Service\Access\PermissionService;

final class UserAssignmentChangedNotificationListener implements EventListener
{
    use NotificationListenerTrait;

    public function __construct(
        private readonly NotificationService $notificationService,
        private readonly UserReadRepositoryInterface $userReadRepository
    ) {
    }

    public function handle(string $event, array $payload): void
    {
        $userId = (int) ($payload['user_id'] ?? 0);
        if ($userId <= 0) {
            return;
        }

        $actorUserId = isset($payload['actor_user_id']) ? (int) $payload['actor_user_id'] : null;
        $user = $this->userReadRepository->find($userId);
        $displayName = $this->resolveDisplayName($payload, $user, $userId);
        $uuid = $this->resolveUuid($payload, $user);

        $tenantIds = $this->sanitizeTenantIds($payload['tenant_ids'] ?? []);
        $changes = is_array($payload['changes'] ?? null) ? $payload['changes'] : [];
        $link = $uuid !== '' ? 'admin/users/edit/' . $uuid : null;
        $message = NotificationMessage::localized(
            'user.assignment_changed',
            'User assignments updated: %s',
            [$displayName],
            'Tenant, role, or department assignments were changed.',
            [],
            $link,
            [
            'user_id' => $userId,
            'uuid' => $uuid,
            'changes' => $changes,
            ]
        );

        if ($actorUserId === null || $actorUserId !== $userId) {
            $this->notificationService->createFromMessage(
                $userId,
                null,
                $message
            );
        }

        if ($tenantIds === []) {
            return;
        }

        $adminUserIds = $this->userReadRepository->listPrivilegedUserIdsByPermissionKeys(
            [PermissionService::USERS_UPDATE_ASSIGNMENTS]
        );
        if ($adminUserIds === []) {
            return;
        }
        $adminSet = array_fill_keys(array_map('intval', $adminUserIds), true);

        foreach ($tenantIds as $tenantId) {
            $this->notificationService->createForTenantAdminUsersFromMessage(
                $tenantId,
                $message,
                $actorUserId,
                $adminSet
            );
        }
    }
}
