# coding: utf-8

"""
    Airflow API

    Airflow API. All endpoints located under ``/api/v2`` can be used safely, are stable and backward compatible. Endpoints located under ``/ui`` are dedicated to the UI and are subject to breaking change depending on the need of the frontend. Users should not rely on those but use the public ones instead.

    The version of the OpenAPI document: 2
    Generated by OpenAPI Generator (https://openapi-generator.tech)

    Do not edit the class manually.
"""  # noqa: E501


from __future__ import annotations
import pprint
import re  # noqa: F401
import json

from pydantic import BaseModel, ConfigDict, Field, StrictBool
from typing import Any, ClassVar, Dict, List, Optional
from typing_extensions import Annotated
from airflow_client.client.models.task_instance_state import TaskInstanceState
from typing import Optional, Set
from typing_extensions import Self

class PatchTaskInstanceBody(BaseModel):
    """
    Request body for Clear Task Instances endpoint.
    """ # noqa: E501
    include_downstream: Optional[StrictBool] = False
    include_future: Optional[StrictBool] = False
    include_past: Optional[StrictBool] = False
    include_upstream: Optional[StrictBool] = False
    new_state: Optional[TaskInstanceState] = None
    note: Optional[Annotated[str, Field(strict=True, max_length=1000)]] = None
    __properties: ClassVar[List[str]] = ["include_downstream", "include_future", "include_past", "include_upstream", "new_state", "note"]

    model_config = ConfigDict(
        populate_by_name=True,
        validate_assignment=True,
        protected_namespaces=(),
    )


    def to_str(self) -> str:
        """Returns the string representation of the model using alias"""
        return pprint.pformat(self.model_dump(by_alias=True))

    def to_json(self) -> str:
        """Returns the JSON representation of the model using alias"""
        # TODO: pydantic v2: use .model_dump_json(by_alias=True, exclude_unset=True) instead
        return json.dumps(self.to_dict())

    @classmethod
    def from_json(cls, json_str: str) -> Optional[Self]:
        """Create an instance of PatchTaskInstanceBody from a JSON string"""
        return cls.from_dict(json.loads(json_str))

    def to_dict(self) -> Dict[str, Any]:
        """Return the dictionary representation of the model using alias.

        This has the following differences from calling pydantic's
        `self.model_dump(by_alias=True)`:

        * `None` is only added to the output dict for nullable fields that
          were set at model initialization. Other fields with value `None`
          are ignored.
        """
        excluded_fields: Set[str] = set([
        ])

        _dict = self.model_dump(
            by_alias=True,
            exclude=excluded_fields,
            exclude_none=True,
        )
        return _dict

    @classmethod
    def from_dict(cls, obj: Optional[Dict[str, Any]]) -> Optional[Self]:
        """Create an instance of PatchTaskInstanceBody from a dict"""
        if obj is None:
            return None

        if not isinstance(obj, dict):
            return cls.model_validate(obj)

        _obj = cls.model_validate({
            "include_downstream": obj.get("include_downstream") if obj.get("include_downstream") is not None else False,
            "include_future": obj.get("include_future") if obj.get("include_future") is not None else False,
            "include_past": obj.get("include_past") if obj.get("include_past") is not None else False,
            "include_upstream": obj.get("include_upstream") if obj.get("include_upstream") is not None else False,
            "new_state": obj.get("new_state"),
            "note": obj.get("note")
        })
        return _obj


