rmqrcode-python icon indicating copy to clipboard operation
rmqrcode-python copied to clipboard

Newline (`\n`) breaks encoding in some cases

Open flolilo opened this issue 11 months ago • 2 comments

Hello,

I tried to get a multi-line rMQR like this:

FOO BAR

via console:

rmqr "FOO
BAR" ./mytest.png

This breaks things:

Details

Traceback (most recent call last):
  File "./.venv/bin/rmqr", line 8, in <module>
    sys.exit(main())
             ^^^^^^
  File "./.venv/lib/python3.12/site-packages/rmqrcode/console.py", line 57, in main
    qr = _make_qr(args.DATA, ecc=ecc, version=args.version, fit_strategy=fit_strategy)
         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "./.venv/lib/python3.12/site-packages/rmqrcode/console.py", line 22, in _make_qr
    qr = rMQR.fit(data, ecc=ecc, fit_strategy=fit_strategy)
         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "./.venv/lib/python3.12/site-packages/rmqrcode/rmqrcode.py", line 73, in fit
    return rMQROptimizer.compute(data, ecc, fit_strategy)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "./.venv/lib/python3.12/site-packages/rmqrcode/rmqrcode.py", line 500, in compute
    qr.make()
  File "./.venv/lib/python3.12/site-packages/rmqrcode/rmqrcode.py", line 147, in make
    encoded_data = self._encode_data()
                   ^^^^^^^^^^^^^^^^^^^
  File "./.venv/lib/python3.12/site-packages/rmqrcode/rmqrcode.py", line 182, in _encode_data
    res += segment["encoder_class"].encode(segment["data"], character_count_indicator_length)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "./.venv/lib/python3.12/site-packages/rmqrcode/encoder/encoder_base.py", line 40, in encode
    res += cls._encoded_bits(data)
           ^^^^^^^^^^^^^^^^^^^^^^^
  File "./.venv/lib/python3.12/site-packages/rmqrcode/encoder/alphanumeric_encoder.py", line 68, in _encoded_bits
    value = cls.CHARACTER_MAP[s[0]]
            ~~~~~~~~~~~~~~~~~^^^^^^
KeyError: '\n'

However,

rmqr "FO
bBAR" ./mytest.png

works. I also thought that numbers as last pre-\n character lead to a different error, but it seems to happen with multiple combinations (FOO\nbBar also does not work) and giving reproducable examples is quite difficult. In any case, it is easy to experience with using pipes, even/odd counts of characters (e.g. FOOO vs FOO), etc.

The whole (mis)behaviour is also given when using rmqr.fit("FOO\nBAR" [...]) inside a script.

I tried to debug this myself, but the code seems to be a bit above my skill level :-/ Please let me know if I can help!

flolilo avatar Feb 09 '25 23:02 flolilo

The Alphanumeric mode cannot encode the newline character (\n). Therefore, the method AlphanumericEncoder.is_valid_characters('\n') is expected to return False. However, it currently returns True.

The same issue occurs with the NumericEncoder.

from rmqrcode.encoder import *
print(NumericEncoder.is_valid_characters('\n'))  # expected: False, actual: True
print(AlphanumericEncoder.is_valid_characters('\n'))  # expected: False, actual: True

tkamiya22 avatar Apr 23 '25 14:04 tkamiya22

This issue was fixed in a pull request #59.

rmqr "FOO
BAR" ./mytest.png

Image

tkamiya22 avatar Apr 25 '25 09:04 tkamiya22