From c122387ef7f13ca342179fce87d56136e85bbeaa Mon Sep 17 00:00:00 2001 From: Stefan Krulj Date: Mon, 1 Jan 2024 20:06:19 +0000 Subject: [PATCH 1/7] Add NFCPy support --- .../developers/rfid/generic_nfcpy.md | 24 +++++ .../rfid/hardware/generic_nfcpy/README.md | 2 + .../hardware/generic_nfcpy/description.py | 3 + .../hardware/generic_nfcpy/generic_nfcpy.py | 90 +++++++++++++++++++ .../hardware/generic_nfcpy/requirements.txt | 4 + 5 files changed, 123 insertions(+) create mode 100644 documentation/developers/rfid/generic_nfcpy.md create mode 100644 src/jukebox/components/rfid/hardware/generic_nfcpy/README.md create mode 100644 src/jukebox/components/rfid/hardware/generic_nfcpy/description.py create mode 100644 src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py create mode 100644 src/jukebox/components/rfid/hardware/generic_nfcpy/requirements.txt diff --git a/documentation/developers/rfid/generic_nfcpy.md b/documentation/developers/rfid/generic_nfcpy.md new file mode 100644 index 000000000..1672c68bc --- /dev/null +++ b/documentation/developers/rfid/generic_nfcpy.md @@ -0,0 +1,24 @@ +# Generic NFCPy Reader + +This module is based on the user space NFC reader library [nfcpy](https://nfcpy.readthedocs.io/en/latest/overview.html) ([on github](https://github.com/nfcpy/nfcpy)). +The link above also contains a list of supported devices. + +The goal of this module is to handle USB NFC devices, that don't have a HID-keyboard +driver, and thus cannot be used with the [genericusb](genericusb.md) module. + +## Installation + +Since nfcpy is a user-space library, it is required to supress the kernel from loading its driver: + `echo 'install /bin/true' > /etc/modprobe.d/disable_.conf` + +Where is one of the following: + - `pn533_usb` for PN531 PN532 and PN533 based devices connected via USB + - `pn532_uart`\* for PN532 based devices connected via UART (or a UART-to-USB chip) + - `port100`\* for Port100 based devices + - `pn533_usb`\* for RC-S956 based devices + +After the driver has been blacklisted. Unplug the device. Then either do `rmmod ` + +[!NOTE] +\* Needs to be verified. + diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/README.md b/src/jukebox/components/rfid/hardware/generic_nfcpy/README.md new file mode 100644 index 000000000..f1c92ded0 --- /dev/null +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/README.md @@ -0,0 +1,2 @@ + +For documentation see [documentation/developers/rfid/generic_nfcpy.md](../../../../../../documentation/developers/rfid/generic_nfcpy.md). diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/description.py b/src/jukebox/components/rfid/hardware/generic_nfcpy/description.py new file mode 100644 index 000000000..13c7c5038 --- /dev/null +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/description.py @@ -0,0 +1,3 @@ +""" List of supprted devices https://nfcpy.readthedocs.io/en/latest/overview.html""" +# 40 chars: '========================================' +DESCRIPTION = 'Generic NFCPY NFC Reader Module' diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py b/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py new file mode 100644 index 000000000..779979140 --- /dev/null +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py @@ -0,0 +1,90 @@ +# Standard imports from python packages +import logging + +import nfc +from nfc.clf import RemoteTarget + +# Import the ReaderBaseClass for common API. Leave as this line as it is! +from components.rfid import ReaderBaseClass +import jukebox.cfghandler + +# Also import the description string into this module, to make everything available in a single module w/o code duplication +# Leave this line as is! +from .description import DESCRIPTION + +# Create logger. +# Logging is fully setup. Just replace '.new' with something meaningful and short +logger = logging.getLogger('jb.rfid.new') +# Get the global handler to the RFID config +cfg = jukebox.cfghandler.get_handler('rfid') + + + + +def query_customization() -> dict: + """ + Query the user for reader parameter customization + """ + return {} + + +class ReaderClass(ReaderBaseClass): + """ + The reader class for nfcpy supported NFC card readers. + """ + def __init__(self, reader_cfg_key): + # Create a per-instance logger, just in case the reader will run multiple times in various threads + # Replace '.new' with something meaningful and short + self._logger = logging.getLogger(f'jb.rfid.new({reader_cfg_key})') + # Initialize the super-class. Don't change anything here + super().__init__(reader_cfg_key=reader_cfg_key, description=DESCRIPTION, logger=self._logger) + + # Get the configuration from the rfid.yaml: + # Lock config around the access + #with cfg: + # # Get a reference to the actual reader-specific config + # config = cfg.getn('rfid', 'readers', reader_cfg_key, 'config', default=None) + # # No config + + self.clf = nfc.ContactlessFrontend('usb') + + self._keep_running = True + + def cleanup(self): + """ + The cleanup function: free and release all resources used by this card reader (if any). + """ + self.clf.close() + + def stop(self): + """ + This function is called to tell the reader to exit its reading function. + """ + self._keep_running = False + + def read_card(self) -> str: + """ + Blocking or non-blocking function that waits for a new card to appear and return the card's UID as string + """ + self._logger.debug("Wait for card") + while self._keep_running: + target = self.clf.sense(RemoteTarget('106A'), + RemoteTarget('106B'), + RemoteTarget('212F'), + interval=0.1, + iterations=1) + if not target: + continue + + tag = nfc.tag.activate(self.clf, target) + if not tag: + continue + + id = '' + for char in tag.identifier: + id += '%02X' % char + + self._logger.debug(f'Found card with ID: "{id}"') + return id + self._logger.debug("NFC read stopped") + return '' diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/requirements.txt b/src/jukebox/components/rfid/hardware/generic_nfcpy/requirements.txt new file mode 100644 index 000000000..8fb09c9db --- /dev/null +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/requirements.txt @@ -0,0 +1,4 @@ +# NFCPy related requirements +# You need to install these with `python -m pip install --upgrade --force-reinstall -q -r requirements.txt` + +nfcpy From d00715dc171cf4eb946e8aea1c1a59420e5c16da Mon Sep 17 00:00:00 2001 From: Stefan Krulj Date: Sat, 6 Jan 2024 01:58:22 +0100 Subject: [PATCH 2/7] Fixed PR comments --- .../developers/rfid/generic_nfcpy.md | 23 +++--- .../hardware/generic_nfcpy/description.py | 2 +- .../hardware/generic_nfcpy/generic_nfcpy.py | 71 +++++++++++++++---- .../rfid/hardware/generic_nfcpy/setup.inc.sh | 44 ++++++++++++ 4 files changed, 109 insertions(+), 31 deletions(-) create mode 100644 src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh diff --git a/documentation/developers/rfid/generic_nfcpy.md b/documentation/developers/rfid/generic_nfcpy.md index 1672c68bc..cecdb8dc5 100644 --- a/documentation/developers/rfid/generic_nfcpy.md +++ b/documentation/developers/rfid/generic_nfcpy.md @@ -1,24 +1,17 @@ # Generic NFCPy Reader This module is based on the user space NFC reader library [nfcpy](https://nfcpy.readthedocs.io/en/latest/overview.html) ([on github](https://github.com/nfcpy/nfcpy)). -The link above also contains a list of supported devices. +The link above also contains a list of [supported devices](https://nfcpy.readthedocs.io/en/latest/overview.html#supported-devices). The goal of this module is to handle USB NFC devices, that don't have a HID-keyboard driver, and thus cannot be used with the [genericusb](genericusb.md) module. -## Installation +> [!NOTE] +> Since nfcpy is a user-space library, it is required to supress the kernel from loading its driver. +> The setup will do this automatically, so make sure the device is connected +> before running the [RFID reader configuration tool](../coreapps.md#RFID-Reader). -Since nfcpy is a user-space library, it is required to supress the kernel from loading its driver: - `echo 'install /bin/true' > /etc/modprobe.d/disable_.conf` - -Where is one of the following: - - `pn533_usb` for PN531 PN532 and PN533 based devices connected via USB - - `pn532_uart`\* for PN532 based devices connected via UART (or a UART-to-USB chip) - - `port100`\* for Port100 based devices - - `pn533_usb`\* for RC-S956 based devices - -After the driver has been blacklisted. Unplug the device. Then either do `rmmod ` - -[!NOTE] -\* Needs to be verified. +# Configuration +By setting `rfid > readers > generic_nfcpy > config > device_path` you can override the +device location. For possible values see the `path` parameter in this [nfcpy documentation](https://nfcpy.readthedocs.io/en/latest/modules/clf.html#nfc.clf.ContactlessFrontend.open) diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/description.py b/src/jukebox/components/rfid/hardware/generic_nfcpy/description.py index 13c7c5038..eea9438eb 100644 --- a/src/jukebox/components/rfid/hardware/generic_nfcpy/description.py +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/description.py @@ -1,3 +1,3 @@ -""" List of supprted devices https://nfcpy.readthedocs.io/en/latest/overview.html""" +""" List of supported devices https://nfcpy.readthedocs.io/en/latest/overview.html""" # 40 chars: '========================================' DESCRIPTION = 'Generic NFCPY NFC Reader Module' diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py b/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py index 779979140..9be37cf17 100644 --- a/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py @@ -2,30 +2,71 @@ import logging import nfc +import glob from nfc.clf import RemoteTarget # Import the ReaderBaseClass for common API. Leave as this line as it is! from components.rfid import ReaderBaseClass import jukebox.cfghandler +import misc.inputminus as pyil +from misc.simplecolors import Colors # Also import the description string into this module, to make everything available in a single module w/o code duplication # Leave this line as is! from .description import DESCRIPTION # Create logger. -# Logging is fully setup. Just replace '.new' with something meaningful and short -logger = logging.getLogger('jb.rfid.new') +logger = logging.getLogger('jb.rfid.nfcpy') # Get the global handler to the RFID config cfg = jukebox.cfghandler.get_handler('rfid') - - def query_customization() -> dict: - """ - Query the user for reader parameter customization - """ - return {} + possible_device_ids = [ + "usb:054c:02e1", + "usb:054c:06c1", + "usb:054c:06c3", + "usb:054c:0193", + "usb:04cc:0531", + "usb:072f:2200", + "usb:04e6:5591", + "usb:04e6:5593", + "usb:04cc:2533", + ] + + devices = [] + clf = nfc.ContactlessFrontend() + + # find usb devices + for device_id in possible_device_ids: + if clf.open(device_id): + devices.append({'id': device_id, 'vendor': clf.device.vendor_name, 'name': clf.device.product_name}) + clf.close() + + # find tty device + matching_files = glob.glob("/dev/ttyUSB[0-9]*") + matching_files += glob.glob("/dev/ttyACM[0-9]*") + for file_path in matching_files: + for device_id in (f'{file_path}:pn532', f'{file_path}:arygon'): + if clf.open(device_id): + devices.append({'id': device_id, 'vendor': clf.device.vendor_name, 'name': clf.device.product_name}) + clf.close() + + print("\nChoose RFID device from USB device list:\n") + logger.debug(f"USB devices: {[x['name'] for x in devices]}") + if len(devices) == 0: + if len(devices) == 0: + logger.error("USB device list is empty. Make sure USB RFID reader is connected. Then re-run register_reader.py") + return {'device_path': None} + + for idx, dev in enumerate(devices): + print(f" {Colors.lightgreen}{idx:2d}{Colors.reset}:" + f"{Colors.lightcyan}{Colors.bold}{dev['vendor']} {dev['name']}{Colors.reset}") + + dev_id = pyil.input_int("Device number?", min=0, max=len(devices) - 1, prompt_color=Colors.lightgreen, prompt_hint=True) + device_path = devices[dev_id]['id'] + + return {'device_path': device_path} class ReaderClass(ReaderBaseClass): @@ -34,19 +75,19 @@ class ReaderClass(ReaderBaseClass): """ def __init__(self, reader_cfg_key): # Create a per-instance logger, just in case the reader will run multiple times in various threads - # Replace '.new' with something meaningful and short - self._logger = logging.getLogger(f'jb.rfid.new({reader_cfg_key})') + self._logger = logging.getLogger(f'jb.rfid.nfcpy({reader_cfg_key})') # Initialize the super-class. Don't change anything here super().__init__(reader_cfg_key=reader_cfg_key, description=DESCRIPTION, logger=self._logger) # Get the configuration from the rfid.yaml: # Lock config around the access - #with cfg: - # # Get a reference to the actual reader-specific config - # config = cfg.getn('rfid', 'readers', reader_cfg_key, 'config', default=None) - # # No config + with cfg: + # Get a reference to the actual reader-specific config + config = cfg.getn('rfid', 'readers', reader_cfg_key, 'config', default=None) - self.clf = nfc.ContactlessFrontend('usb') + device_path = config.setdefault('device_path', None) + self.clf = nfc.ContactlessFrontend() + self.clf.open(device_path) self._keep_running = True diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh b/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh new file mode 100644 index 000000000..7057c2ed4 --- /dev/null +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh @@ -0,0 +1,44 @@ +#!/usr/bin/env bash + +modprobe_file="/etc/modprobe.d/disable_driver_jukebox_nfcpy.conf" + + +if lsmod | grep "pn533_usb"; then + sudo rmmod pn533_usb 2>/dev/null + sudo sh -c "echo 'install pn533_usb /bin/true' >> $modprobe_file" +fi + +if lsmod | grep "port100"; then + sudo rmmod port100 2>/dev/null + sudo sh -c "echo 'install v /bin/true' >> $modprobe_file" +fi + +udev_file="/etc/udev/rules.d/50-usb-nfc-rule.rules" + +usb_devices=$(lsusb | sed -e 's/.*ID \([a-f0-9]\+:[a-f0-9]\+\).*/\1/g') + +valid_device_ids=( + "054c:02e1" + "054c:06c1" + "054c:06c3" + "054c:0193" + "04cc:0531" + "04cc:2533" + "072f:2200" + "04e6:5591" + "04e6:5593" +) + +for dev in $usb_devices; do + if echo ${valid_device_ids[@]} | grep -woq $dev; then + #$dev is in valid id array + VID="${dev%%:*}" + PID="${dev#*:}" + sudo sh -c "echo 'SUBSYSTEM==\"usb\", ATTRS{idVendor}==\"$VID\", ATTRS{idProduct}==\"$PID\", MODE=\"0666\"' >> $udev_file" + fi +done +sudo udevadm control --reload-rules +sudo udevadm trigger + +sudo gpasswd -a pi dialout +sudo gpasswd -a pi tty \ No newline at end of file From 76550f2d5920419fe7eb9e2c1c7e534a5670f7c2 Mon Sep 17 00:00:00 2001 From: Stefan Krulj Date: Mon, 29 Jan 2024 02:26:22 +0100 Subject: [PATCH 3/7] Improve documentation, add an example --- .../developers/rfid/generic_nfcpy.md | 23 +++++++++++++++++-- 1 file changed, 21 insertions(+), 2 deletions(-) diff --git a/documentation/developers/rfid/generic_nfcpy.md b/documentation/developers/rfid/generic_nfcpy.md index cecdb8dc5..bea7b302a 100644 --- a/documentation/developers/rfid/generic_nfcpy.md +++ b/documentation/developers/rfid/generic_nfcpy.md @@ -13,5 +13,24 @@ driver, and thus cannot be used with the [genericusb](genericusb.md) module. # Configuration -By setting `rfid > readers > generic_nfcpy > config > device_path` you can override the -device location. For possible values see the `path` parameter in this [nfcpy documentation](https://nfcpy.readthedocs.io/en/latest/modules/clf.html#nfc.clf.ContactlessFrontend.open) +The installation script will scan for compatible devices and will assist in configuration. +By setting `rfid > readers > generic_nfcpy > config > device_path` in `shared/settings/rfid.yaml` you can override the +device location. By specifying an explicit device location it is possible to use multiple readers compatible with NFCpy. + +Example configuration for a usb-device with vendor ID 072f and product ID 2200: +```yaml +rfid: + readers: + read_00: + module: generic_nfcpy + config: + device_path: usb:072f:2200 + same_id_delay: 1.0 + log_ignored_cards: false + place_not_swipe: + enabled: false + card_removal_action: + alias: pause +``` + +For possible values see the `path` parameter in this [nfcpy documentation](https://nfcpy.readthedocs.io/en/latest/modules/clf.html#nfc.clf.ContactlessFrontend.open) \ No newline at end of file From d780b38165d7ab94cf8ae757f1b9ae6110a16b58 Mon Sep 17 00:00:00 2001 From: Stefan Krulj Date: Mon, 29 Jan 2024 02:47:39 +0100 Subject: [PATCH 4/7] Fix setup.inc.sh execution rights --- src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh | 0 1 file changed, 0 insertions(+), 0 deletions(-) mode change 100644 => 100755 src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh b/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh old mode 100644 new mode 100755 From 5d00ff87ab12809e46ae90c295e7bc763fb35536 Mon Sep 17 00:00:00 2001 From: Stefan Krulj Date: Tue, 30 Jan 2024 20:43:11 +0100 Subject: [PATCH 5/7] Fix PR comments --- .../components/rfid/hardware/generic_nfcpy/generic_nfcpy.py | 3 +-- .../components/rfid/hardware/generic_nfcpy/setup.inc.sh | 6 ++++-- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py b/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py index 9be37cf17..d12b049f4 100644 --- a/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py @@ -55,8 +55,7 @@ def query_customization() -> dict: print("\nChoose RFID device from USB device list:\n") logger.debug(f"USB devices: {[x['name'] for x in devices]}") if len(devices) == 0: - if len(devices) == 0: - logger.error("USB device list is empty. Make sure USB RFID reader is connected. Then re-run register_reader.py") + logger.error("USB device list is empty. Make sure USB RFID reader is connected. Then re-run register_reader.py") return {'device_path': None} for idx, dev in enumerate(devices): diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh b/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh index 7057c2ed4..7659fcf41 100755 --- a/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh @@ -1,5 +1,7 @@ #!/usr/bin/env bash +CURRENT_USER="${SUDO_USER:-$(whoami)}" + modprobe_file="/etc/modprobe.d/disable_driver_jukebox_nfcpy.conf" @@ -40,5 +42,5 @@ done sudo udevadm control --reload-rules sudo udevadm trigger -sudo gpasswd -a pi dialout -sudo gpasswd -a pi tty \ No newline at end of file +sudo gpasswd -a $CURRENT_USER dialout +sudo gpasswd -a $CURRENT_USER tty \ No newline at end of file From 30c38ce2b1fc3f64d323e5e043197567182d70d0 Mon Sep 17 00:00:00 2001 From: Stefan Krulj Date: Thu, 1 Feb 2024 01:50:36 +0100 Subject: [PATCH 6/7] Fix PR comments --- .../rfid/hardware/generic_nfcpy/generic_nfcpy.py | 8 ++++++-- .../rfid/hardware/generic_nfcpy/setup.inc.sh | 10 ++++++++-- 2 files changed, 14 insertions(+), 4 deletions(-) diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py b/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py index d12b049f4..99d425229 100644 --- a/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py @@ -22,6 +22,10 @@ def query_customization() -> dict: + # filter all log records from nfc.clf + logger = logging.getLogger('nfc.clf') + logger.filter = lambda record: 0 + possible_device_ids = [ "usb:054c:02e1", "usb:054c:06c1", @@ -45,7 +49,7 @@ def query_customization() -> dict: # find tty device matching_files = glob.glob("/dev/ttyUSB[0-9]*") - matching_files += glob.glob("/dev/ttyACM[0-9]*") + matching_files += glob.glob("/dev/ttyAMA[0-9]*") for file_path in matching_files: for device_id in (f'{file_path}:pn532', f'{file_path}:arygon'): if clf.open(device_id): @@ -55,7 +59,7 @@ def query_customization() -> dict: print("\nChoose RFID device from USB device list:\n") logger.debug(f"USB devices: {[x['name'] for x in devices]}") if len(devices) == 0: - logger.error("USB device list is empty. Make sure USB RFID reader is connected. Then re-run register_reader.py") + logger.error("USB device list is empty. Make sure USB RFID reader is connected. Then re-run reader registration") return {'device_path': None} for idx, dev in enumerate(devices): diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh b/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh index 7659fcf41..eaf2f3d33 100755 --- a/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh @@ -4,7 +4,9 @@ CURRENT_USER="${SUDO_USER:-$(whoami)}" modprobe_file="/etc/modprobe.d/disable_driver_jukebox_nfcpy.conf" - +if [ -e "$modprobe_file" ]; then + sudo rm -f "$modprobe_file" +fi if lsmod | grep "pn533_usb"; then sudo rmmod pn533_usb 2>/dev/null sudo sh -c "echo 'install pn533_usb /bin/true' >> $modprobe_file" @@ -31,16 +33,20 @@ valid_device_ids=( "04e6:5593" ) +if [ -e "$udev_file" ]; then + sudo rm -f "$udev_file" +fi for dev in $usb_devices; do if echo ${valid_device_ids[@]} | grep -woq $dev; then #$dev is in valid id array VID="${dev%%:*}" PID="${dev#*:}" - sudo sh -c "echo 'SUBSYSTEM==\"usb\", ATTRS{idVendor}==\"$VID\", ATTRS{idProduct}==\"$PID\", MODE=\"0666\"' >> $udev_file" + sudo sh -c "echo 'SUBSYSTEM==\"usb\", ATTRS{idVendor}==\"$VID\", ATTRS{idProduct}==\"$PID\", GROUP=\"plugdev\"' >> $udev_file" fi done sudo udevadm control --reload-rules sudo udevadm trigger +sudo gpasswd -a $CURRENT_USER plugdev sudo gpasswd -a $CURRENT_USER dialout sudo gpasswd -a $CURRENT_USER tty \ No newline at end of file From b730739a65a06c7660cb07610271bfce63bfaff4 Mon Sep 17 00:00:00 2001 From: Stefan Krulj Date: Sat, 3 Feb 2024 19:14:23 +0100 Subject: [PATCH 7/7] Fix PR comments --- .../hardware/generic_nfcpy/generic_nfcpy.py | 26 +++++++------------ .../rfid/hardware/generic_nfcpy/setup.inc.sh | 14 ++-------- 2 files changed, 12 insertions(+), 28 deletions(-) diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py b/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py index 99d425229..4b6ac0051 100644 --- a/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/generic_nfcpy.py @@ -4,6 +4,7 @@ import nfc import glob from nfc.clf import RemoteTarget +import nfc.clf.device # Import the ReaderBaseClass for common API. Leave as this line as it is! from components.rfid import ReaderBaseClass @@ -23,26 +24,15 @@ def query_customization() -> dict: # filter all log records from nfc.clf - logger = logging.getLogger('nfc.clf') - logger.filter = lambda record: 0 - - possible_device_ids = [ - "usb:054c:02e1", - "usb:054c:06c1", - "usb:054c:06c3", - "usb:054c:0193", - "usb:04cc:0531", - "usb:072f:2200", - "usb:04e6:5591", - "usb:04e6:5593", - "usb:04cc:2533", - ] + loggerNfcClf = logging.getLogger('nfc.clf') + loggerNfcClf.filter = lambda record: 0 devices = [] clf = nfc.ContactlessFrontend() # find usb devices - for device_id in possible_device_ids: + for vid_pid_pair in nfc.clf.device.usb_device_map.keys(): + device_id = "usb:%04x:%04x" % vid_pid_pair if clf.open(device_id): devices.append({'id': device_id, 'vendor': clf.device.vendor_name, 'name': clf.device.product_name}) clf.close() @@ -51,7 +41,8 @@ def query_customization() -> dict: matching_files = glob.glob("/dev/ttyUSB[0-9]*") matching_files += glob.glob("/dev/ttyAMA[0-9]*") for file_path in matching_files: - for device_id in (f'{file_path}:pn532', f'{file_path}:arygon'): + for driver in nfc.clf.device.tty_driver_list: + device_id = f'{file_path}:{driver}' if clf.open(device_id): devices.append({'id': device_id, 'vendor': clf.device.vendor_name, 'name': clf.device.product_name}) clf.close() @@ -87,6 +78,9 @@ def __init__(self, reader_cfg_key): with cfg: # Get a reference to the actual reader-specific config config = cfg.getn('rfid', 'readers', reader_cfg_key, 'config', default=None) + if config is None: + self._logger.error("Configuration may not be empty!!") + raise KeyError("configuration may not be empty!!") device_path = config.setdefault('device_path', None) self.clf = nfc.ContactlessFrontend() diff --git a/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh b/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh index eaf2f3d33..d831b3de9 100755 --- a/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh +++ b/src/jukebox/components/rfid/hardware/generic_nfcpy/setup.inc.sh @@ -14,24 +14,14 @@ fi if lsmod | grep "port100"; then sudo rmmod port100 2>/dev/null - sudo sh -c "echo 'install v /bin/true' >> $modprobe_file" + sudo sh -c "echo 'install port100 /bin/true' >> $modprobe_file" fi udev_file="/etc/udev/rules.d/50-usb-nfc-rule.rules" usb_devices=$(lsusb | sed -e 's/.*ID \([a-f0-9]\+:[a-f0-9]\+\).*/\1/g') -valid_device_ids=( - "054c:02e1" - "054c:06c1" - "054c:06c3" - "054c:0193" - "04cc:0531" - "04cc:2533" - "072f:2200" - "04e6:5591" - "04e6:5593" -) +valid_device_ids=($(python -c "import nfc.clf.device; [print('%04x:%04x' % x) for x in nfc.clf.device.usb_device_map.keys()]")) if [ -e "$udev_file" ]; then sudo rm -f "$udev_file"