"""Code generated by Speakeasy (https://speakeasy.com). DO NOT EDIT."""

from __future__ import annotations
from .eventpaginatedresult import EventPaginatedResult, EventPaginatedResultTypedDict
from datetime import datetime
from enum import Enum
from outpost_sdk.types import BaseModel, UNSET_SENTINEL
from outpost_sdk.utils import FieldMetadata, QueryParamMetadata
import pydantic
from pydantic import model_serializer
from typing import Callable, List, Optional, Union
from typing_extensions import Annotated, NotRequired, TypeAliasType, TypedDict


ListEventsIDTypedDict = TypeAliasType("ListEventsIDTypedDict", Union[str, List[str]])
r"""Filter events by ID(s). Use bracket notation for multiple values (e.g., `id[0]=abc&id[1]=def`)."""


ListEventsID = TypeAliasType("ListEventsID", Union[str, List[str]])
r"""Filter events by ID(s). Use bracket notation for multiple values (e.g., `id[0]=abc&id[1]=def`)."""


ListEventsTenantIDTypedDict = TypeAliasType(
    "ListEventsTenantIDTypedDict", Union[str, List[str]]
)
r"""Filter events by tenant ID(s). Use bracket notation for multiple values (e.g., `tenant_id[0]=t1&tenant_id[1]=t2`).
When authenticated with a Tenant JWT, this parameter is ignored and the JWT's tenant is used.
If not provided with API key auth, returns events from all tenants.

"""


ListEventsTenantID = TypeAliasType("ListEventsTenantID", Union[str, List[str]])
r"""Filter events by tenant ID(s). Use bracket notation for multiple values (e.g., `tenant_id[0]=t1&tenant_id[1]=t2`).
When authenticated with a Tenant JWT, this parameter is ignored and the JWT's tenant is used.
If not provided with API key auth, returns events from all tenants.

"""


ListEventsTopicTypedDict = TypeAliasType(
    "ListEventsTopicTypedDict", Union[str, List[str]]
)
r"""Filter events by topic(s). Use bracket notation for multiple values (e.g., `topic[0]=user.created&topic[1]=user.updated`)."""


ListEventsTopic = TypeAliasType("ListEventsTopic", Union[str, List[str]])
r"""Filter events by topic(s). Use bracket notation for multiple values (e.g., `topic[0]=user.created&topic[1]=user.updated`)."""


class ListEventsOrderBy(str, Enum):
    r"""Field to sort by."""

    TIME = "time"


class ListEventsDir(str, Enum):
    r"""Sort direction."""

    ASC = "asc"
    DESC = "desc"


class ListEventsRequestTypedDict(TypedDict):
    id: NotRequired[ListEventsIDTypedDict]
    r"""Filter events by ID(s). Use bracket notation for multiple values (e.g., `id[0]=abc&id[1]=def`)."""
    tenant_id: NotRequired[ListEventsTenantIDTypedDict]
    r"""Filter events by tenant ID(s). Use bracket notation for multiple values (e.g., `tenant_id[0]=t1&tenant_id[1]=t2`).
    When authenticated with a Tenant JWT, this parameter is ignored and the JWT's tenant is used.
    If not provided with API key auth, returns events from all tenants.

    """
    topic: NotRequired[ListEventsTopicTypedDict]
    r"""Filter events by topic(s). Use bracket notation for multiple values (e.g., `topic[0]=user.created&topic[1]=user.updated`)."""
    time_gte: NotRequired[datetime]
    r"""Filter events with time >= value (RFC3339 or YYYY-MM-DD format)."""
    time_lte: NotRequired[datetime]
    r"""Filter events with time <= value (RFC3339 or YYYY-MM-DD format)."""
    time_gt: NotRequired[datetime]
    r"""Filter events with time > value (RFC3339 or YYYY-MM-DD format)."""
    time_lt: NotRequired[datetime]
    r"""Filter events with time < value (RFC3339 or YYYY-MM-DD format)."""
    limit: NotRequired[int]
    r"""Number of items per page (default 100, max 1000)."""
    next_cursor: NotRequired[str]
    r"""Cursor for next page of results."""
    prev_cursor: NotRequired[str]
    r"""Cursor for previous page of results."""
    order_by: NotRequired[ListEventsOrderBy]
    r"""Field to sort by."""
    direction: NotRequired[ListEventsDir]
    r"""Sort direction."""


class ListEventsRequest(BaseModel):
    id: Annotated[
        Optional[ListEventsID],
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = None
    r"""Filter events by ID(s). Use bracket notation for multiple values (e.g., `id[0]=abc&id[1]=def`)."""

    tenant_id: Annotated[
        Optional[ListEventsTenantID],
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = None
    r"""Filter events by tenant ID(s). Use bracket notation for multiple values (e.g., `tenant_id[0]=t1&tenant_id[1]=t2`).
    When authenticated with a Tenant JWT, this parameter is ignored and the JWT's tenant is used.
    If not provided with API key auth, returns events from all tenants.

    """

    topic: Annotated[
        Optional[ListEventsTopic],
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = None
    r"""Filter events by topic(s). Use bracket notation for multiple values (e.g., `topic[0]=user.created&topic[1]=user.updated`)."""

    time_gte: Annotated[
        Optional[datetime],
        pydantic.Field(alias="time[gte]"),
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = None
    r"""Filter events with time >= value (RFC3339 or YYYY-MM-DD format)."""

    time_lte: Annotated[
        Optional[datetime],
        pydantic.Field(alias="time[lte]"),
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = None
    r"""Filter events with time <= value (RFC3339 or YYYY-MM-DD format)."""

    time_gt: Annotated[
        Optional[datetime],
        pydantic.Field(alias="time[gt]"),
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = None
    r"""Filter events with time > value (RFC3339 or YYYY-MM-DD format)."""

    time_lt: Annotated[
        Optional[datetime],
        pydantic.Field(alias="time[lt]"),
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = None
    r"""Filter events with time < value (RFC3339 or YYYY-MM-DD format)."""

    limit: Annotated[
        Optional[int],
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = 100
    r"""Number of items per page (default 100, max 1000)."""

    next_cursor: Annotated[
        Optional[str],
        pydantic.Field(alias="next"),
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = None
    r"""Cursor for next page of results."""

    prev_cursor: Annotated[
        Optional[str],
        pydantic.Field(alias="prev"),
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = None
    r"""Cursor for previous page of results."""

    order_by: Annotated[
        Optional[ListEventsOrderBy],
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = ListEventsOrderBy.TIME
    r"""Field to sort by."""

    direction: Annotated[
        Optional[ListEventsDir],
        pydantic.Field(alias="dir"),
        FieldMetadata(query=QueryParamMetadata(style="form", explode=True)),
    ] = ListEventsDir.DESC
    r"""Sort direction."""

    @model_serializer(mode="wrap")
    def serialize_model(self, handler):
        optional_fields = set(
            [
                "id",
                "tenant_id",
                "topic",
                "time[gte]",
                "time[lte]",
                "time[gt]",
                "time[lt]",
                "limit",
                "next_cursor",
                "prev_cursor",
                "order_by",
                "direction",
            ]
        )
        serialized = handler(self)
        m = {}

        for n, f in type(self).model_fields.items():
            k = f.alias or n
            val = serialized.get(k, serialized.get(n))

            if val != UNSET_SENTINEL:
                if val is not None or k not in optional_fields:
                    m[k] = val

        return m


class ListEventsResponseTypedDict(TypedDict):
    result: EventPaginatedResultTypedDict


class ListEventsResponse(BaseModel):
    next: Callable[[], Optional[ListEventsResponse]]

    result: EventPaginatedResult
