Я учился выполнять базовые c операции CRUD в DRF, и когда я выполняю запрос PUT по этому URL-адресу, я обнаружил эту ошибку.
ParseError at /api-article/detail/2/
JSON parse error - Expecting value: line 1 column 1 (char 0)
Request Method: PUT
Request URL: http://127.0.0.1:8000/api-article/detail/2/
Django Version: 3.0.8
Exception Type: ParseError
Exception Value:
JSON parse error - Expecting value: line 1 column 1 (char 0)
Exception Location: /home/AnimeshK/Dev/parviz_api/lib/python3.8/site-packages/rest_framework/parsers.py
при синтаксическом анализе, строка 67 Python Исполняемый файл: / home / AnimeshK / Dev / parviz_api / bin / python Python Версия: 3.8.3 Python Путь: ['/ home / AnimeshK / Dev / parviz_api / sr c', '/usr/lib/python38.zip', '/usr/lib/python3.8', '/ usr / lib / python3 .8 / lib-dynload ',' /home/AnimeshK/Dev/parviz_api/lib/python3.8/site-packages '] Время сервера: пт, 10 июл 2020 15:12:12 + 0000
Ниже мой view.py
@csrf_exempt
def article_detail(request, id):
try:
art_obj = Article.objects.get(id=id)
except Article.DoesNotExist:
raise Http404
if (request.method == 'GET'): # normal detail view
serializer = ArticleSerializer(art_obj)
return JsonResponse(serializer.data)
elif (request.method == 'PUT'): # article update view
data = JSONParser().parse(request)
serializer = ArticleSerializer(art_obj, data=data) # so that the existing data gets rendered in the PUT walla form
if (serializer.is_valid()):
serializer.save()
return JsonResponse(serializer.data)
return JsonResponse(serializer.errors, status=400)
elif (request.method == 'DELETE'):
art_obj.delete()
return HttpResponse(status=204)
Ниже приводится полная трассировка:
> representation and the index in ``s`` where the document ended.
> This can be used to decode a JSON document from a string that may
> have extraneous data at the end.
> """
> try:
> obj, end = self.scan_once(s, idx) …
> except StopIteration as err:
> raise JSONDecodeError("Expecting value", s, err.value) from None
> return obj, end ▶ Local vars Variable Value idx 0 s '' self <json.decoder.JSONDecoder object at 0x7fe6482815e0> During handling of
> the above exception (0), another exception occurred:
> /home/AnimeshK/Dev/parviz_api/lib/python3.8/site-packages/rest_framework/parsers.py
> in parse
> """
> parser_context = parser_context or {}
> encoding = parser_context.get('encoding', settings.DEFAULT_CHARSET)
> try:
> decoded_stream = codecs.getreader(encoding)(stream)
> parse_constant = json.strict_constant if self.strict else None
> return json.load(decoded_stream, parse_constant=parse_constant) …
> except ValueError as exc:
> raise ParseError('JSON parse error - %s' % str(exc)) class FormParser(BaseParser):
> """ ▶ Local vars Variable Value decoded_stream <encodings.utf_8.StreamReader object at 0x7fe648259790> encoding
> 'utf-8' media_type None parse_constant <function strict_constant at
> 0x7fe6485c5280> parser_context {} self
> <rest_framework.parsers.JSONParser object at 0x7fe64825d5e0> stream
> <WSGIRequest: PUT '/api-article/detail/2/'>
> /home/AnimeshK/Dev/parviz_api/lib/python3.8/site-packages/rest_framework/utils/json.py
> in load
> kwargs.setdefault('allow_nan', False)
> return json.dumps(*args, **kwargs) @functools.wraps(json.load) def load(*args, **kwargs):
> kwargs.setdefault('parse_constant', strict_constant)
> return json.load(*args, **kwargs) … @functools.wraps(json.loads) def loads(*args, **kwargs):
> kwargs.setdefault('parse_constant', strict_constant)
> return json.loads(*args, **kwargs) ▶ Local vars Variable Value args (<encodings.utf_8.StreamReader object at 0x7fe648259790>,)
> kwargs {'parse_constant': <function strict_constant at
> 0x7fe6485c5280>} /usr/lib/python3.8/json/__init__.py in load
> return value of ``object_pairs_hook`` will be used instead of the ``dict``.
> This feature can be used to implement custom decoders. If ``object_hook``
> is also defined, the ``object_pairs_hook`` takes priority.
> To use a custom ``JSONDecoder`` subclass, specify it with the ``cls``
> kwarg; otherwise ``JSONDecoder`` is used.
> """
> return loads(fp.read(), …
> cls=cls, object_hook=object_hook,
> parse_float=parse_float, parse_int=parse_int,
> parse_constant=parse_constant, object_pairs_hook=object_pairs_hook, **kw) def loads(s, *, cls=None,
> object_hook=None, parse_float=None, ▶ Local vars Variable Value cls
> None fp <encodings.utf_8.StreamReader object at 0x7fe648259790> kw
> {} object_hook None object_pairs_hook None parse_constant <function
> strict_constant at 0x7fe6485c5280> parse_float None parse_int None
> /usr/lib/python3.8/json/__init__.py in loads
> kw['object_pairs_hook'] = object_pairs_hook
> if parse_float is not None:
> kw['parse_float'] = parse_float
> if parse_int is not None:
> kw['parse_int'] = parse_int
> if parse_constant is not None:
> kw['parse_constant'] = parse_constant
> return cls(**kw).decode(s) … ▶ Local vars Variable Value cls <class 'json.decoder.JSONDecoder'> kw {'parse_constant': <function
> strict_constant at 0x7fe6485c5280>} object_hook None
> object_pairs_hook None parse_constant <function strict_constant at
> 0x7fe6485c5280> parse_float None parse_int None s ''
> /usr/lib/python3.8/json/decoder.py in decode
> def decode(self, s, _w=WHITESPACE.match):
> """Return the Python representation of ``s`` (a ``str`` instance
> containing a JSON document).
> """
> obj, end = self.raw_decode(s, idx=_w(s, 0).end()) …
> end = _w(s, end).end()
> if end != len(s):
> raise JSONDecodeError("Extra data", s, end)
> return obj
> def raw_decode(self, s, idx=0): ▶ Local vars Variable Value
> _w <built-in method match of re.Pattern object at 0x7fe64a3f2270> s '' self <json.decoder.JSONDecoder object at 0x7fe6482815e0>
> /usr/lib/python3.8/json/decoder.py in raw_decode
> This can be used to decode a JSON document from a string that may
> have extraneous data at the end.
> """
> try:
> obj, end = self.scan_once(s, idx)
> except StopIteration as err:
> raise JSONDecodeError("Expecting value", s, err.value) from None …
> return obj, end ▶ Local vars Variable Value idx 0 s '' self <json.decoder.JSONDecoder object at 0x7fe6482815e0> During handling of
> the above exception (Expecting value: line 1 column 1 (char 0)),
> another exception occurred:
> /home/AnimeshK/Dev/parviz_api/lib/python3.8/site-packages/django/core/handlers/exception.py
> in inner
> This decorator is automatically applied to all middleware to ensure that
> no middleware leaks an exception and that the next middleware in the stack
> can rely on getting a response instead of an exception.
> """
> @wraps(get_response)
> def inner(request):
> try:
> response = get_response(request) …
> except Exception as exc:
> response = response_for_exception(request, exc)
> return response
> return inner ▶ Local vars Variable Value exc ParseError('JSON parse error - Expecting value: line 1 column 1 (char 0)')
> get_response <bound method BaseHandler._get_response of
> <django.core.handlers.wsgi.WSGIHandler object at 0x7fe64967dd00>>
> request <WSGIRequest: PUT '/api-article/detail/2/'>
> /home/AnimeshK/Dev/parviz_api/lib/python3.8/site-packages/django/core/handlers/base.py
> in _get_response
> break
> if response is None:
> wrapped_callback = self.make_view_atomic(callback)
> try:
> response = wrapped_callback(request, *callback_args, **callback_kwargs)
> except Exception as e:
> response = self.process_exception_by_middleware(e, request) …
> # Complain if the view returned None (a common error).
> if response is None:
> if isinstance(callback, types.FunctionType): # FBV
> view_name = callback.__name__
> else: # CBV ▶ Local vars Variable Value callback <function article_detail at
> 0x7fe64846a0d0> callback_args () callback_kwargs {'id': 2}
> middleware_method <bound method CsrfViewMiddleware.process_view of
> <django.middleware.csrf.CsrfViewMiddleware object at 0x7fe6495f4f40>>
> request <WSGIRequest: PUT '/api-article/detail/2/'> resolver
> <URLResolver 'parviz_api.urls' (None:None) '^/'> resolver_match
> ResolverMatch(func=api_basic.views.article_detail, args=(),
> kwargs={'id': 2}, url_name=article_detail, app_names=['api_basic'],
> namespaces=['api_basic'], route=api-article/detail/<int:id>/)
> response None self <django.core.handlers.wsgi.WSGIHandler object at
> 0x7fe64967dd00> wrapped_callback <function article_detail at
> 0x7fe64846a0d0>
> /home/AnimeshK/Dev/parviz_api/lib/python3.8/site-packages/django/core/handlers/base.py
> in _get_response
> response = middleware_method(request, callback, callback_args, callback_kwargs)
> if response:
> break
> if response is None:
> wrapped_callback = self.make_view_atomic(callback)
> try:
> response = wrapped_callback(request, *callback_args, **callback_kwargs) …
> except Exception as e:
> response = self.process_exception_by_middleware(e, request)
> # Complain if the view returned None (a common error).
> if response is None:
> if isinstance(callback, types.FunctionType): # FBV ▶ Local vars Variable Value callback <function article_detail at
> 0x7fe64846a0d0> callback_args () callback_kwargs {'id': 2}
> middleware_method <bound method CsrfViewMiddleware.process_view of
> <django.middleware.csrf.CsrfViewMiddleware object at 0x7fe6495f4f40>>
> request <WSGIRequest: PUT '/api-article/detail/2/'> resolver
> <URLResolver 'parviz_api.urls' (None:None) '^/'> resolver_match
> ResolverMatch(func=api_basic.views.article_detail, args=(),
> kwargs={'id': 2}, url_name=article_detail, app_names=['api_basic'],
> namespaces=['api_basic'], route=api-article/detail/<int:id>/)
> response None self <django.core.handlers.wsgi.WSGIHandler object at
> 0x7fe64967dd00> wrapped_callback <function article_detail at
> 0x7fe64846a0d0>
> /home/AnimeshK/Dev/parviz_api/lib/python3.8/site-packages/django/views/decorators/csrf.py
> in wrapped_view def csrf_exempt(view_func):
> """Mark a view function as being exempt from the CSRF view protection."""
> # view_func.csrf_exempt = True would also work, but decorators are nicer
> # if they don't have side effects, so return a new function.
> def wrapped_view(*args, **kwargs):
> return view_func(*args, **kwargs) …
> wrapped_view.csrf_exempt = True
> return wraps(view_func)(wrapped_view) ▶ Local vars Variable Value args (<WSGIRequest: PUT '/api-article/detail/2/'>,) kwargs {'id': 2}
> view_func <function article_detail at 0x7fe64846a040>
> /home/AnimeshK/Dev/parviz_api/src/api_basic/views.py in article_detail
> raise Http404 if (request.method == 'GET'): # normal detail view
> serializer = ArticleSerializer(art_obj)
> return JsonResponse(serializer.data)
> elif (request.method == 'PUT'): # article update view
> data = JSONParser().parse(request) …
> serializer = ArticleSerializer(art_obj, data=data) # so that the existing data gets rendered in the PUT walla form
> if (serializer.is_valid()):
> serializer.save()
> return JsonResponse(serializer.data)
> return JsonResponse(serializer.errors, status=400) ▶ Local vars Variable Value art_obj <Article: Beauty and Brans2 by Mr. Sura Saha>
> id 2 request <WSGIRequest: PUT '/api-article/detail/2/'>
> /home/AnimeshK/Dev/parviz_api/lib/python3.8/site-packages/rest_framework/parsers.py
> in parse
> encoding = parser_context.get('encoding', settings.DEFAULT_CHARSET)
> try:
> decoded_stream = codecs.getreader(encoding)(stream)
> parse_constant = json.strict_constant if self.strict else None
> return json.load(decoded_stream, parse_constant=parse_constant)
> except ValueError as exc:
> raise ParseError('JSON parse error - %s' % str(exc)) … class FormParser(BaseParser):
> """
> Parser for form data.
> """ ▶ Local vars Variable Value decoded_stream <encodings.utf_8.StreamReader object at 0x7fe648259790> encoding
> 'utf-8' media_type None parse_constant <function strict_constant at
> 0x7fe6485c5280> parser_context {} self
> <rest_framework.parsers.JSONParser object at 0x7fe64825d5e0> stream
> <WSGIRequest: PUT '/api-article/detail/2/'>