from typing import Hashable, Iterable, List, Optional

from django.conf import settings
from django.contrib.auth.validators import ASCIIUsernameValidator
from django.core.exceptions import ValidationError
from django.utils.translation import gettext_lazy as _


def validate_unique_elements(it: [Iterable, Hashable], error_message: Optional[str] = None) -> Iterable:
    if len(it) != len(set(it)):
        raise ValidationError(
            _('элементы коллекции {} должны быть уникальны').format(it)
            if error_message is None
            else error_message.format(it),
            code='unique',
        )

    return it


def list_of_logins_validator(logins: List[str]) -> List:
    if not isinstance(logins, list):
        raise ValidationError(_("не является списком"))

    if not logins:
        raise ValidationError(_("пустой список логинов"))

    if settings.MAX_USERS_IN_COHORT != 0 and len(logins) > settings.MAX_USERS_IN_COHORT:
        raise ValidationError(_(f"в когорте может быть не более {settings.MAX_USERS_IN_COHORT} пользователей"))

    invalid_logins = []
    login_validator = ASCIIUsernameValidator()
    for login in logins:
        try:
            if login is None:
                raise ValidationError(_("логин не должен быть пустым"))
            login_validator(login)
        except ValidationError:
            invalid_logins.append(login)

    if invalid_logins:
        raise ValidationError({'invalid_logins': invalid_logins})

    return logins
