# Path: lepo/decoders.py
# def get_decoder(content_type):
#     """
#     Get a decoder function for the content type given, or None if there is none.
# 
#     :param content_type: Content type string
#     :type content_type: str
#     :return: function or None
#     """
#     if content_type.endswith('+json'):  # Process all +json vendor types like JSON
#         content_type = 'application/json'
# 
#     if content_type in DECODERS:
#         return DECODERS[content_type]
# 
#     return None
# 
# Path: lepo/excs.py
# class InvalidBodyContent(ValueError):
#     pass
# 
# Path: lepo/utils.py
# def maybe_resolve(object, resolve):
#     """
#     Call `resolve` on the `object`'s `$ref` value if it has one.
# 
#     :param object: An object.
#     :param resolve: A resolving function.
#     :return: An object, or some other object! :sparkles:
#     """
#     if isinstance(object, dict) and object.get('$ref'):
#         return resolve(object['$ref'])
#     return object


import jsonschema
from django.core.files import File
from django.utils.encoding import force_str
from jsonschema import Draft4Validator
from lepo.decoders import get_decoder
from lepo.excs import InvalidBodyContent
from lepo.utils import maybe_resolve


def read_body(request, parameter=None):
    if parameter:
        if parameter.type == 'binary':
            return request.body.read()
    try:
        if request.content_type == 'multipart/form-data':
            # TODO: this definitely doesn't handle multiple values for the same key correctly
            data = dict()
            data.update(request.POST.items())
            data.update(request.FILES.items())
            return data
        decoder = get_decoder(request.content_type)
        if decoder:
            return decoder(request.body, encoding=request.content_params.get('charset', 'UTF-8'))
    except Exception as exc:
        raise InvalidBodyContent(f'Unable to parse this body as {request.content_type}') from exc
    raise NotImplementedError(f'No idea how to parse content-type {request.content_type}')  # pragma: no cover


class LepoDraft4Validator(Draft4Validator):
    def iter_errors(self, instance, _schema=None):
        if isinstance(instance, File):
            # Skip validating File instances that come from POST requests...
            return
        yield from super().iter_errors(instance, _schema)


def validate_schema(schema, api, value):

# Path: lepo/decoders.py
# def get_decoder(content_type):
#     """
#     Get a decoder function for the content type given, or None if there is none.
# 
#     :param content_type: Content type string
#     :type content_type: str
#     :return: function or None
#     """
#     if content_type.endswith('+json'):  # Process all +json vendor types like JSON
#         content_type = 'application/json'
# 
#     if content_type in DECODERS:
#         return DECODERS[content_type]
# 
#     return None
# 
# Path: lepo/excs.py
# class InvalidBodyContent(ValueError):
#     pass
# 
# Path: lepo/utils.py
# def maybe_resolve(object, resolve):
#     """
#     Call `resolve` on the `object`'s `$ref` value if it has one.
# 
#     :param object: An object.
#     :param resolve: A resolving function.
#     :return: An object, or some other object! :sparkles:
#     """
#     if isinstance(object, dict) and object.get('$ref'):
#         return resolve(object['$ref'])
#     return object


# Path: lepo/apidef/parameter/utils.py
import jsonschema
from django.core.files import File
from django.utils.encoding import force_str
from jsonschema import Draft4Validator
from lepo.decoders import get_decoder
from lepo.excs import InvalidBodyContent
from lepo.utils import maybe_resolve



def read_body(request, parameter=None):
    if parameter:
        if parameter.type == 'binary':
            return request.body.read()
    try:
        if request.content_type == 'multipart/form-data':
            # TODO: this definitely doesn't handle multiple values for the same key correctly
            data = dict()
            data.update(request.POST.items())
            data.update(request.FILES.items())
            return data
        decoder = get_decoder(request.content_type)
        if decoder:
            return decoder(request.body, encoding=request.content_params.get('charset', 'UTF-8'))
    except Exception as exc:
        raise InvalidBodyContent(f'Unable to parse this body as {request.content_type}') from exc
    raise NotImplementedError(f'No idea how to parse content-type {request.content_type}')  # pragma: no cover


class LepoDraft4Validator(Draft4Validator):
    def iter_errors(self, instance, _schema=None):
        if isinstance(instance, File):
            # Skip validating File instances that come from POST requests...
            return
        yield from super().iter_errors(instance, _schema)


def validate_schema(schema, api, value):

    schema = maybe_resolve(schema, resolve=api.resolve_reference)