Skip to content

Commit ab3353a

Browse files
authored
Added tests for recognizing image from Bytes and Files (#44)
* Added tests for recognizing image from Bytes and Files * Add ability to recognize image from bytes
1 parent 0717e88 commit ab3353a

File tree

10 files changed

+230
-34
lines changed

10 files changed

+230
-34
lines changed

Makefile

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,14 @@ check_git:
88
git fetch origin
99
git diff origin/main --exit-code
1010

11-
.PHONY: clean
12-
clean:
11+
.PHONY: clean-git
12+
clean-git:
1313
git clean -dfx --exclude='tests/configuration*.json'
1414

15+
.PHONY: clean-pyc
16+
clean-pyc:
17+
find . -type f -name '*.pyc' -delete
18+
1519
.PHONY: dist
1620
dist:
1721
python3 setup.py sdist bdist_wheel --universal
@@ -58,6 +62,10 @@ publish-docker: init-docker test-tox dist
5862
test:
5963
python -Werror -m pytest --cov tests/
6064

65+
.PHONY: unittest
66+
unittest:
67+
python -Werror -m unittest discover -v
68+
6169
.PHONY: test-example
6270
test-example:
6371
python -Werror example.py

aspose_barcode_cloud/__init__.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
# coding: utf-8
22

3-
# flake8: noqa
3+
# flake8: noqa: F401
44

55
"""
66
@@ -29,6 +29,8 @@
2929

3030
from __future__ import absolute_import
3131

32+
from aspose_barcode_cloud.rest import ApiException
33+
3234
# import apis into sdk package
3335
from aspose_barcode_cloud.api.barcode_api import BarcodeApi
3436
from aspose_barcode_cloud.api.file_api import FileApi

aspose_barcode_cloud/api_client.py

Lines changed: 48 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,10 @@
2626
from __future__ import absolute_import, division
2727

2828
import datetime
29+
import io
2930
import json
3031
import mimetypes
32+
from collections import namedtuple
3133
from multiprocessing.pool import ThreadPool
3234
import os
3335
import re
@@ -37,18 +39,23 @@
3739
import six
3840
from six.moves.urllib.parse import quote
3941

42+
if not six.PY2:
43+
from typing import Union
44+
import pathlib
45+
4046
from aspose_barcode_cloud.configuration import Configuration
4147
import aspose_barcode_cloud.models
42-
from aspose_barcode_cloud import rest
48+
from aspose_barcode_cloud.rest import RESTClientObject, ApiException
49+
50+
FileFieldData = namedtuple("FileFieldData", ("file_name", "file_bytes", "mime_type"))
4351

4452

4553
class ApiClient(object):
4654
"""Generic API client for Swagger client library builds.
4755
48-
Swagger generic API client. This client handles the client-
49-
server communication, and is invariant across implementations. Specifics of
50-
the methods and models for each application are generated from the Swagger
51-
templates.
56+
Swagger generic API client. This client handles the client-server communication,
57+
and is invariant across implementations. Specifics of the methods and
58+
models for each application are generated from the Swagger templates.
5259
5360
NOTE: This class is auto generated by the swagger code generator program.
5461
Ref: https://github.com/swagger-api/swagger-codegen
@@ -81,7 +88,7 @@ def __init__(self, configuration=None, header_name=None, header_value=None, cook
8188

8289
# Use the pool property to lazily initialize the ThreadPool.
8390
self._pool = None
84-
self.rest_client = rest.RESTClientObject(configuration)
91+
self.rest_client = RESTClientObject(configuration)
8592
self.default_headers = {
8693
"x-aspose-client": "python sdk",
8794
"x-aspose-client-version": "22.8.0",
@@ -485,7 +492,7 @@ def parameters_to_tuples(self, params, collection_formats):
485492
new_params = []
486493
if collection_formats is None:
487494
collection_formats = {}
488-
for k, v in six.iteritems(params) if isinstance(params, dict) else params: # noqa: E501
495+
for k, v in six.iteritems(params) if isinstance(params, dict) else params:
489496
if k in collection_formats:
490497
collection_format = collection_formats[k]
491498
if collection_format == "multi":
@@ -504,29 +511,48 @@ def parameters_to_tuples(self, params, collection_formats):
504511
new_params.append((k, v))
505512
return new_params
506513

514+
def is_not_ascii(self, string):
515+
return any(ord(c) >= 128 for c in string)
516+
517+
def prepare_one_file(self, file_data):
518+
# type: (Union[bytes, str, file, pathlib.Path, io.BytesIO]) -> FileFieldData # noqa: F821
519+
520+
# Python 2 has no difference between Bytes and Str
521+
# So decide non-ascii string is Bytes
522+
if isinstance(file_data, bytes) and (not six.PY2 or self.is_not_ascii(file_data)):
523+
return FileFieldData("data.bin", file_data, "application/octet-stream")
524+
525+
if isinstance(file_data, str) or (not six.PY2 and isinstance(file_data, pathlib.PurePath)):
526+
with open(file_data, "rb") as f:
527+
fname = os.path.basename(f.name)
528+
file_bytes = f.read()
529+
mime_type = mimetypes.guess_type(fname)[0] or "application/octet-stream"
530+
return FileFieldData(fname, file_bytes, mime_type)
531+
532+
if isinstance(file_data, io.BytesIO):
533+
return FileFieldData("data.bin", file_data.read(), "application/octet-stream")
534+
535+
if isinstance(file_data, io.BufferedReader) or (six.PY2 and isinstance(file_data, file)): # noqa: F821
536+
return FileFieldData(os.path.basename(file_data.name), file_data.read(), "application/octet-stream")
537+
538+
raise ApiException(reason="Unknown type {type_name} for file parameter".format(type_name=type(file_data)))
539+
507540
def prepare_post_parameters(self, post_params=None, files=None):
508541
"""Builds form parameters.
509542
510543
:param post_params: Normal form parameters.
511544
:param files: File parameters.
512545
:return: Form parameters with files.
513546
"""
514-
params = []
515-
516-
if post_params:
517-
params = post_params
547+
params = post_params or []
518548

519549
if files:
520-
for k, v in six.iteritems(files):
521-
if not v:
550+
for field_name, data in six.iteritems(files):
551+
if not data:
522552
continue
523-
file_names = v if type(v) is list else [v]
524-
for n in file_names:
525-
with open(n, "rb") as f:
526-
filename = os.path.basename(f.name)
527-
filedata = f.read()
528-
mimetype = mimetypes.guess_type(filename)[0] or "application/octet-stream"
529-
params.append(tuple([k, tuple([filename, filedata, mimetype])]))
553+
file_names = data if type(data) is list else [data]
554+
for file_data in file_names:
555+
params.append((field_name, self.prepare_one_file(file_data)))
530556

531557
return params
532558

@@ -642,7 +668,7 @@ def __deserialize_date(self, string):
642668
except ImportError:
643669
return string
644670
except ValueError:
645-
raise rest.ApiException(status=0, reason="Failed to parse '{0}' as date object".format(string))
671+
raise ApiException(reason="Failed to parse '{0}' as date object".format(string))
646672

647673
def __deserialize_datetime(self, string):
648674
"""Deserializes string to datetime.
@@ -659,7 +685,7 @@ def __deserialize_datetime(self, string):
659685
except ImportError:
660686
return string
661687
except ValueError:
662-
raise rest.ApiException(status=0, reason=("Failed to parse '{0}' as datetime object".format(string)))
688+
raise ApiException(reason=("Failed to parse '{0}' as datetime object".format(string)))
663689

664690
def __hasattr(self, object, name):
665691
return name in object.__class__.__dict__

aspose_barcode_cloud/rest.py

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -229,15 +229,15 @@ def _request(
229229
msg = """Cannot prepare a request message for provided
230230
arguments. Please check that your arguments match
231231
declared content type."""
232-
raise ApiException(status=0, reason=msg)
232+
raise ApiException(reason=msg)
233233
# For 'GET', 'HEAD'
234234
else:
235235
r = self.pool_manager.request(
236236
method, url, fields=query_params, preload_content=_preload_content, timeout=timeout, headers=headers
237237
)
238238
except urllib3.exceptions.SSLError as e:
239239
msg = "{0}\n{1}".format(type(e).__name__, str(e))
240-
raise ApiException(status=0, reason=msg)
240+
raise ApiException(reason=msg)
241241

242242
if _preload_content:
243243
r = RESTResponse(r)
@@ -375,7 +375,8 @@ def close(self):
375375

376376

377377
class ApiException(Exception):
378-
def __init__(self, status=None, reason=None, http_resp=None):
378+
def __init__(self, status=0, reason=None, http_resp=None):
379+
# type: (int, str, RESTResponse) -> None
379380
if http_resp:
380381
self.status = http_resp.status
381382
self.reason = http_resp.reason

tests/test_auth.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22

33
import unittest
44

5-
from aspose_barcode_cloud import Configuration, ApiClient, BarcodeApi, EncodeBarcodeType
5+
from aspose_barcode_cloud import Configuration, ApiClient, BarcodeApi, EncodeBarcodeType, ApiException
66
from .load_configuration import TEST_CONFIGURATION
77

88

@@ -37,7 +37,7 @@ def test_works_with_access_token(self):
3737
def test_unauthorized_raises(self):
3838
api = BarcodeApi(ApiClient(Configuration(access_token="incorrect token", host=TEST_CONFIGURATION.host)))
3939

40-
with self.assertRaises(Exception) as context:
40+
with self.assertRaises(ApiException) as context:
4141
api.get_barcode_generate(EncodeBarcodeType.QR, "Testing")
4242

4343
self.assertEqual(401, context.exception.status)

tests/test_barcode_api.py

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -26,10 +26,13 @@ class TestBarcodeApi(unittest.TestCase):
2626

2727
@classmethod
2828
def setUpClass(cls):
29-
cls.test_filename = os.path.join("testdata", "pdf417Sample.png")
29+
cls.test_filename = os.path.abspath(
30+
os.path.join(os.path.dirname(__file__), "..", "testdata", "pdf417Sample.png")
31+
)
3032

3133
cls.api_client = ApiClient(configuration=TEST_CONFIGURATION)
3234

35+
# noinspection PyUnresolvedReferences
3336
cls.api = BarcodeApi(api_client=cls.api_client)
3437
cls.temp_folder_path = "BarcodeTests/%s" % uuid.uuid4()
3538

@@ -49,7 +52,9 @@ def test_get_barcode_recognize(self):
4952
5053
Recognize barcode from a file on server.
5154
"""
52-
filename = self.upload_test_file("testdata/pdf417Sample.png")
55+
filename = self.upload_test_file(
56+
file_path=os.path.abspath(os.path.join(os.path.dirname(__file__), "..", "testdata", "pdf417Sample.png"))
57+
)
5358

5459
response = self.api.get_barcode_recognize(
5560
filename, folder=self.temp_folder_path, preset=PresetType.HIGHPERFORMANCE
@@ -154,10 +159,11 @@ def test_put_generate_multiple(self):
154159
self.assertGreater(response.image_height, 0)
155160

156161
def upload_test_file(self, file_path):
162+
self.assertTrue(os.path.isfile(file_path))
157163
file_api = FileApi(self.api_client)
158-
file_name = os.path.split(file_path)[-1]
164+
fname = os.path.basename(file_path)
159165

160-
upload_result = file_api.upload_file(self.temp_folder_path + "/" + file_name, file_path)
166+
upload_result = file_api.upload_file(path=self.temp_folder_path + "/" + fname, file=file_path)
161167

162168
self.assertFalse(upload_result.errors, str(upload_result.errors))
163169
self.assertTrue(upload_result.uploaded)

tests/test_recognize_bytes.py

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
import io
2+
import os
3+
import unittest
4+
5+
from aspose_barcode_cloud import PresetType, ApiClient, BarcodeApi, DecodeBarcodeType
6+
from .load_configuration import TEST_CONFIGURATION
7+
8+
9+
class TestRecognizeBytes(unittest.TestCase):
10+
@classmethod
11+
def setUpClass(cls):
12+
cls.test_filename = os.path.abspath(
13+
os.path.join(os.path.dirname(__file__), "..", "testdata", "pdf417Sample.png")
14+
)
15+
16+
cls.api = BarcodeApi(api_client=ApiClient(configuration=TEST_CONFIGURATION))
17+
18+
def test_post_barcode_recognize_from_url_or_content_bytes(self):
19+
"""Test case for post_barcode_recognize_from_url_or_content
20+
21+
Recognize barcode from bytes.
22+
"""
23+
with open(self.test_filename, "rb") as f:
24+
image_bytes = f.read()
25+
26+
response = self.api.post_barcode_recognize_from_url_or_content(
27+
preset=PresetType.HIGHPERFORMANCE,
28+
image=image_bytes,
29+
)
30+
31+
self.assertEqual(1, len(response.barcodes))
32+
barcode = response.barcodes[0]
33+
self.assertEqual(DecodeBarcodeType.PDF417, barcode.type)
34+
self.assertEqual("Aspose.BarCode for Cloud Sample", barcode.barcode_value)
35+
36+
def test_post_barcode_recognize_from_url_or_content_BytesIO(self):
37+
"""Test case for post_barcode_recognize_from_url_or_content
38+
39+
Recognize barcode from BytesIO.
40+
"""
41+
with open(self.test_filename, "rb") as f:
42+
bytes_io = io.BytesIO(f.read())
43+
44+
response = self.api.post_barcode_recognize_from_url_or_content(
45+
preset=PresetType.HIGHPERFORMANCE,
46+
image=bytes_io,
47+
)
48+
49+
self.assertEqual(1, len(response.barcodes))
50+
barcode = response.barcodes[0]
51+
self.assertEqual(DecodeBarcodeType.PDF417, barcode.type)
52+
self.assertEqual("Aspose.BarCode for Cloud Sample", barcode.barcode_value)

tests/test_recognize_file.py

Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
import os
2+
import sys
3+
4+
import six
5+
import unittest
6+
7+
from aspose_barcode_cloud import PresetType, ApiClient, BarcodeApi, DecodeBarcodeType
8+
from .load_configuration import TEST_CONFIGURATION
9+
10+
if not six.PY2:
11+
import pathlib
12+
13+
PY35orLess = sys.version_info[0:2] <= (3, 5)
14+
15+
16+
class TestRecognizeFile(unittest.TestCase):
17+
@classmethod
18+
def setUpClass(cls):
19+
cls.test_filename = os.path.abspath(
20+
os.path.join(os.path.dirname(__file__), "..", "testdata", "pdf417Sample.png")
21+
)
22+
23+
cls.api = BarcodeApi(api_client=ApiClient(configuration=TEST_CONFIGURATION))
24+
25+
def test_post_barcode_recognize_from_url_or_content_filename(self):
26+
"""Test case for post_barcode_recognize_from_url_or_content
27+
28+
Recognize barcode from a local file.
29+
"""
30+
31+
response = self.api.post_barcode_recognize_from_url_or_content(
32+
preset=PresetType.HIGHPERFORMANCE,
33+
image=self.test_filename,
34+
)
35+
36+
self.assertEqual(1, len(response.barcodes))
37+
barcode = response.barcodes[0]
38+
self.assertEqual(DecodeBarcodeType.PDF417, barcode.type)
39+
self.assertEqual("Aspose.BarCode for Cloud Sample", barcode.barcode_value)
40+
41+
@unittest.skipIf(PY35orLess, "No pathlib in Python2 and Python3.5 raises an error")
42+
def test_post_barcode_recognize_from_url_or_content_pathlike(self):
43+
"""Test case for post_barcode_recognize_from_url_or_content
44+
45+
Recognize barcode from a local file by pathlike.
46+
"""
47+
48+
response = self.api.post_barcode_recognize_from_url_or_content(
49+
preset=PresetType.HIGHPERFORMANCE,
50+
image=pathlib.Path(self.test_filename),
51+
)
52+
53+
self.assertEqual(1, len(response.barcodes))
54+
barcode = response.barcodes[0]
55+
self.assertEqual(DecodeBarcodeType.PDF417, barcode.type)
56+
self.assertEqual("Aspose.BarCode for Cloud Sample", barcode.barcode_value)
57+
58+
def test_post_barcode_recognize_from_url_or_content_file_obj(self):
59+
"""Test case for post_barcode_recognize_from_url_or_content
60+
61+
Recognize barcode from a local file obj.
62+
"""
63+
with open(self.test_filename, "rb") as file_obj:
64+
response = self.api.post_barcode_recognize_from_url_or_content(
65+
preset=PresetType.HIGHPERFORMANCE,
66+
image=file_obj,
67+
)
68+
69+
self.assertEqual(1, len(response.barcodes))
70+
barcode = response.barcodes[0]
71+
self.assertEqual(DecodeBarcodeType.PDF417, barcode.type)
72+
self.assertEqual("Aspose.BarCode for Cloud Sample", barcode.barcode_value)

0 commit comments

Comments
 (0)