# This file was auto-generated by Fern from our API Definition.

import typing
from json.decoder import JSONDecodeError

from ..core.api_error import ApiError
from ..core.client_wrapper import AsyncClientWrapper, SyncClientWrapper
from ..core.http_response import AsyncHttpResponse, HttpResponse
from ..core.jsonable_encoder import jsonable_encoder
from ..core.pydantic_utilities import parse_obj_as
from ..core.request_options import RequestOptions
from ..core.serialization import convert_and_respect_annotation_metadata
from ..errors.bad_request_error import BadRequestError
from ..errors.internal_server_error import InternalServerError
from ..errors.service_unavailable_error import ServiceUnavailableError
from ..errors.unauthorized_error import UnauthorizedError
from ..types.contacts_field import ContactsField
from ..types.file_content import FileContent
from ..types.idempotency_key import IdempotencyKey
from ..types.instrument import Instrument
from ..types.org_parent_id import OrgParentId
from ..types.orgaddress import Orgaddress
from ..types.organization_query_record import OrganizationQueryRecord
from ..types.orgcity import Orgcity
from ..types.orgcountry import Orgcountry
from ..types.orgentryname import Orgentryname
from ..types.orgidstring import Orgidstring
from ..types.orgname import Orgname
from ..types.orgstate import Orgstate
from ..types.orgtimezone import Orgtimezone
from ..types.orgtype import Orgtype
from ..types.orgwebsite import Orgwebsite
from ..types.orgzip import Orgzip
from ..types.payabli_api_response import PayabliApiResponse
from ..types.reply_to_email import ReplyToEmail
from ..types.service_cost import ServiceCost
from ..types.settings_query_record import SettingsQueryRecord
from .types.add_organization_response import AddOrganizationResponse
from .types.delete_organization_response import DeleteOrganizationResponse
from .types.edit_organization_response import EditOrganizationResponse

# this is used as the default value for optional parameters
OMIT = typing.cast(typing.Any, ...)


class RawOrganizationClient:
    def __init__(self, *, client_wrapper: SyncClientWrapper):
        self._client_wrapper = client_wrapper

    def add_organization(
        self,
        *,
        org_name: Orgname,
        org_type: Orgtype,
        reply_to_email: ReplyToEmail,
        idempotency_key: typing.Optional[IdempotencyKey] = None,
        services: typing.Optional[typing.Sequence[ServiceCost]] = OMIT,
        billing_info: typing.Optional[Instrument] = OMIT,
        contacts: typing.Optional[ContactsField] = OMIT,
        has_billing: typing.Optional[bool] = OMIT,
        has_residual: typing.Optional[bool] = OMIT,
        org_address: typing.Optional[Orgaddress] = OMIT,
        org_city: typing.Optional[Orgcity] = OMIT,
        org_country: typing.Optional[Orgcountry] = OMIT,
        org_entry_name: typing.Optional[Orgentryname] = OMIT,
        org_id: typing.Optional[Orgidstring] = OMIT,
        org_logo: typing.Optional[FileContent] = OMIT,
        org_parent_id: typing.Optional[OrgParentId] = OMIT,
        org_state: typing.Optional[Orgstate] = OMIT,
        org_timezone: typing.Optional[Orgtimezone] = OMIT,
        org_website: typing.Optional[Orgwebsite] = OMIT,
        org_zip: typing.Optional[Orgzip] = OMIT,
        request_options: typing.Optional[RequestOptions] = None,
    ) -> HttpResponse[AddOrganizationResponse]:
        """
        Creates an organization under a parent organization. This is also referred to as a suborganization.

        Parameters
        ----------
        org_name : Orgname

        org_type : Orgtype

        reply_to_email : ReplyToEmail

        idempotency_key : typing.Optional[IdempotencyKey]

        services : typing.Optional[typing.Sequence[ServiceCost]]

        billing_info : typing.Optional[Instrument]

        contacts : typing.Optional[ContactsField]

        has_billing : typing.Optional[bool]

        has_residual : typing.Optional[bool]

        org_address : typing.Optional[Orgaddress]

        org_city : typing.Optional[Orgcity]

        org_country : typing.Optional[Orgcountry]

        org_entry_name : typing.Optional[Orgentryname]

        org_id : typing.Optional[Orgidstring]

        org_logo : typing.Optional[FileContent]

        org_parent_id : typing.Optional[OrgParentId]

        org_state : typing.Optional[Orgstate]

        org_timezone : typing.Optional[Orgtimezone]

        org_website : typing.Optional[Orgwebsite]

        org_zip : typing.Optional[Orgzip]

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        HttpResponse[AddOrganizationResponse]
            Success.
        """
        _response = self._client_wrapper.httpx_client.request(
            "Organization",
            method="POST",
            json={
                "services": convert_and_respect_annotation_metadata(
                    object_=services, annotation=typing.Sequence[ServiceCost], direction="write"
                ),
                "billingInfo": convert_and_respect_annotation_metadata(
                    object_=billing_info, annotation=Instrument, direction="write"
                ),
                "contacts": convert_and_respect_annotation_metadata(
                    object_=contacts, annotation=ContactsField, direction="write"
                ),
                "hasBilling": has_billing,
                "hasResidual": has_residual,
                "orgAddress": org_address,
                "orgCity": org_city,
                "orgCountry": org_country,
                "orgEntryName": org_entry_name,
                "orgId": org_id,
                "orgLogo": convert_and_respect_annotation_metadata(
                    object_=org_logo, annotation=FileContent, direction="write"
                ),
                "orgName": org_name,
                "orgParentId": org_parent_id,
                "orgState": org_state,
                "orgTimezone": org_timezone,
                "orgType": org_type,
                "orgWebsite": org_website,
                "orgZip": org_zip,
                "replyToEmail": reply_to_email,
            },
            headers={
                "content-type": "application/json",
                "idempotencyKey": str(idempotency_key) if idempotency_key is not None else None,
            },
            request_options=request_options,
            omit=OMIT,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    AddOrganizationResponse,
                    parse_obj_as(
                        type_=AddOrganizationResponse,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return HttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    def delete_organization(
        self, org_id: int, *, request_options: typing.Optional[RequestOptions] = None
    ) -> HttpResponse[DeleteOrganizationResponse]:
        """
        Delete an organization by ID.

        Parameters
        ----------
        org_id : int
            The numeric identifier for organization, assigned by Payabli.

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        HttpResponse[DeleteOrganizationResponse]
            Success
        """
        _response = self._client_wrapper.httpx_client.request(
            f"Organization/{jsonable_encoder(org_id)}",
            method="DELETE",
            request_options=request_options,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    DeleteOrganizationResponse,
                    parse_obj_as(
                        type_=DeleteOrganizationResponse,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return HttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    def edit_organization(
        self,
        org_id: int,
        *,
        services: typing.Optional[typing.Sequence[ServiceCost]] = OMIT,
        billing_info: typing.Optional[Instrument] = OMIT,
        contacts: typing.Optional[ContactsField] = OMIT,
        has_billing: typing.Optional[bool] = OMIT,
        has_residual: typing.Optional[bool] = OMIT,
        org_address: typing.Optional[Orgaddress] = OMIT,
        org_city: typing.Optional[Orgcity] = OMIT,
        org_country: typing.Optional[Orgcountry] = OMIT,
        org_entry_name: typing.Optional[Orgentryname] = OMIT,
        organization_data_org_id: typing.Optional[Orgidstring] = OMIT,
        org_logo: typing.Optional[FileContent] = OMIT,
        org_name: typing.Optional[Orgname] = OMIT,
        org_parent_id: typing.Optional[OrgParentId] = OMIT,
        org_state: typing.Optional[Orgstate] = OMIT,
        org_timezone: typing.Optional[Orgtimezone] = OMIT,
        org_type: typing.Optional[Orgtype] = OMIT,
        org_website: typing.Optional[Orgwebsite] = OMIT,
        org_zip: typing.Optional[Orgzip] = OMIT,
        reply_to_email: typing.Optional[ReplyToEmail] = OMIT,
        request_options: typing.Optional[RequestOptions] = None,
    ) -> HttpResponse[EditOrganizationResponse]:
        """
        Updates an organization's details by ID.

        Parameters
        ----------
        org_id : int
            The numeric identifier for organization, assigned by Payabli.

        services : typing.Optional[typing.Sequence[ServiceCost]]

        billing_info : typing.Optional[Instrument]

        contacts : typing.Optional[ContactsField]

        has_billing : typing.Optional[bool]

        has_residual : typing.Optional[bool]

        org_address : typing.Optional[Orgaddress]

        org_city : typing.Optional[Orgcity]

        org_country : typing.Optional[Orgcountry]

        org_entry_name : typing.Optional[Orgentryname]

        organization_data_org_id : typing.Optional[Orgidstring]

        org_logo : typing.Optional[FileContent]

        org_name : typing.Optional[Orgname]

        org_parent_id : typing.Optional[OrgParentId]

        org_state : typing.Optional[Orgstate]

        org_timezone : typing.Optional[Orgtimezone]

        org_type : typing.Optional[Orgtype]

        org_website : typing.Optional[Orgwebsite]

        org_zip : typing.Optional[Orgzip]

        reply_to_email : typing.Optional[ReplyToEmail]

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        HttpResponse[EditOrganizationResponse]
            Success
        """
        _response = self._client_wrapper.httpx_client.request(
            f"Organization/{jsonable_encoder(org_id)}",
            method="PUT",
            json={
                "services": convert_and_respect_annotation_metadata(
                    object_=services, annotation=typing.Sequence[ServiceCost], direction="write"
                ),
                "billingInfo": convert_and_respect_annotation_metadata(
                    object_=billing_info, annotation=Instrument, direction="write"
                ),
                "contacts": convert_and_respect_annotation_metadata(
                    object_=contacts, annotation=ContactsField, direction="write"
                ),
                "hasBilling": has_billing,
                "hasResidual": has_residual,
                "orgAddress": org_address,
                "orgCity": org_city,
                "orgCountry": org_country,
                "orgEntryName": org_entry_name,
                "orgId": organization_data_org_id,
                "orgLogo": convert_and_respect_annotation_metadata(
                    object_=org_logo, annotation=FileContent, direction="write"
                ),
                "orgName": org_name,
                "orgParentId": org_parent_id,
                "orgState": org_state,
                "orgTimezone": org_timezone,
                "orgType": org_type,
                "orgWebsite": org_website,
                "orgZip": org_zip,
                "replyToEmail": reply_to_email,
            },
            headers={
                "content-type": "application/json",
            },
            request_options=request_options,
            omit=OMIT,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    EditOrganizationResponse,
                    parse_obj_as(
                        type_=EditOrganizationResponse,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return HttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    def get_basic_organization(
        self, entry: str, *, request_options: typing.Optional[RequestOptions] = None
    ) -> HttpResponse[OrganizationQueryRecord]:
        """
        Gets an organization's basic information by entry name (entrypoint identifier).

        Parameters
        ----------
        entry : str
            The paypoint's entrypoint identifier. [Learn more](/api-reference/api-overview#entrypoint-vs-entry)

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        HttpResponse[OrganizationQueryRecord]
            Success
        """
        _response = self._client_wrapper.httpx_client.request(
            f"Organization/basic/{jsonable_encoder(entry)}",
            method="GET",
            request_options=request_options,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    OrganizationQueryRecord,
                    parse_obj_as(
                        type_=OrganizationQueryRecord,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return HttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    def get_basic_organization_by_id(
        self, org_id: int, *, request_options: typing.Optional[RequestOptions] = None
    ) -> HttpResponse[OrganizationQueryRecord]:
        """
        Gets an organizations basic details by org ID.

        Parameters
        ----------
        org_id : int
            The numeric identifier for organization, assigned by Payabli.

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        HttpResponse[OrganizationQueryRecord]
            Success
        """
        _response = self._client_wrapper.httpx_client.request(
            f"Organization/basicById/{jsonable_encoder(org_id)}",
            method="GET",
            request_options=request_options,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    OrganizationQueryRecord,
                    parse_obj_as(
                        type_=OrganizationQueryRecord,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return HttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    def get_organization(
        self, org_id: int, *, request_options: typing.Optional[RequestOptions] = None
    ) -> HttpResponse[OrganizationQueryRecord]:
        """
        Retrieves details for an organization by ID.

        Parameters
        ----------
        org_id : int
            The numeric identifier for organization, assigned by Payabli.

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        HttpResponse[OrganizationQueryRecord]
            Success
        """
        _response = self._client_wrapper.httpx_client.request(
            f"Organization/read/{jsonable_encoder(org_id)}",
            method="GET",
            request_options=request_options,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    OrganizationQueryRecord,
                    parse_obj_as(
                        type_=OrganizationQueryRecord,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return HttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    def get_settings_organization(
        self, org_id: int, *, request_options: typing.Optional[RequestOptions] = None
    ) -> HttpResponse[SettingsQueryRecord]:
        """
        Retrieves an organization's settings.

        Parameters
        ----------
        org_id : int
            The numeric identifier for organization, assigned by Payabli.

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        HttpResponse[SettingsQueryRecord]
            Success
        """
        _response = self._client_wrapper.httpx_client.request(
            f"Organization/settings/{jsonable_encoder(org_id)}",
            method="GET",
            request_options=request_options,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    SettingsQueryRecord,
                    parse_obj_as(
                        type_=SettingsQueryRecord,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return HttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)


class AsyncRawOrganizationClient:
    def __init__(self, *, client_wrapper: AsyncClientWrapper):
        self._client_wrapper = client_wrapper

    async def add_organization(
        self,
        *,
        org_name: Orgname,
        org_type: Orgtype,
        reply_to_email: ReplyToEmail,
        idempotency_key: typing.Optional[IdempotencyKey] = None,
        services: typing.Optional[typing.Sequence[ServiceCost]] = OMIT,
        billing_info: typing.Optional[Instrument] = OMIT,
        contacts: typing.Optional[ContactsField] = OMIT,
        has_billing: typing.Optional[bool] = OMIT,
        has_residual: typing.Optional[bool] = OMIT,
        org_address: typing.Optional[Orgaddress] = OMIT,
        org_city: typing.Optional[Orgcity] = OMIT,
        org_country: typing.Optional[Orgcountry] = OMIT,
        org_entry_name: typing.Optional[Orgentryname] = OMIT,
        org_id: typing.Optional[Orgidstring] = OMIT,
        org_logo: typing.Optional[FileContent] = OMIT,
        org_parent_id: typing.Optional[OrgParentId] = OMIT,
        org_state: typing.Optional[Orgstate] = OMIT,
        org_timezone: typing.Optional[Orgtimezone] = OMIT,
        org_website: typing.Optional[Orgwebsite] = OMIT,
        org_zip: typing.Optional[Orgzip] = OMIT,
        request_options: typing.Optional[RequestOptions] = None,
    ) -> AsyncHttpResponse[AddOrganizationResponse]:
        """
        Creates an organization under a parent organization. This is also referred to as a suborganization.

        Parameters
        ----------
        org_name : Orgname

        org_type : Orgtype

        reply_to_email : ReplyToEmail

        idempotency_key : typing.Optional[IdempotencyKey]

        services : typing.Optional[typing.Sequence[ServiceCost]]

        billing_info : typing.Optional[Instrument]

        contacts : typing.Optional[ContactsField]

        has_billing : typing.Optional[bool]

        has_residual : typing.Optional[bool]

        org_address : typing.Optional[Orgaddress]

        org_city : typing.Optional[Orgcity]

        org_country : typing.Optional[Orgcountry]

        org_entry_name : typing.Optional[Orgentryname]

        org_id : typing.Optional[Orgidstring]

        org_logo : typing.Optional[FileContent]

        org_parent_id : typing.Optional[OrgParentId]

        org_state : typing.Optional[Orgstate]

        org_timezone : typing.Optional[Orgtimezone]

        org_website : typing.Optional[Orgwebsite]

        org_zip : typing.Optional[Orgzip]

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        AsyncHttpResponse[AddOrganizationResponse]
            Success.
        """
        _response = await self._client_wrapper.httpx_client.request(
            "Organization",
            method="POST",
            json={
                "services": convert_and_respect_annotation_metadata(
                    object_=services, annotation=typing.Sequence[ServiceCost], direction="write"
                ),
                "billingInfo": convert_and_respect_annotation_metadata(
                    object_=billing_info, annotation=Instrument, direction="write"
                ),
                "contacts": convert_and_respect_annotation_metadata(
                    object_=contacts, annotation=ContactsField, direction="write"
                ),
                "hasBilling": has_billing,
                "hasResidual": has_residual,
                "orgAddress": org_address,
                "orgCity": org_city,
                "orgCountry": org_country,
                "orgEntryName": org_entry_name,
                "orgId": org_id,
                "orgLogo": convert_and_respect_annotation_metadata(
                    object_=org_logo, annotation=FileContent, direction="write"
                ),
                "orgName": org_name,
                "orgParentId": org_parent_id,
                "orgState": org_state,
                "orgTimezone": org_timezone,
                "orgType": org_type,
                "orgWebsite": org_website,
                "orgZip": org_zip,
                "replyToEmail": reply_to_email,
            },
            headers={
                "content-type": "application/json",
                "idempotencyKey": str(idempotency_key) if idempotency_key is not None else None,
            },
            request_options=request_options,
            omit=OMIT,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    AddOrganizationResponse,
                    parse_obj_as(
                        type_=AddOrganizationResponse,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return AsyncHttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    async def delete_organization(
        self, org_id: int, *, request_options: typing.Optional[RequestOptions] = None
    ) -> AsyncHttpResponse[DeleteOrganizationResponse]:
        """
        Delete an organization by ID.

        Parameters
        ----------
        org_id : int
            The numeric identifier for organization, assigned by Payabli.

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        AsyncHttpResponse[DeleteOrganizationResponse]
            Success
        """
        _response = await self._client_wrapper.httpx_client.request(
            f"Organization/{jsonable_encoder(org_id)}",
            method="DELETE",
            request_options=request_options,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    DeleteOrganizationResponse,
                    parse_obj_as(
                        type_=DeleteOrganizationResponse,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return AsyncHttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    async def edit_organization(
        self,
        org_id: int,
        *,
        services: typing.Optional[typing.Sequence[ServiceCost]] = OMIT,
        billing_info: typing.Optional[Instrument] = OMIT,
        contacts: typing.Optional[ContactsField] = OMIT,
        has_billing: typing.Optional[bool] = OMIT,
        has_residual: typing.Optional[bool] = OMIT,
        org_address: typing.Optional[Orgaddress] = OMIT,
        org_city: typing.Optional[Orgcity] = OMIT,
        org_country: typing.Optional[Orgcountry] = OMIT,
        org_entry_name: typing.Optional[Orgentryname] = OMIT,
        organization_data_org_id: typing.Optional[Orgidstring] = OMIT,
        org_logo: typing.Optional[FileContent] = OMIT,
        org_name: typing.Optional[Orgname] = OMIT,
        org_parent_id: typing.Optional[OrgParentId] = OMIT,
        org_state: typing.Optional[Orgstate] = OMIT,
        org_timezone: typing.Optional[Orgtimezone] = OMIT,
        org_type: typing.Optional[Orgtype] = OMIT,
        org_website: typing.Optional[Orgwebsite] = OMIT,
        org_zip: typing.Optional[Orgzip] = OMIT,
        reply_to_email: typing.Optional[ReplyToEmail] = OMIT,
        request_options: typing.Optional[RequestOptions] = None,
    ) -> AsyncHttpResponse[EditOrganizationResponse]:
        """
        Updates an organization's details by ID.

        Parameters
        ----------
        org_id : int
            The numeric identifier for organization, assigned by Payabli.

        services : typing.Optional[typing.Sequence[ServiceCost]]

        billing_info : typing.Optional[Instrument]

        contacts : typing.Optional[ContactsField]

        has_billing : typing.Optional[bool]

        has_residual : typing.Optional[bool]

        org_address : typing.Optional[Orgaddress]

        org_city : typing.Optional[Orgcity]

        org_country : typing.Optional[Orgcountry]

        org_entry_name : typing.Optional[Orgentryname]

        organization_data_org_id : typing.Optional[Orgidstring]

        org_logo : typing.Optional[FileContent]

        org_name : typing.Optional[Orgname]

        org_parent_id : typing.Optional[OrgParentId]

        org_state : typing.Optional[Orgstate]

        org_timezone : typing.Optional[Orgtimezone]

        org_type : typing.Optional[Orgtype]

        org_website : typing.Optional[Orgwebsite]

        org_zip : typing.Optional[Orgzip]

        reply_to_email : typing.Optional[ReplyToEmail]

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        AsyncHttpResponse[EditOrganizationResponse]
            Success
        """
        _response = await self._client_wrapper.httpx_client.request(
            f"Organization/{jsonable_encoder(org_id)}",
            method="PUT",
            json={
                "services": convert_and_respect_annotation_metadata(
                    object_=services, annotation=typing.Sequence[ServiceCost], direction="write"
                ),
                "billingInfo": convert_and_respect_annotation_metadata(
                    object_=billing_info, annotation=Instrument, direction="write"
                ),
                "contacts": convert_and_respect_annotation_metadata(
                    object_=contacts, annotation=ContactsField, direction="write"
                ),
                "hasBilling": has_billing,
                "hasResidual": has_residual,
                "orgAddress": org_address,
                "orgCity": org_city,
                "orgCountry": org_country,
                "orgEntryName": org_entry_name,
                "orgId": organization_data_org_id,
                "orgLogo": convert_and_respect_annotation_metadata(
                    object_=org_logo, annotation=FileContent, direction="write"
                ),
                "orgName": org_name,
                "orgParentId": org_parent_id,
                "orgState": org_state,
                "orgTimezone": org_timezone,
                "orgType": org_type,
                "orgWebsite": org_website,
                "orgZip": org_zip,
                "replyToEmail": reply_to_email,
            },
            headers={
                "content-type": "application/json",
            },
            request_options=request_options,
            omit=OMIT,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    EditOrganizationResponse,
                    parse_obj_as(
                        type_=EditOrganizationResponse,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return AsyncHttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    async def get_basic_organization(
        self, entry: str, *, request_options: typing.Optional[RequestOptions] = None
    ) -> AsyncHttpResponse[OrganizationQueryRecord]:
        """
        Gets an organization's basic information by entry name (entrypoint identifier).

        Parameters
        ----------
        entry : str
            The paypoint's entrypoint identifier. [Learn more](/api-reference/api-overview#entrypoint-vs-entry)

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        AsyncHttpResponse[OrganizationQueryRecord]
            Success
        """
        _response = await self._client_wrapper.httpx_client.request(
            f"Organization/basic/{jsonable_encoder(entry)}",
            method="GET",
            request_options=request_options,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    OrganizationQueryRecord,
                    parse_obj_as(
                        type_=OrganizationQueryRecord,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return AsyncHttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    async def get_basic_organization_by_id(
        self, org_id: int, *, request_options: typing.Optional[RequestOptions] = None
    ) -> AsyncHttpResponse[OrganizationQueryRecord]:
        """
        Gets an organizations basic details by org ID.

        Parameters
        ----------
        org_id : int
            The numeric identifier for organization, assigned by Payabli.

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        AsyncHttpResponse[OrganizationQueryRecord]
            Success
        """
        _response = await self._client_wrapper.httpx_client.request(
            f"Organization/basicById/{jsonable_encoder(org_id)}",
            method="GET",
            request_options=request_options,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    OrganizationQueryRecord,
                    parse_obj_as(
                        type_=OrganizationQueryRecord,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return AsyncHttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    async def get_organization(
        self, org_id: int, *, request_options: typing.Optional[RequestOptions] = None
    ) -> AsyncHttpResponse[OrganizationQueryRecord]:
        """
        Retrieves details for an organization by ID.

        Parameters
        ----------
        org_id : int
            The numeric identifier for organization, assigned by Payabli.

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        AsyncHttpResponse[OrganizationQueryRecord]
            Success
        """
        _response = await self._client_wrapper.httpx_client.request(
            f"Organization/read/{jsonable_encoder(org_id)}",
            method="GET",
            request_options=request_options,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    OrganizationQueryRecord,
                    parse_obj_as(
                        type_=OrganizationQueryRecord,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return AsyncHttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)

    async def get_settings_organization(
        self, org_id: int, *, request_options: typing.Optional[RequestOptions] = None
    ) -> AsyncHttpResponse[SettingsQueryRecord]:
        """
        Retrieves an organization's settings.

        Parameters
        ----------
        org_id : int
            The numeric identifier for organization, assigned by Payabli.

        request_options : typing.Optional[RequestOptions]
            Request-specific configuration.

        Returns
        -------
        AsyncHttpResponse[SettingsQueryRecord]
            Success
        """
        _response = await self._client_wrapper.httpx_client.request(
            f"Organization/settings/{jsonable_encoder(org_id)}",
            method="GET",
            request_options=request_options,
        )
        try:
            if 200 <= _response.status_code < 300:
                _data = typing.cast(
                    SettingsQueryRecord,
                    parse_obj_as(
                        type_=SettingsQueryRecord,  # type: ignore
                        object_=_response.json(),
                    ),
                )
                return AsyncHttpResponse(response=_response, data=_data)
            if _response.status_code == 400:
                raise BadRequestError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 401:
                raise UnauthorizedError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 500:
                raise InternalServerError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        typing.Optional[typing.Any],
                        parse_obj_as(
                            type_=typing.Optional[typing.Any],  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            if _response.status_code == 503:
                raise ServiceUnavailableError(
                    headers=dict(_response.headers),
                    body=typing.cast(
                        PayabliApiResponse,
                        parse_obj_as(
                            type_=PayabliApiResponse,  # type: ignore
                            object_=_response.json(),
                        ),
                    ),
                )
            _response_json = _response.json()
        except JSONDecodeError:
            raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
        raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
