How to fix 'TypeError: Object of type bytes is not JSON serializable'

How to fix 'TypeError: Object of type bytes is not JSON serializable'

我正在使用 Microsoft Azures Vision API 从本地 JPEG 图像中识别手写文本。我正在编辑 Microsoft 的源代码以允许从本地源而不是 URL 识别图像。但是,我不确定如何处理此错误:'TypeError: Object of type bytes is not JSON serializable'.

image_path = "/Users/FelixWallis/Downloads/IMG_2430.jpg"

image_data = open(image_path, "rb").read()
headers = {'Ocp-Apim-Subscription-Key': subscription_key}

params  = {'mode': 'Handwritten'}
response = requests.post(
    text_recognition_url, headers=headers, params=params, json=image_data)
response.raise_for_status()


operation_url = response.headers["Operation-Location"]

analysis = {}
poll = True
while (poll):
    response_final = requests.get(
        response.headers["Operation-Location"], headers=headers)
    analysis = response_final.json()
    time.sleep(1)
    if ("recognitionResult" in analysis):
        poll= False 
    if ("status" in analysis and analysis['status'] == 'Failed'):
        poll= False

polygons=[]
if ("recognitionResult" in analysis):
    # Extract the recognized text, with bounding boxes.
    polygons = [(line["boundingBox"], line["text"])
        for line in analysis["recognitionResult"]["lines"]]

plt.figure(figsize=(15, 15))
image = Image.open(BytesIO(image_data))
ax = plt.imshow(image)
for polygon in polygons:
    vertices = [(polygon[0][i], polygon[0][i+1])
        for i in range(0, len(polygon[0]), 2)]
    text     = polygon[1]
    patch    = Polygon(vertices, closed=True, fill=False, linewidth=2, color='y')
    ax.axes.add_patch(patch)
    plt.text(vertices[0][0], vertices[0][1], text, fontsize=20, va="top")
_ = plt.axis("off")

回溯:

TypeError                                 Traceback (most recent call last)
<ipython-input-2-9eba870c3121> in <module>
     32 params  = {'mode': 'Handwritten'}
     33 response = requests.post(
---> 34     text_recognition_url, headers=headers, params=params, json=image_data)
     35 response.raise_for_status()
     36 

/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/site-packages/requests/api.py in post(url, data, json, **kwargs)
    114     """
    115 
--> 116     return request('post', url, data=data, json=json, **kwargs)
    117 
    118 

/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/site-packages/requests/api.py in request(method, url, **kwargs)
     58     # cases, and look like a memory leak in others.
     59     with sessions.Session() as session:
---> 60         return session.request(method=method, url=url, **kwargs)
     61 
     62 

/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/site-packages/requests/sessions.py in request(self, method, url, params, data, headers, cookies, files, auth, timeout, allow_redirects, proxies, hooks, stream, verify, cert, json)
    517             hooks=hooks,
    518         )
--> 519         prep = self.prepare_request(req)
    520 
    521         proxies = proxies or {}

/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/site-packages/requests/sessions.py in prepare_request(self, request)
    460             auth=merge_setting(auth, self.auth),
    461             cookies=merged_cookies,
--> 462             hooks=merge_hooks(request.hooks, self.hooks),
    463         )
    464         return p

/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/site-packages/requests/models.py in prepare(self, method, url, headers, files, data, params, auth, cookies, hooks, json)
    314         self.prepare_headers(headers)
    315         self.prepare_cookies(cookies)
--> 316         self.prepare_body(data, files, json)
    317         self.prepare_auth(auth, url)
    318 

/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/site-packages/requests/models.py in prepare_body(self, data, files, json)
    464             # provides this natively, but Python 3 gives a Unicode string.
    465             content_type = 'application/json'
--> 466             body = complexjson.dumps(json)
    467             if not isinstance(body, bytes):
    468                 body = body.encode('utf-8')

/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/json/__init__.py in dumps(obj, skipkeys, ensure_ascii, check_circular, allow_nan, cls, indent, separators, default, sort_keys, **kw)
    229         cls is None and indent is None and separators is None and
    230         default is None and not sort_keys and not kw):
--> 231         return _default_encoder.encode(obj)
    232     if cls is None:
    233         cls = JSONEncoder

/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/json/encoder.py in encode(self, o)
    197         # exceptions aren't as detailed.  The list call should be roughly
    198         # equivalent to the PySequence_Fast that ''.join() would do.
--> 199         chunks = self.iterencode(o, _one_shot=True)
    200         if not isinstance(chunks, (list, tuple)):
    201             chunks = list(chunks)

/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/json/encoder.py in iterencode(self, o, _one_shot)
    255                 self.key_separator, self.item_separator, self.sort_keys,
    256                 self.skipkeys, _one_shot)
--> 257         return _iterencode(o, 0)
    258 
    259 def _make_iterencode(markers, _default, _encoder, _indent, _floatstr,

/Library/Frameworks/Python.framework/Versions/3.7/lib/python3.7/json/encoder.py in default(self, o)
    177 
    178         """
--> 179         raise TypeError(f'Object of type {o.__class__.__name__} '
    180                         f'is not JSON serializable')
    181 

TypeError: Object of type bytes is not JSON serializable

根据你的代码和错误信息,问题是本地图片的image_data值传递给了错误的参数json(应该是data)而丢失了方法requests.post中本地图片的Content-Type头,请仔细参考the reference of Recognize Text API

这是我的代码作为参考。

import requests

image_path = '<the file path, like /Users/FelixWallis/Downloads/IMG_2430.jpg>'
image_data = open(image_path, "rb").read()

headers = {
    'Ocp-Apim-Subscription-Key': '<your subscription key>',
    'Content-Type': 'application/octet-stream'
}

params  = {'mode': 'Handwritten'}
text_recognition_url = 'https://<your cognitive service region, such as southeastasia for me>.api.cognitive.microsoft.com/vision/v2.0/recognizeText'
response = requests.post(text_recognition_url, headers=headers, params=params, data=image_data)

print(response.raw.status) # the result is 202
print(response.raise_for_status()) # the result is None

operation_url = response.headers["Operation-Location"]
print(operation_url) # the result for me is like https://southeastasia.api.cognitive.microsoft.com/vision/v2.0/textOperations/xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx