Closed JustLnF closed 2 years ago
Any chance you could create another QR with dummy data or point to what created the QR code?
This QR Code is generated by the government according to the DIVOC standard that contains COVID vaccination status https://divoc.egov.org.in/implementing-divoc/what-information-goes-into-a-qr-code
It is just a zip file binary data with only 1 file inside named certificate.json
What I can see is that the binary data detected by pyboof is inserting null bytes (possibly other bytes) when assigned to a python string that caused the binary data to be corrupted/invalid.
The null bytes comment is a good hint. Are you comfortable building the project? This will probably require a bit of guess and check to fix. Unrelated, I'm also planning on updating PyBoof to the latest version of BoofCV which can read transposed QRs.
Sure, i don't mind building the project. Will you be able to point me into the direction of what I can do to debug?
Basically follow instructions in the readme.md to install from source then try running your code and see if it works. There's a new branch that I'll be working in release40 that you should checkout. I just finished updating it. There is an extremely slim chance the issue could be fixed since I updated a few dependencies also. If it fails when you build Java let me know. I'll update the build script to make it even easier to use.
pip3 install -r requirements.txt giving this error for opencv-python
ERROR: Could not find a version that satisfies the requirement opencv-python==4.2.0.34 (from versions: 3.4.0.14, 3.4.10.37, 3.4.11.39, 3.4.11.41, 3.4.11.43, 3.4.11.45, 3.4.13.47, 3.4.14.51, 3.4.14.53, 3.4.15.55, 3.4.16.57, 3.4.16.59, 3.4.17.61, 4.3.0.38, 4.4.0.40, 4.4.0.42, 4.4.0.44, 4.4.0.46, 4.5.1.48, 4.5.2.52, 4.5.2.54, 4.5.3.56, 4.5.4.58, 4.5.4.60, 4.5.5.62)
ERROR: No matching distribution found for opencv-python==4.2.0.34
But i have installed it separately using pip3 install opencv-python.
Update: Built release40 branch and results is the same.
Will pyboof be able to somehow return bytes instead of assigning it into a string?
That can be added. Not all the information has been propagated into the python wrapper. I'll try that next.
That can be added. Not all the information has been propagated into the python wrapper. I'll try that next.
Thank you very much
Sorry, just to check do you have any possible timeline of which the library can be updated with the bytes value support?
I'll try it today. It's already available in Java. Just a matter of copying it over efficiently.
QrCode structure now has a field 'corrected' which is the raw byte after error correction has been applied. I'm not 100% sure if this is what you need since it will include the null terminator and padding bits, but it's worth a try. I might need to add the size of the raw message, excluding padding bits. This will be more involved since BoofCV will need to be modified.
I might know how to solve this! Tell it which encoding to use, then decode it using that known encoding. Accessing the correct raw bytes would work, but you're going to need to know the message format very well...
config.forceEncoding = "UTF-8"
detector = pb.FactoryFiducial(np.uint8).qrcode(config)
detector.detect(image)
for qr in detector.detections:
data = bytes(qr.message, 'utf-8')
QrCode structure now has a field 'corrected' which is the raw byte after error correction has been applied. I'm not 100% sure if this is what you need since it will include the null terminator and padding bits, but it's worth a try. I might need to add the size of the raw message, excluding padding bits. This will be more involved since BoofCV will need to be modified.
Unfortunately, the raw bytes now being recognized as application/octet-stream instead of application/zip.
config.forceEncoding = "UTF-8"
detector = pb.FactoryFiducial(np.uint8).qrcode(config)
detector.detect(image)
for qr in detector.detections:
data = bytes(qr.message, 'utf-8')
This produces the same string as not specifying the encoding.
Seems like the raw bytes like what you mentioned is still not working as it still has padding and null terminator.
Can I contact you via email or other mediums in addition to here?
Think I found the issue. If it can't determine the encoding to use it was defaulting to UTF-8. This would change the values of some bytes as not all raw bytes have a mapping to UTF-8. Things get a bit tricky here. The QR code specification says that you would convert it to a raw JIS8 string. That format uses all 8-bit values. Literally no one uses JIS8 and UTF-8 is more common by defacto. I'm going to see if changing the behavior to using raw values if it doesn't look like UTF-8 is a good fit works. Hopefully I don't horribly break things...
The latest release40 build having this error for some qr codes.
File "/usr/local/lib/python3.9/site-packages/PyBoof-0.40.0-py3.9.egg/pyboof/recognition.py", line 323, in detect
E self.failures = [QrCode(x) for x in self.java_obj.getFailures()]
E File "/usr/local/lib/python3.9/site-packages/PyBoof-0.40.0-py3.9.egg/pyboof/recognition.py", line 323, in <listcomp>
E self.failures = [QrCode(x) for x in self.java_obj.getFailures()]
E File "/usr/local/lib/python3.9/site-packages/PyBoof-0.40.0-py3.9.egg/pyboof/recognition.py", line 291, in __init__
E self.corrected = mmap_array_java_to_python(jobj.corrected, MmapType.ARRAY_U8)
E File "/usr/local/lib/python3.9/site-packages/PyBoof-0.40.0-py3.9.egg/pyboof/common.py", line 167, in mmap_array_java_to_python
E num_elements = len(java_array)
E TypeError: object of type 'NoneType' has no len()
This was resolved by updating the underlying BoofCV library to better handle detection of UTF-8 encoding. You can now specify "binary" encoding and it will not modify the incoming BYTE data and it will tell you wish encoding it selected for each individual QR code. Most of the time the code below should work:
for qr in detector.detections:
data = bytes(qr.message, qr.byteEncoding)
Alternatively, you can force "binary" and convert the string to a bytearray using the specified function.
config = pb.ConfigQrCode()
config.forceEncoding = "binary"
detector = pb.FactoryFiducial(np.uint8).qrcode(config)
detector.detect(image)
for qr in detector.detections:
data = pb.string_to_bytearray(qr.message)
Hi, I am using pyboof qr detection and it has been working great.
However, it has come to my attention that if the qr code content contains binary data of a zipfile, converting to base64 from qr.message results in a corrupted/invalid zipfile. However, using other qr reader library in node.js it is able to detect and convert to base64 and open up the zipfile correctly.
Unfortunately I am not able to include the qr content as it contains private information.