# 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

import warnings
from pydantic import validate_call, Field, StrictFloat, StrictStr, StrictInt
from typing import Any, Dict, List, Optional, Tuple, Union
from typing_extensions import Annotated

from datetime import datetime
from pydantic import Field, StrictBool, StrictStr, field_validator
from typing import Any, List, Optional
from typing_extensions import Annotated
from airflow_client.client.models.dag_collection_response import DAGCollectionResponse
from airflow_client.client.models.dag_details_response import DAGDetailsResponse
from airflow_client.client.models.dag_patch_body import DAGPatchBody
from airflow_client.client.models.dag_response import DAGResponse
from airflow_client.client.models.dag_tag_collection_response import DAGTagCollectionResponse
from airflow_client.client.models.dag_run_state import DagRunState

from airflow_client.client.api_client import ApiClient, RequestSerialized
from airflow_client.client.api_response import ApiResponse
from airflow_client.client.rest import RESTResponseType


class DAGApi:
    """NOTE: This class is auto generated by OpenAPI Generator
    Ref: https://openapi-generator.tech

    Do not edit the class manually.
    """

    def __init__(self, api_client=None) -> None:
        if api_client is None:
            api_client = ApiClient.get_default()
        self.api_client = api_client


    @validate_call
    def delete_dag(
        self,
        dag_id: StrictStr,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> object:
        """Delete Dag

        Delete the specific DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._delete_dag_serialize(
            dag_id=dag_id,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "object",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPExceptionResponse",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        ).data


    @validate_call
    def delete_dag_with_http_info(
        self,
        dag_id: StrictStr,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> ApiResponse[object]:
        """Delete Dag

        Delete the specific DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._delete_dag_serialize(
            dag_id=dag_id,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "object",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPExceptionResponse",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        )


    @validate_call
    def delete_dag_without_preload_content(
        self,
        dag_id: StrictStr,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> RESTResponseType:
        """Delete Dag

        Delete the specific DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._delete_dag_serialize(
            dag_id=dag_id,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "object",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPExceptionResponse",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        return response_data.response


    def _delete_dag_serialize(
        self,
        dag_id,
        _request_auth,
        _content_type,
        _headers,
        _host_index,
    ) -> RequestSerialized:

        _host = None

        _collection_formats: Dict[str, str] = {
        }

        _path_params: Dict[str, str] = {}
        _query_params: List[Tuple[str, str]] = []
        _header_params: Dict[str, Optional[str]] = _headers or {}
        _form_params: List[Tuple[str, str]] = []
        _files: Dict[
            str, Union[str, bytes, List[str], List[bytes], List[Tuple[str, bytes]]]
        ] = {}
        _body_params: Optional[bytes] = None

        # process the path parameters
        if dag_id is not None:
            _path_params['dag_id'] = dag_id
        # process the query parameters
        # process the header parameters
        # process the form parameters
        # process the body parameter


        # set the HTTP header `Accept`
        if 'Accept' not in _header_params:
            _header_params['Accept'] = self.api_client.select_header_accept(
                [
                    'application/json'
                ]
            )


        # authentication setting
        _auth_settings: List[str] = [
            'OAuth2PasswordBearer'
        ]

        return self.api_client.param_serialize(
            method='DELETE',
            resource_path='/api/v2/dags/{dag_id}',
            path_params=_path_params,
            query_params=_query_params,
            header_params=_header_params,
            body=_body_params,
            post_params=_form_params,
            files=_files,
            auth_settings=_auth_settings,
            collection_formats=_collection_formats,
            _host=_host,
            _request_auth=_request_auth
        )




    @validate_call
    def get_dag(
        self,
        dag_id: StrictStr,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> DAGResponse:
        """Get Dag

        Get basic information about a DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dag_serialize(
            dag_id=dag_id,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPExceptionResponse",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        ).data


    @validate_call
    def get_dag_with_http_info(
        self,
        dag_id: StrictStr,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> ApiResponse[DAGResponse]:
        """Get Dag

        Get basic information about a DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dag_serialize(
            dag_id=dag_id,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPExceptionResponse",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        )


    @validate_call
    def get_dag_without_preload_content(
        self,
        dag_id: StrictStr,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> RESTResponseType:
        """Get Dag

        Get basic information about a DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dag_serialize(
            dag_id=dag_id,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPExceptionResponse",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        return response_data.response


    def _get_dag_serialize(
        self,
        dag_id,
        _request_auth,
        _content_type,
        _headers,
        _host_index,
    ) -> RequestSerialized:

        _host = None

        _collection_formats: Dict[str, str] = {
        }

        _path_params: Dict[str, str] = {}
        _query_params: List[Tuple[str, str]] = []
        _header_params: Dict[str, Optional[str]] = _headers or {}
        _form_params: List[Tuple[str, str]] = []
        _files: Dict[
            str, Union[str, bytes, List[str], List[bytes], List[Tuple[str, bytes]]]
        ] = {}
        _body_params: Optional[bytes] = None

        # process the path parameters
        if dag_id is not None:
            _path_params['dag_id'] = dag_id
        # process the query parameters
        # process the header parameters
        # process the form parameters
        # process the body parameter


        # set the HTTP header `Accept`
        if 'Accept' not in _header_params:
            _header_params['Accept'] = self.api_client.select_header_accept(
                [
                    'application/json'
                ]
            )


        # authentication setting
        _auth_settings: List[str] = [
            'OAuth2PasswordBearer'
        ]

        return self.api_client.param_serialize(
            method='GET',
            resource_path='/api/v2/dags/{dag_id}',
            path_params=_path_params,
            query_params=_query_params,
            header_params=_header_params,
            body=_body_params,
            post_params=_form_params,
            files=_files,
            auth_settings=_auth_settings,
            collection_formats=_collection_formats,
            _host=_host,
            _request_auth=_request_auth
        )




    @validate_call
    def get_dag_details(
        self,
        dag_id: StrictStr,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> DAGDetailsResponse:
        """Get Dag Details

        Get details of DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dag_details_serialize(
            dag_id=dag_id,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGDetailsResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        ).data


    @validate_call
    def get_dag_details_with_http_info(
        self,
        dag_id: StrictStr,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> ApiResponse[DAGDetailsResponse]:
        """Get Dag Details

        Get details of DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dag_details_serialize(
            dag_id=dag_id,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGDetailsResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        )


    @validate_call
    def get_dag_details_without_preload_content(
        self,
        dag_id: StrictStr,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> RESTResponseType:
        """Get Dag Details

        Get details of DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dag_details_serialize(
            dag_id=dag_id,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGDetailsResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        return response_data.response


    def _get_dag_details_serialize(
        self,
        dag_id,
        _request_auth,
        _content_type,
        _headers,
        _host_index,
    ) -> RequestSerialized:

        _host = None

        _collection_formats: Dict[str, str] = {
        }

        _path_params: Dict[str, str] = {}
        _query_params: List[Tuple[str, str]] = []
        _header_params: Dict[str, Optional[str]] = _headers or {}
        _form_params: List[Tuple[str, str]] = []
        _files: Dict[
            str, Union[str, bytes, List[str], List[bytes], List[Tuple[str, bytes]]]
        ] = {}
        _body_params: Optional[bytes] = None

        # process the path parameters
        if dag_id is not None:
            _path_params['dag_id'] = dag_id
        # process the query parameters
        # process the header parameters
        # process the form parameters
        # process the body parameter


        # set the HTTP header `Accept`
        if 'Accept' not in _header_params:
            _header_params['Accept'] = self.api_client.select_header_accept(
                [
                    'application/json'
                ]
            )


        # authentication setting
        _auth_settings: List[str] = [
            'OAuth2PasswordBearer'
        ]

        return self.api_client.param_serialize(
            method='GET',
            resource_path='/api/v2/dags/{dag_id}/details',
            path_params=_path_params,
            query_params=_query_params,
            header_params=_header_params,
            body=_body_params,
            post_params=_form_params,
            files=_files,
            auth_settings=_auth_settings,
            collection_formats=_collection_formats,
            _host=_host,
            _request_auth=_request_auth
        )




    @validate_call
    def get_dag_tags(
        self,
        limit: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        offset: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        order_by: Optional[StrictStr] = None,
        tag_name_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> DAGTagCollectionResponse:
        """Get Dag Tags

        Get all DAG tags.

        :param limit:
        :type limit: int
        :param offset:
        :type offset: int
        :param order_by:
        :type order_by: str
        :param tag_name_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type tag_name_pattern: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dag_tags_serialize(
            limit=limit,
            offset=offset,
            order_by=order_by,
            tag_name_pattern=tag_name_pattern,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGTagCollectionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        ).data


    @validate_call
    def get_dag_tags_with_http_info(
        self,
        limit: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        offset: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        order_by: Optional[StrictStr] = None,
        tag_name_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> ApiResponse[DAGTagCollectionResponse]:
        """Get Dag Tags

        Get all DAG tags.

        :param limit:
        :type limit: int
        :param offset:
        :type offset: int
        :param order_by:
        :type order_by: str
        :param tag_name_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type tag_name_pattern: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dag_tags_serialize(
            limit=limit,
            offset=offset,
            order_by=order_by,
            tag_name_pattern=tag_name_pattern,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGTagCollectionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        )


    @validate_call
    def get_dag_tags_without_preload_content(
        self,
        limit: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        offset: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        order_by: Optional[StrictStr] = None,
        tag_name_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> RESTResponseType:
        """Get Dag Tags

        Get all DAG tags.

        :param limit:
        :type limit: int
        :param offset:
        :type offset: int
        :param order_by:
        :type order_by: str
        :param tag_name_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type tag_name_pattern: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dag_tags_serialize(
            limit=limit,
            offset=offset,
            order_by=order_by,
            tag_name_pattern=tag_name_pattern,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGTagCollectionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        return response_data.response


    def _get_dag_tags_serialize(
        self,
        limit,
        offset,
        order_by,
        tag_name_pattern,
        _request_auth,
        _content_type,
        _headers,
        _host_index,
    ) -> RequestSerialized:

        _host = None

        _collection_formats: Dict[str, str] = {
        }

        _path_params: Dict[str, str] = {}
        _query_params: List[Tuple[str, str]] = []
        _header_params: Dict[str, Optional[str]] = _headers or {}
        _form_params: List[Tuple[str, str]] = []
        _files: Dict[
            str, Union[str, bytes, List[str], List[bytes], List[Tuple[str, bytes]]]
        ] = {}
        _body_params: Optional[bytes] = None

        # process the path parameters
        # process the query parameters
        if limit is not None:
            
            _query_params.append(('limit', limit))
            
        if offset is not None:
            
            _query_params.append(('offset', offset))
            
        if order_by is not None:
            
            _query_params.append(('order_by', order_by))
            
        if tag_name_pattern is not None:
            
            _query_params.append(('tag_name_pattern', tag_name_pattern))
            
        # process the header parameters
        # process the form parameters
        # process the body parameter


        # set the HTTP header `Accept`
        if 'Accept' not in _header_params:
            _header_params['Accept'] = self.api_client.select_header_accept(
                [
                    'application/json'
                ]
            )


        # authentication setting
        _auth_settings: List[str] = [
            'OAuth2PasswordBearer'
        ]

        return self.api_client.param_serialize(
            method='GET',
            resource_path='/api/v2/dagTags',
            path_params=_path_params,
            query_params=_query_params,
            header_params=_header_params,
            body=_body_params,
            post_params=_form_params,
            files=_files,
            auth_settings=_auth_settings,
            collection_formats=_collection_formats,
            _host=_host,
            _request_auth=_request_auth
        )




    @validate_call
    def get_dags(
        self,
        limit: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        offset: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        tags: Optional[List[StrictStr]] = None,
        tags_match_mode: Optional[StrictStr] = None,
        owners: Optional[List[StrictStr]] = None,
        dag_id_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        dag_display_name_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        exclude_stale: Optional[StrictBool] = None,
        paused: Optional[StrictBool] = None,
        last_dag_run_state: Optional[DagRunState] = None,
        dag_run_start_date_gte: Optional[datetime] = None,
        dag_run_start_date_lte: Optional[datetime] = None,
        dag_run_end_date_gte: Optional[datetime] = None,
        dag_run_end_date_lte: Optional[datetime] = None,
        dag_run_state: Optional[List[StrictStr]] = None,
        order_by: Optional[StrictStr] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> DAGCollectionResponse:
        """Get Dags

        Get all DAGs.

        :param limit:
        :type limit: int
        :param offset:
        :type offset: int
        :param tags:
        :type tags: List[str]
        :param tags_match_mode:
        :type tags_match_mode: str
        :param owners:
        :type owners: List[str]
        :param dag_id_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type dag_id_pattern: str
        :param dag_display_name_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type dag_display_name_pattern: str
        :param exclude_stale:
        :type exclude_stale: bool
        :param paused:
        :type paused: bool
        :param last_dag_run_state:
        :type last_dag_run_state: DagRunState
        :param dag_run_start_date_gte:
        :type dag_run_start_date_gte: datetime
        :param dag_run_start_date_lte:
        :type dag_run_start_date_lte: datetime
        :param dag_run_end_date_gte:
        :type dag_run_end_date_gte: datetime
        :param dag_run_end_date_lte:
        :type dag_run_end_date_lte: datetime
        :param dag_run_state:
        :type dag_run_state: List[str]
        :param order_by:
        :type order_by: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dags_serialize(
            limit=limit,
            offset=offset,
            tags=tags,
            tags_match_mode=tags_match_mode,
            owners=owners,
            dag_id_pattern=dag_id_pattern,
            dag_display_name_pattern=dag_display_name_pattern,
            exclude_stale=exclude_stale,
            paused=paused,
            last_dag_run_state=last_dag_run_state,
            dag_run_start_date_gte=dag_run_start_date_gte,
            dag_run_start_date_lte=dag_run_start_date_lte,
            dag_run_end_date_gte=dag_run_end_date_gte,
            dag_run_end_date_lte=dag_run_end_date_lte,
            dag_run_state=dag_run_state,
            order_by=order_by,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGCollectionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        ).data


    @validate_call
    def get_dags_with_http_info(
        self,
        limit: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        offset: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        tags: Optional[List[StrictStr]] = None,
        tags_match_mode: Optional[StrictStr] = None,
        owners: Optional[List[StrictStr]] = None,
        dag_id_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        dag_display_name_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        exclude_stale: Optional[StrictBool] = None,
        paused: Optional[StrictBool] = None,
        last_dag_run_state: Optional[DagRunState] = None,
        dag_run_start_date_gte: Optional[datetime] = None,
        dag_run_start_date_lte: Optional[datetime] = None,
        dag_run_end_date_gte: Optional[datetime] = None,
        dag_run_end_date_lte: Optional[datetime] = None,
        dag_run_state: Optional[List[StrictStr]] = None,
        order_by: Optional[StrictStr] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> ApiResponse[DAGCollectionResponse]:
        """Get Dags

        Get all DAGs.

        :param limit:
        :type limit: int
        :param offset:
        :type offset: int
        :param tags:
        :type tags: List[str]
        :param tags_match_mode:
        :type tags_match_mode: str
        :param owners:
        :type owners: List[str]
        :param dag_id_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type dag_id_pattern: str
        :param dag_display_name_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type dag_display_name_pattern: str
        :param exclude_stale:
        :type exclude_stale: bool
        :param paused:
        :type paused: bool
        :param last_dag_run_state:
        :type last_dag_run_state: DagRunState
        :param dag_run_start_date_gte:
        :type dag_run_start_date_gte: datetime
        :param dag_run_start_date_lte:
        :type dag_run_start_date_lte: datetime
        :param dag_run_end_date_gte:
        :type dag_run_end_date_gte: datetime
        :param dag_run_end_date_lte:
        :type dag_run_end_date_lte: datetime
        :param dag_run_state:
        :type dag_run_state: List[str]
        :param order_by:
        :type order_by: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dags_serialize(
            limit=limit,
            offset=offset,
            tags=tags,
            tags_match_mode=tags_match_mode,
            owners=owners,
            dag_id_pattern=dag_id_pattern,
            dag_display_name_pattern=dag_display_name_pattern,
            exclude_stale=exclude_stale,
            paused=paused,
            last_dag_run_state=last_dag_run_state,
            dag_run_start_date_gte=dag_run_start_date_gte,
            dag_run_start_date_lte=dag_run_start_date_lte,
            dag_run_end_date_gte=dag_run_end_date_gte,
            dag_run_end_date_lte=dag_run_end_date_lte,
            dag_run_state=dag_run_state,
            order_by=order_by,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGCollectionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        )


    @validate_call
    def get_dags_without_preload_content(
        self,
        limit: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        offset: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        tags: Optional[List[StrictStr]] = None,
        tags_match_mode: Optional[StrictStr] = None,
        owners: Optional[List[StrictStr]] = None,
        dag_id_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        dag_display_name_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        exclude_stale: Optional[StrictBool] = None,
        paused: Optional[StrictBool] = None,
        last_dag_run_state: Optional[DagRunState] = None,
        dag_run_start_date_gte: Optional[datetime] = None,
        dag_run_start_date_lte: Optional[datetime] = None,
        dag_run_end_date_gte: Optional[datetime] = None,
        dag_run_end_date_lte: Optional[datetime] = None,
        dag_run_state: Optional[List[StrictStr]] = None,
        order_by: Optional[StrictStr] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> RESTResponseType:
        """Get Dags

        Get all DAGs.

        :param limit:
        :type limit: int
        :param offset:
        :type offset: int
        :param tags:
        :type tags: List[str]
        :param tags_match_mode:
        :type tags_match_mode: str
        :param owners:
        :type owners: List[str]
        :param dag_id_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type dag_id_pattern: str
        :param dag_display_name_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type dag_display_name_pattern: str
        :param exclude_stale:
        :type exclude_stale: bool
        :param paused:
        :type paused: bool
        :param last_dag_run_state:
        :type last_dag_run_state: DagRunState
        :param dag_run_start_date_gte:
        :type dag_run_start_date_gte: datetime
        :param dag_run_start_date_lte:
        :type dag_run_start_date_lte: datetime
        :param dag_run_end_date_gte:
        :type dag_run_end_date_gte: datetime
        :param dag_run_end_date_lte:
        :type dag_run_end_date_lte: datetime
        :param dag_run_state:
        :type dag_run_state: List[str]
        :param order_by:
        :type order_by: str
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._get_dags_serialize(
            limit=limit,
            offset=offset,
            tags=tags,
            tags_match_mode=tags_match_mode,
            owners=owners,
            dag_id_pattern=dag_id_pattern,
            dag_display_name_pattern=dag_display_name_pattern,
            exclude_stale=exclude_stale,
            paused=paused,
            last_dag_run_state=last_dag_run_state,
            dag_run_start_date_gte=dag_run_start_date_gte,
            dag_run_start_date_lte=dag_run_start_date_lte,
            dag_run_end_date_gte=dag_run_end_date_gte,
            dag_run_end_date_lte=dag_run_end_date_lte,
            dag_run_state=dag_run_state,
            order_by=order_by,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGCollectionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        return response_data.response


    def _get_dags_serialize(
        self,
        limit,
        offset,
        tags,
        tags_match_mode,
        owners,
        dag_id_pattern,
        dag_display_name_pattern,
        exclude_stale,
        paused,
        last_dag_run_state,
        dag_run_start_date_gte,
        dag_run_start_date_lte,
        dag_run_end_date_gte,
        dag_run_end_date_lte,
        dag_run_state,
        order_by,
        _request_auth,
        _content_type,
        _headers,
        _host_index,
    ) -> RequestSerialized:

        _host = None

        _collection_formats: Dict[str, str] = {
            'tags': 'multi',
            'owners': 'multi',
            'dag_run_state': 'multi',
        }

        _path_params: Dict[str, str] = {}
        _query_params: List[Tuple[str, str]] = []
        _header_params: Dict[str, Optional[str]] = _headers or {}
        _form_params: List[Tuple[str, str]] = []
        _files: Dict[
            str, Union[str, bytes, List[str], List[bytes], List[Tuple[str, bytes]]]
        ] = {}
        _body_params: Optional[bytes] = None

        # process the path parameters
        # process the query parameters
        if limit is not None:
            
            _query_params.append(('limit', limit))
            
        if offset is not None:
            
            _query_params.append(('offset', offset))
            
        if tags is not None:
            
            _query_params.append(('tags', tags))
            
        if tags_match_mode is not None:
            
            _query_params.append(('tags_match_mode', tags_match_mode))
            
        if owners is not None:
            
            _query_params.append(('owners', owners))
            
        if dag_id_pattern is not None:
            
            _query_params.append(('dag_id_pattern', dag_id_pattern))
            
        if dag_display_name_pattern is not None:
            
            _query_params.append(('dag_display_name_pattern', dag_display_name_pattern))
            
        if exclude_stale is not None:
            
            _query_params.append(('exclude_stale', exclude_stale))
            
        if paused is not None:
            
            _query_params.append(('paused', paused))
            
        if last_dag_run_state is not None:
            
            _query_params.append(('last_dag_run_state', last_dag_run_state.value))
            
        if dag_run_start_date_gte is not None:
            if isinstance(dag_run_start_date_gte, datetime):
                _query_params.append(
                    (
                        'dag_run_start_date_gte',
                        dag_run_start_date_gte.strftime(
                            self.api_client.configuration.datetime_format
                        )
                    )
                )
            else:
                _query_params.append(('dag_run_start_date_gte', dag_run_start_date_gte))
            
        if dag_run_start_date_lte is not None:
            if isinstance(dag_run_start_date_lte, datetime):
                _query_params.append(
                    (
                        'dag_run_start_date_lte',
                        dag_run_start_date_lte.strftime(
                            self.api_client.configuration.datetime_format
                        )
                    )
                )
            else:
                _query_params.append(('dag_run_start_date_lte', dag_run_start_date_lte))
            
        if dag_run_end_date_gte is not None:
            if isinstance(dag_run_end_date_gte, datetime):
                _query_params.append(
                    (
                        'dag_run_end_date_gte',
                        dag_run_end_date_gte.strftime(
                            self.api_client.configuration.datetime_format
                        )
                    )
                )
            else:
                _query_params.append(('dag_run_end_date_gte', dag_run_end_date_gte))
            
        if dag_run_end_date_lte is not None:
            if isinstance(dag_run_end_date_lte, datetime):
                _query_params.append(
                    (
                        'dag_run_end_date_lte',
                        dag_run_end_date_lte.strftime(
                            self.api_client.configuration.datetime_format
                        )
                    )
                )
            else:
                _query_params.append(('dag_run_end_date_lte', dag_run_end_date_lte))
            
        if dag_run_state is not None:
            
            _query_params.append(('dag_run_state', dag_run_state))
            
        if order_by is not None:
            
            _query_params.append(('order_by', order_by))
            
        # process the header parameters
        # process the form parameters
        # process the body parameter


        # set the HTTP header `Accept`
        if 'Accept' not in _header_params:
            _header_params['Accept'] = self.api_client.select_header_accept(
                [
                    'application/json'
                ]
            )


        # authentication setting
        _auth_settings: List[str] = [
            'OAuth2PasswordBearer'
        ]

        return self.api_client.param_serialize(
            method='GET',
            resource_path='/api/v2/dags',
            path_params=_path_params,
            query_params=_query_params,
            header_params=_header_params,
            body=_body_params,
            post_params=_form_params,
            files=_files,
            auth_settings=_auth_settings,
            collection_formats=_collection_formats,
            _host=_host,
            _request_auth=_request_auth
        )




    @validate_call
    def patch_dag(
        self,
        dag_id: StrictStr,
        dag_patch_body: DAGPatchBody,
        update_mask: Optional[List[StrictStr]] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> DAGResponse:
        """Patch Dag

        Patch the specific DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param dag_patch_body: (required)
        :type dag_patch_body: DAGPatchBody
        :param update_mask:
        :type update_mask: List[str]
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._patch_dag_serialize(
            dag_id=dag_id,
            dag_patch_body=dag_patch_body,
            update_mask=update_mask,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        ).data


    @validate_call
    def patch_dag_with_http_info(
        self,
        dag_id: StrictStr,
        dag_patch_body: DAGPatchBody,
        update_mask: Optional[List[StrictStr]] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> ApiResponse[DAGResponse]:
        """Patch Dag

        Patch the specific DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param dag_patch_body: (required)
        :type dag_patch_body: DAGPatchBody
        :param update_mask:
        :type update_mask: List[str]
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._patch_dag_serialize(
            dag_id=dag_id,
            dag_patch_body=dag_patch_body,
            update_mask=update_mask,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        )


    @validate_call
    def patch_dag_without_preload_content(
        self,
        dag_id: StrictStr,
        dag_patch_body: DAGPatchBody,
        update_mask: Optional[List[StrictStr]] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> RESTResponseType:
        """Patch Dag

        Patch the specific DAG.

        :param dag_id: (required)
        :type dag_id: str
        :param dag_patch_body: (required)
        :type dag_patch_body: DAGPatchBody
        :param update_mask:
        :type update_mask: List[str]
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._patch_dag_serialize(
            dag_id=dag_id,
            dag_patch_body=dag_patch_body,
            update_mask=update_mask,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        return response_data.response


    def _patch_dag_serialize(
        self,
        dag_id,
        dag_patch_body,
        update_mask,
        _request_auth,
        _content_type,
        _headers,
        _host_index,
    ) -> RequestSerialized:

        _host = None

        _collection_formats: Dict[str, str] = {
            'update_mask': 'multi',
        }

        _path_params: Dict[str, str] = {}
        _query_params: List[Tuple[str, str]] = []
        _header_params: Dict[str, Optional[str]] = _headers or {}
        _form_params: List[Tuple[str, str]] = []
        _files: Dict[
            str, Union[str, bytes, List[str], List[bytes], List[Tuple[str, bytes]]]
        ] = {}
        _body_params: Optional[bytes] = None

        # process the path parameters
        if dag_id is not None:
            _path_params['dag_id'] = dag_id
        # process the query parameters
        if update_mask is not None:
            
            _query_params.append(('update_mask', update_mask))
            
        # process the header parameters
        # process the form parameters
        # process the body parameter
        if dag_patch_body is not None:
            _body_params = dag_patch_body


        # set the HTTP header `Accept`
        if 'Accept' not in _header_params:
            _header_params['Accept'] = self.api_client.select_header_accept(
                [
                    'application/json'
                ]
            )

        # set the HTTP header `Content-Type`
        if _content_type:
            _header_params['Content-Type'] = _content_type
        else:
            _default_content_type = (
                self.api_client.select_header_content_type(
                    [
                        'application/json'
                    ]
                )
            )
            if _default_content_type is not None:
                _header_params['Content-Type'] = _default_content_type

        # authentication setting
        _auth_settings: List[str] = [
            'OAuth2PasswordBearer'
        ]

        return self.api_client.param_serialize(
            method='PATCH',
            resource_path='/api/v2/dags/{dag_id}',
            path_params=_path_params,
            query_params=_query_params,
            header_params=_header_params,
            body=_body_params,
            post_params=_form_params,
            files=_files,
            auth_settings=_auth_settings,
            collection_formats=_collection_formats,
            _host=_host,
            _request_auth=_request_auth
        )




    @validate_call
    def patch_dags(
        self,
        dag_patch_body: DAGPatchBody,
        update_mask: Optional[List[StrictStr]] = None,
        limit: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        offset: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        tags: Optional[List[StrictStr]] = None,
        tags_match_mode: Optional[StrictStr] = None,
        owners: Optional[List[StrictStr]] = None,
        dag_id_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        exclude_stale: Optional[StrictBool] = None,
        paused: Optional[StrictBool] = None,
        last_dag_run_state: Optional[DagRunState] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> DAGCollectionResponse:
        """Patch Dags

        Patch multiple DAGs.

        :param dag_patch_body: (required)
        :type dag_patch_body: DAGPatchBody
        :param update_mask:
        :type update_mask: List[str]
        :param limit:
        :type limit: int
        :param offset:
        :type offset: int
        :param tags:
        :type tags: List[str]
        :param tags_match_mode:
        :type tags_match_mode: str
        :param owners:
        :type owners: List[str]
        :param dag_id_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type dag_id_pattern: str
        :param exclude_stale:
        :type exclude_stale: bool
        :param paused:
        :type paused: bool
        :param last_dag_run_state:
        :type last_dag_run_state: DagRunState
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._patch_dags_serialize(
            dag_patch_body=dag_patch_body,
            update_mask=update_mask,
            limit=limit,
            offset=offset,
            tags=tags,
            tags_match_mode=tags_match_mode,
            owners=owners,
            dag_id_pattern=dag_id_pattern,
            exclude_stale=exclude_stale,
            paused=paused,
            last_dag_run_state=last_dag_run_state,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGCollectionResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        ).data


    @validate_call
    def patch_dags_with_http_info(
        self,
        dag_patch_body: DAGPatchBody,
        update_mask: Optional[List[StrictStr]] = None,
        limit: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        offset: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        tags: Optional[List[StrictStr]] = None,
        tags_match_mode: Optional[StrictStr] = None,
        owners: Optional[List[StrictStr]] = None,
        dag_id_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        exclude_stale: Optional[StrictBool] = None,
        paused: Optional[StrictBool] = None,
        last_dag_run_state: Optional[DagRunState] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> ApiResponse[DAGCollectionResponse]:
        """Patch Dags

        Patch multiple DAGs.

        :param dag_patch_body: (required)
        :type dag_patch_body: DAGPatchBody
        :param update_mask:
        :type update_mask: List[str]
        :param limit:
        :type limit: int
        :param offset:
        :type offset: int
        :param tags:
        :type tags: List[str]
        :param tags_match_mode:
        :type tags_match_mode: str
        :param owners:
        :type owners: List[str]
        :param dag_id_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type dag_id_pattern: str
        :param exclude_stale:
        :type exclude_stale: bool
        :param paused:
        :type paused: bool
        :param last_dag_run_state:
        :type last_dag_run_state: DagRunState
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._patch_dags_serialize(
            dag_patch_body=dag_patch_body,
            update_mask=update_mask,
            limit=limit,
            offset=offset,
            tags=tags,
            tags_match_mode=tags_match_mode,
            owners=owners,
            dag_id_pattern=dag_id_pattern,
            exclude_stale=exclude_stale,
            paused=paused,
            last_dag_run_state=last_dag_run_state,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGCollectionResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        response_data.read()
        return self.api_client.response_deserialize(
            response_data=response_data,
            response_types_map=_response_types_map,
        )


    @validate_call
    def patch_dags_without_preload_content(
        self,
        dag_patch_body: DAGPatchBody,
        update_mask: Optional[List[StrictStr]] = None,
        limit: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        offset: Optional[Annotated[int, Field(strict=True, ge=0)]] = None,
        tags: Optional[List[StrictStr]] = None,
        tags_match_mode: Optional[StrictStr] = None,
        owners: Optional[List[StrictStr]] = None,
        dag_id_pattern: Annotated[Optional[StrictStr], Field(description="SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.")] = None,
        exclude_stale: Optional[StrictBool] = None,
        paused: Optional[StrictBool] = None,
        last_dag_run_state: Optional[DagRunState] = None,
        _request_timeout: Union[
            None,
            Annotated[StrictFloat, Field(gt=0)],
            Tuple[
                Annotated[StrictFloat, Field(gt=0)],
                Annotated[StrictFloat, Field(gt=0)]
            ]
        ] = None,
        _request_auth: Optional[Dict[StrictStr, Any]] = None,
        _content_type: Optional[StrictStr] = None,
        _headers: Optional[Dict[StrictStr, Any]] = None,
        _host_index: Annotated[StrictInt, Field(ge=0, le=0)] = 0,
    ) -> RESTResponseType:
        """Patch Dags

        Patch multiple DAGs.

        :param dag_patch_body: (required)
        :type dag_patch_body: DAGPatchBody
        :param update_mask:
        :type update_mask: List[str]
        :param limit:
        :type limit: int
        :param offset:
        :type offset: int
        :param tags:
        :type tags: List[str]
        :param tags_match_mode:
        :type tags_match_mode: str
        :param owners:
        :type owners: List[str]
        :param dag_id_pattern: SQL LIKE expression — use `%` / `_` wildcards (e.g. `%customer_%`). Regular expressions are **not** supported.
        :type dag_id_pattern: str
        :param exclude_stale:
        :type exclude_stale: bool
        :param paused:
        :type paused: bool
        :param last_dag_run_state:
        :type last_dag_run_state: DagRunState
        :param _request_timeout: timeout setting for this request. If one
                                 number provided, it will be total request
                                 timeout. It can also be a pair (tuple) of
                                 (connection, read) timeouts.
        :type _request_timeout: int, tuple(int, int), optional
        :param _request_auth: set to override the auth_settings for an a single
                              request; this effectively ignores the
                              authentication in the spec for a single request.
        :type _request_auth: dict, optional
        :param _content_type: force content-type for the request.
        :type _content_type: str, Optional
        :param _headers: set to override the headers for a single
                         request; this effectively ignores the headers
                         in the spec for a single request.
        :type _headers: dict, optional
        :param _host_index: set to override the host_index for a single
                            request; this effectively ignores the host_index
                            in the spec for a single request.
        :type _host_index: int, optional
        :return: Returns the result object.
        """ # noqa: E501

        _param = self._patch_dags_serialize(
            dag_patch_body=dag_patch_body,
            update_mask=update_mask,
            limit=limit,
            offset=offset,
            tags=tags,
            tags_match_mode=tags_match_mode,
            owners=owners,
            dag_id_pattern=dag_id_pattern,
            exclude_stale=exclude_stale,
            paused=paused,
            last_dag_run_state=last_dag_run_state,
            _request_auth=_request_auth,
            _content_type=_content_type,
            _headers=_headers,
            _host_index=_host_index
        )

        _response_types_map: Dict[str, Optional[str]] = {
            '200': "DAGCollectionResponse",
            '400': "HTTPExceptionResponse",
            '401': "HTTPExceptionResponse",
            '403': "HTTPExceptionResponse",
            '404': "HTTPExceptionResponse",
            '422': "HTTPValidationError",
        }
        response_data = self.api_client.call_api(
            *_param,
            _request_timeout=_request_timeout
        )
        return response_data.response


    def _patch_dags_serialize(
        self,
        dag_patch_body,
        update_mask,
        limit,
        offset,
        tags,
        tags_match_mode,
        owners,
        dag_id_pattern,
        exclude_stale,
        paused,
        last_dag_run_state,
        _request_auth,
        _content_type,
        _headers,
        _host_index,
    ) -> RequestSerialized:

        _host = None

        _collection_formats: Dict[str, str] = {
            'update_mask': 'multi',
            'tags': 'multi',
            'owners': 'multi',
        }

        _path_params: Dict[str, str] = {}
        _query_params: List[Tuple[str, str]] = []
        _header_params: Dict[str, Optional[str]] = _headers or {}
        _form_params: List[Tuple[str, str]] = []
        _files: Dict[
            str, Union[str, bytes, List[str], List[bytes], List[Tuple[str, bytes]]]
        ] = {}
        _body_params: Optional[bytes] = None

        # process the path parameters
        # process the query parameters
        if update_mask is not None:
            
            _query_params.append(('update_mask', update_mask))
            
        if limit is not None:
            
            _query_params.append(('limit', limit))
            
        if offset is not None:
            
            _query_params.append(('offset', offset))
            
        if tags is not None:
            
            _query_params.append(('tags', tags))
            
        if tags_match_mode is not None:
            
            _query_params.append(('tags_match_mode', tags_match_mode))
            
        if owners is not None:
            
            _query_params.append(('owners', owners))
            
        if dag_id_pattern is not None:
            
            _query_params.append(('dag_id_pattern', dag_id_pattern))
            
        if exclude_stale is not None:
            
            _query_params.append(('exclude_stale', exclude_stale))
            
        if paused is not None:
            
            _query_params.append(('paused', paused))
            
        if last_dag_run_state is not None:
            
            _query_params.append(('last_dag_run_state', last_dag_run_state.value))
            
        # process the header parameters
        # process the form parameters
        # process the body parameter
        if dag_patch_body is not None:
            _body_params = dag_patch_body


        # set the HTTP header `Accept`
        if 'Accept' not in _header_params:
            _header_params['Accept'] = self.api_client.select_header_accept(
                [
                    'application/json'
                ]
            )

        # set the HTTP header `Content-Type`
        if _content_type:
            _header_params['Content-Type'] = _content_type
        else:
            _default_content_type = (
                self.api_client.select_header_content_type(
                    [
                        'application/json'
                    ]
                )
            )
            if _default_content_type is not None:
                _header_params['Content-Type'] = _default_content_type

        # authentication setting
        _auth_settings: List[str] = [
            'OAuth2PasswordBearer'
        ]

        return self.api_client.param_serialize(
            method='PATCH',
            resource_path='/api/v2/dags',
            path_params=_path_params,
            query_params=_query_params,
            header_params=_header_params,
            body=_body_params,
            post_params=_form_params,
            files=_files,
            auth_settings=_auth_settings,
            collection_formats=_collection_formats,
            _host=_host,
            _request_auth=_request_auth
        )


