refactor; update setup.py

more verbose logging
better error messages
This commit is contained in:
scito 2022-12-24 15:30:17 +01:00
parent 06b8efff62
commit e754befb52
6 changed files with 108 additions and 77 deletions

View File

@ -69,32 +69,33 @@ Known to work with
For protobuf versions 3.14.0 or similar or Python 3.6, use the extract_otp_secret_keys version 1.4.0.
### Linux and macOS
### Shared libs installation for reading QR code images
For reading QR code images the zbar lib must be installed.
For reading QR code images the zbar library must be installed.
If you do not extract directly from images, you do not need to install the zbar shared library.
Detailed [installation documentation for pyzbar](https://github.com/NaturalHistoryMuseum/pyzbar#installation).
For a detailed installation documentation of [pyzbar](https://github.com/NaturalHistoryMuseum/pyzbar#installation).
#### Windows
The zbar DLLs are included with the Windows Python wheels. On other operating systems, you will need to install the zbar shared library.
#### Mac OS X
brew install zbar
#### Linux (Debian, Ubuntu, ...)
sudo apt-get install libzbar0
#### Linux (OpenSUSE)
sudo zyper install libzbar0
sudo zypper install libzbar0
#### Linux (Fedora)
sudo dnf install libzbar0
#### Mac OS X
brew install zbar
## Examples
### Printing otp secrets form text file

View File

@ -100,8 +100,11 @@ def extract_otps(args):
otps = []
i = j = 0
i = j = k = 0
if verbose: print('Input files: {}'.format(args.infile))
for infile in args.infile:
if verbose: print('Processing infile {}'.format(infile))
k += 1
for line in get_lines_from_file(infile):
if verbose: print(line)
if line.startswith('#') or line == '': continue
@ -134,32 +137,32 @@ def extract_otps(args):
print()
otps.append(otp)
if verbose: print('{} infile(s) processed'.format(k))
return otps
def get_lines_from_file(filename):
# stdin stream cannot be rewinded, thus distinguish, use - for utf-8 stdin and = for binary image stdin
if filename != '=':
check_file_exists(filename)
lines = read_lines_from_text_file(filename)
if are_bytes(lines):
abort('\nBinary input was given in stdin, please use = instead of -.')
elif lines:
if lines:
return lines
# could not process text file, try reading as image
if filename != '-':
return convert_img_to_line(filename)
def read_lines_from_text_file(filename):
if filename != '=':
check_file_exists(filename)
if verbose: print('Reading lines of {}'.format(filename))
finput = fileinput.input(filename)
try:
lines = []
for line in (line.strip() for line in finput):
# TODO improve
# if verbose: print(line)
# if line.startswith('#') or line == '':
# continue
if verbose: print(line)
if is_binary(line):
abort('\nBinary input was given in stdin, please use = instead of - as infile argument for images.')
# unfortunately yield line leads to random test fails
lines.append(line)
return lines
@ -174,7 +177,7 @@ def read_lines_from_text_file(filename):
def convert_img_to_line(filename):
if filename != '-':
if verbose: print('Reading image {}'.format(filename))
try:
if filename != '=':
image = imread(filename)
@ -193,11 +196,15 @@ def convert_img_to_line(filename):
if image is None:
abort('\nERROR: Unable to open file for reading.\ninput file: {}'.format(filename))
# dynamic import of QReader since this module has a dependency to zbar lib
# dynamic import of QReader since this module has a dependency to zbar lib and import it only when necessary
try:
from qreader import QReader
except ImportError as e:
abort('\nERROR: Cannot import QReader module probably due to missing zbar shared library. Exception:\n{}'.format(str(e)))
abort('''
ERROR: Cannot import QReader module. This problem is probably due to the missing zbar shared library.
On Linux and macOS libzbar0 must be installed.
See in README.md for the installation of the libzbar0.
Exception: {}'''.format(str(e)))
decoder = QReader()
decoded_text = decoder.detect_and_decode(image=image)
@ -392,10 +399,9 @@ def check_file_exists(filename):
'\ninput file: {}'.format(filename))
def are_bytes(lines):
if lines and len(lines) > 0:
def is_binary(line):
try:
lines[0].startswith('#')
line.startswith('#')
return False
except (UnicodeDecodeError, AttributeError, TypeError):
return True

View File

@ -48,7 +48,9 @@ setup(
install_requires=[
'protobuf',
'qrcode',
'Pillow'
'Pillow',
'qreader',
'opencv-python'
],
project_urls={

View File

@ -1,3 +1,24 @@
Input files: ['example_export.txt']
Processing infile example_export.txt
Reading lines of example_export.txt
# 2FA example from https://www.raspberrypi.org/blog/setting-up-two-factor-authentication-on-your-raspberry-pi/
# Secret key: 7KSQL2JTUDIS5EF65KLMRQIIGY
# otpauth://totp/pi@raspberrypi?secret=7KSQL2JTUDIS5EF65KLMRQIIGY&issuer=raspberrypi
otpauth-migration://offline?data=CjUKEPqlBekzoNEukL7qlsjBCDYSDnBpQHJhc3BiZXJyeXBpGgtyYXNwYmVycnlwaSABKAEwAhABGAEgACjr4JKK%2B%2F%2F%2F%2F%2F8B
# otpauth://totp/pi@raspberrypi?secret=7KSQL2JTUDIS5EF65KLMRQIIGY
otpauth-migration://offline?data=CigKEPqlBekzoNEukL7qlsjBCDYSDnBpQHJhc3BiZXJyeXBpIAEoATACEAEYASAAKLzjp5n4%2F%2F%2F%2F%2FwE%3D
# otpauth://totp/pi@raspberrypi?secret=7KSQL2JTUDIS5EF65KLMRQIIGY&issuer=raspberrypi
# otpauth://totp/pi@raspberrypi?secret=7KSQL2JTUDIS5EF65KLMRQIIGY
otpauth-migration://offline?data=CigKEPqlBekzoNEukL7qlsjBCDYSDnBpQHJhc3BiZXJyeXBpIAEoATACCjUKEPqlBekzoNEukL7qlsjBCDYSDnBpQHJhc3BiZXJyeXBpGgtyYXNwYmVycnlwaSABKAEwAhABGAEgACiQ7OOa%2Bf%2F%2F%2F%2F8B
# otpauth://hotp/hotp%20demo?secret=7KSQL2JTUDIS5EF65KLMRQIIGY&counter=4
otpauth-migration://offline?data=CiUKEPqlBekzoNEukL7qlsjBCDYSCWhvdHAgZGVtbyABKAEwATgEEAEYASAAKNuv15j6%2F%2F%2F%2F%2FwE%3D
# otpauth://totp/encoding%3A%20%C2%BF%C3%A4%C3%84%C3%A9%C3%89%3F%20%28demo%29?secret=7KSQL2JTUDIS5EF65KLMRQIIGY
# Name: "encoding: ¿äÄéÉ? (demo)"
otpauth-migration://offline?data=CjYKEPqlBekzoNEukL7qlsjBCDYSHGVuY29kaW5nOiDCv8Okw4TDqcOJPyAoZGVtbykgASgBMAIQARgBIAAorfCurv%2F%2F%2F%2F%2F%2FAQ%3D%3D
# 2FA example from https://www.raspberrypi.org/blog/setting-up-two-factor-authentication-on-your-raspberry-pi/
# Secret key: 7KSQL2JTUDIS5EF65KLMRQIIGY
# otpauth://totp/pi@raspberrypi?secret=7KSQL2JTUDIS5EF65KLMRQIIGY&issuer=raspberrypi
@ -136,3 +157,4 @@ Secret: 7KSQL2JTUDIS5EF65KLMRQIIGY
Type: totp
otpauth://totp/encoding%3A%20%C2%BF%C3%A4%C3%84%C3%A9%C3%89%3F%20%28demo%29?secret=7KSQL2JTUDIS5EF65KLMRQIIGY
1 infile(s) processed

View File

@ -562,7 +562,7 @@ def test_img_qr_reader_from_stdin_wrong_symbol(capsys, monkeypatch):
# Assert
captured = capsys.readouterr()
expected_stderr = '\nBinary input was given in stdin, please use = instead of -.\n'
expected_stderr = '\nBinary input was given in stdin, please use = instead of - as infile argument for images.\n'
assert captured.err == expected_stderr
assert captured.out == ''

View File

@ -23,7 +23,7 @@ from utils import Capturing
import extract_otp_secret_keys
class TestExtract(unittest.TestCase):
class TestQRImageExtract(unittest.TestCase):
def test_img_qr_reader_happy_path(self):
with Capturing() as actual_output:
extract_otp_secret_keys.main(['test/test_googleauth_export.png'])