from datetime import datetime

from pydantic import BaseModel


class Resource(BaseModel, frozen=True):

    id: int | None = None


_TYPE_TO_PATH: dict = {}

_PATH_TO_TYPE: dict = {}


def register_type(label: str, t):
    _PATH_TO_TYPE[label] = t
    _TYPE_TO_PATH[t.__name__] = label


def get_path_from_item(resource: Resource) -> str:
    return _TYPE_TO_PATH[type(resource).__name__]


def get_path_from_type(item_t) -> str:
    return _TYPE_TO_PATH[item_t.__name__]


def get_type(path: str):
    return _PATH_TO_TYPE[path]


class Identifiable(Resource, frozen=True):
    url: str | None = None


class Timestamped(Identifiable, frozen=True):
    created_at: datetime | None = None
    updated_at: datetime | None = None


class Member(Timestamped, frozen=True):
    username: str
    email: str
    first_name: str
    last_name: str | None = None
    phone: str | None = None
    organizations: list[str] = []
    profile_url: str | None = None
    profile_thumbnail_url: str | None = None
    all_permissions: list[str] = []


class Group(Timestamped, frozen=True):
    name: str


class Address(Timestamped, frozen=True):
    line1: str
    line2: str | None
    line3: str | None
    city: str | None
    region: str
    postcode: str | None
    country: str


class Organization(Timestamped, frozen=True):
    name: str
    acronym: str | None = None
    description: str | None = None
    address: Address
    website: str | None = None


register_type("members", Member)
register_type("groups", Group)
register_type("organizations", Organization)
