相关文章推荐
logo

Solve Raise JSONDecodeError(Expecting Value, S, err.value) From None in Python

Solve Raise JSONDecodeError(Expecting Value, S, err.value) From None in Python

When working with URLs and APIs in Pythons, you often have to use the urllib and json libraries. More importantly, the json library helps with processing JSON data which is the default way to transfer data, especially with APIs.

Within the json library, there is a method, loads() , that returns the JSONDecodeError error. In this article, we will discuss how to resolve such errors and deal with them appropriately.

计算碎片化

Use try to Solve raise JSONDecodeError("Expecting value", s, err.value) from None in Python

Before dealing with JSON, we often had to receive data via the urllib package. However, when working with the urllib package , it is important to understand how to import such a package into your code as it could result in errors.

For us to make use of the urllib package, we have to import it. Often, people might import it as below.

import urllib
queryString = { 'name' : 'Jhon', 'age' : '18'}
urllib.parse.urlencode(queryString)

The output of the code above will give an AttributeError :

Traceback (most recent call last):
  File "c:\Users\akinl\Documents\HTML\python\test.py", line 3, in <module>
    urllib.parse.urlencode(queryString)
AttributeError: module 'urllib' has no attribute 'parse'

The correct way to import the urllib can be seen below.

import urllib.parse
queryString = {'name': 'Jhon', 'age': '18'}
urllib.parse.urlencode(queryString)

Alternatively, you can use the as keyword and your alias (often shorter) to make it easier to write your Python code.

import urllib.parse as urlp
queryString = {'name': 'Jhon', 'age': '18'}
urlp.urlencode(queryString)

All of the above works for request , error , and robotparser :

import urllib.request
import urllib.error
import urllib.robotparser

With these common errors out of the way, we can deal further with the function that often works with the urllib library when working with URLs that throws the JSONDecodeError error, as seen earlier, which is the json.load() function.

raise JSONDecodeError("Expecting value", s, err.value) from None
json.decoder.JSONDecodeError: Expecting value: line 1 column 1 (char 0)

The load() method parses valid JSON string that it receives as an argument and converts it into a Python dictionary for manipulation. The error message shows that it expected a JSON value but did not receive one.

That means your code did not parse JSON string or parse an empty string to the load() method. A quick code snippet can easily verify this.

import json
data = ""
js = json.loads(data)

The output of the code:

Traceback (most recent call last):
  File "c:\Users\akinl\Documents\python\texts.py", line 4, in <module>
    js = json.loads(data)
  File "C:\Python310\lib\json\__init__.py", line 346, in loads
    return _default_decoder.decode(s)
  File "C:\Python310\lib\json\decoder.py", line 337, in decode
    obj, end = self.raw_decode(s, idx=_w(s, 0).end())
  File "C:\Python310\lib\json\decoder.py", line 355, in raw_decode
    raise JSONDecodeError("Expecting value", s, err.value) from None
json.decoder.JSONDecodeError: Expecting value: line 1 column 1 (char 0)

The same error message is present, and we can ascertain that the error came from an empty string argument.

For a more detailed example, let us try to access a Google Map API and collect user location, e.g., US or NG, but it does not return any value.

import urllib.parse
import urllib.request
import json
googleURL = 'http://maps.googleapis.com/maps/api/geocode/json?'
while True:
    address = input('Enter location: ')
        if address == "exit":
      break
    if len(address) < 1:
        break
    url = googleURL + urllib.parse.urlencode({'sensor': 'false',
                                              'address': address})
    print('Retrieving', url)
    uReq = urllib.request.urlopen(url)
    data = uReq.read()
    print('Returned', len(data), 'characters')
    js = json.loads(data)
    print(js)

The output of the code:

Traceback (most recent call last):
  File "C:\Users\akinl\Documents\html\python\jsonArt.py", line 18, in <module>
    js = json.loads(str(data))
  File "C:\Python310\lib\json\__init__.py", line 346, in loads
    return _default_decoder.decode(s)
  File "C:\Python310\lib\json\decoder.py", line 337, in decode
    obj, end = self.raw_decode(s, idx=_w(s, 0).end())
  File "C:\Python310\lib\json\decoder.py", line 355, in raw_decode
    raise JSONDecodeError("Expecting value", s, err.value) from None
json.decoder.JSONDecodeError: Expecting value: line 1 column 1 (char 0)

We obtained the same error. However, to catch such errors and prevent breakdown, we can use the try/except logic to safeguard our code.

Therefore, if the API does not return any JSON value at a point of request, we can return another expression and not an error.

The above code becomes:

import urllib.parse
import urllib.request
import json
googleURL = 'http://maps.googleapis.com/maps/api/geocode/json?'
while True:
    address = input('Enter location: ')
    if address == "exit":
        break
    if len(address) < 1:
        break
    url = googleURL + urllib.parse.urlencode({'sensor': 'false',
                                              'address': address})
    print('Retrieving', url)
    uReq = urllib.request.urlopen(url)
    data = uReq.read()
    print('Returned', len(data), 'characters')
    try:
        js = json.loads(str(data))
    except:
        print("no json returned")
 
推荐文章