Einbindung eines Fingerabdrucklesers des Typs ZFM-20 (auch bekannt als "Arduino fingerprint sensor") zur Öffnung der Türe

    This site uses cookies. By continuing to browse this site, you are agreeing to our Cookie Policy.

    Da in jedem Forum ein paar Regeln eingehalten werden müssen, möchte ich diese auch vorher hier festlegen und niederschreiben. Die grundsätzliche Netiquette setze ich bei Jedem voraus. Darüber hinaus möchte ich nur spezielle Regeln ansprechen:
    - Unterlasse FullQuote sondern nutze Alternativen wie Inline-Quoting
    -> siehe auch https://de.wikipedia.org/wiki/Fullquote vs. https://de.wikipedia.org/wiki/TOFU#Alternativen_zu_TOFU
    - Unterlasse nichtssagende Antworten wie "Danke" oder "werde ich mal testen" oder ähnliches, sofern Du nicht der Threadersteller bist und einen Lösungsvorschlag angeboten bekommen hast.
    - Vermeide Doppel-Posts (zwei Beiträge von Dir hintereinander) sondern editiere wenn möglich Deine Posts.

    Danke...

    • Einbindung eines Fingerabdrucklesers des Typs ZFM-20 (auch bekannt als "Arduino fingerprint sensor") zur Öffnung der Türe

      Ich habe meinen Fingarabdruckleser des Typs ZFM-20 (auch bekannt als "Arduino fingerprint sensor") an mein DoorPi geklemmt. da es dafür (noch) kein Keyboard gibt, habe ich mir das "virtuelle Keyboard" zu Nutze gemacht um die Freigabe des Fingerabdrucklesers zu implementieren.

      Was es Braucht:
      • Funktionierendes DoorPi, vorkonfiguriert auf Raspberry Pi B+ oder 3 (bei mir ist der 3-er im Einsatz)
      • Fingerabdruckleser des Typs ZFM-20 (ebay, AliExpress...)
      • USB-TTL-Konverter (z.B. mit dem CP2102-Chip) oder einen Arduino Nano mit gebrücktem GND-Rst, so kann dieser als USB-TTL fungieren.
      • wahlweise zwei LED's (grün / rot oder Dual-LED)
      • Kabel, Lötkolben, Widerstände...


      Vorbereitung der Hardware:
      • Fingerabdruckleser in entsprechend sinnvolles Gehäuse packen
      • Ich habe für die initialisierung des Lesevorganges einen Taster auf das Gehäuse gepackt. (zukünftig will ich den Leser anderweitig einbauen und die Auslösung dann über eine Lichtschranke realisieren.)
      • ebenfalls fanden die beiden LED's darauf platz (diese signalisieren den Lesvorgang erfolgreich / fehlerhaft)
      • PiFace Board ist von Vorteil, würde aber auch über GPIO mit entsprechenden Widerständen und Relais-Board funktionieren (war mir aber zu Umständlich)
      • Wie man den Fingerabdruckleser genau anschliesst und wie die Library dafür installiert wird, könnt ihr Bastian Raschke's Webseite entnehmen, da spare ich mir das Wiederkäuen.
      • Anschliessend Fingerleser gemäss Bastian's Anleitung testen.



      Vorbereitung der Software:
      • Die Python-Library für den Fingerabdruckleser hat ebenfalls einige Beispiele mitgeliefert:
      • Mit dem Beispiel "example_enroll.py" können die Finger entsprechend eingelesen werden
      • Das "example_search.py" habe ich entsprechend erweitert, damit das erfolgreiche Lesen eine Aktion in DoorPi auslöst
      • Ich habe das Script abgeändert und in "finger.py" umbenannt. Anschliessend habe ich es unter "/usr/local/etc/DoorPi/scripts/" abgelegt (ausführbar machen nicht vergessen, aber das wisst ihr sicher)
      Der CODE muss an diversen Stellen noch am jeweiligen System angepasst werden. Dies habe ich im Code kommentiert:

      Source Code: finger.py

      1. #!/usr/bin/env python
      2. # -*- coding: utf-8 -*-
      3. """
      4. PyFingerprint
      5. Copyright (C) 2015 Bastian Raschke <bastian.raschke@posteo.de>
      6. All rights reserved.
      7. @author: Bastian Raschke <bastian.raschke@posteo.de>
      8. @revisioned <a class="call-via-3cx" href="tcxcallto:<a class="call-via-3cx" href="tcxcallto:@@d4ffc86dab09cac3b0cbbcfc2e5754df5bb22408@@">@@f9d961a1a1ba22838b65711c4f1821adbec56d8d@@</a>"><a class="call-via-3cx" href="tcxcallto:@@7217a3d48f1797541b968b41592726ff789cdeeb@@">@@ac11236649dd470c2d5a270220fd828c0d893682@@</a></a> by Sven Gächter (sven@familiegaechter.ch) to interact with DoorPi to unlock Doors
      9. """
      10. import hashlib
      11. from pyfingerprint.pyfingerprint import PyFingerprint
      12. import time , requests
      13. import os
      14. os.environ['http_proxy']=''
      15. import urllib2
      16. #Timeout for Reader unread
      17. t_end = time.time() + 10
      18. #print(time.time())
      19. #print(t_end)
      20. ## Search for a finger
      21. ## Tries to initialize the sensor
      22. try:
      23. f = PyFingerprint('/dev/ttyUSB0', 57600, 0xFFFFFFFF, 0x00000000)
      24. if ( f.verifyPassword() == False ):
      25. raise ValueError('The given fingerprint sensor password is wrong!')
      26. except Exception as e:
      27. print('The fingerprint sensor could not be initialized!')
      28. print('Exception message: ' + str(e))
      29. exit(1)
      30. ## Gets some sensor information
      31. print('Currently stored templates: ' + str(f.getTemplateCount()))
      32. ## Tries to search the finger and calculate hash
      33. try:
      34. print('Waiting for finger...')
      35. ## Wait that finger is read
      36. while time.time() < t_end and ( f.readImage() == False ):
      37. pass
      38. ## Converts read image to characteristics and stores it in charbuffer 1
      39. f.convertImage(0x01)
      40. ## Searchs template
      41. result = f.searchTemplate()
      42. positionNumber = result[0]
      43. accuracyScore = result[1]
      44. if ( positionNumber == -1 ):
      45. print('No match found!')
      46. # Transaction to DoorPi: No Finger listed or too long- Timeout. // Please modify URL below with your credentials e.g: http://door:pi@doorpi:8080
      47. r = requests.get('http://username:password@doorpi-url:port/control/trigger_event?event_name=OnKeyPressed_webservice.redled&event_source=doorpi.keyboard.from_filesystem')
      48. r.json()
      49. exit(0)
      50. else:
      51. print('Found template at position #' + str(positionNumber))
      52. print('The accuracy score is: ' + str(accuracyScore))
      53. # Transaction to DoorPi: Door Release OK. // Please modify URL below with your credentials e.g: http://door:pi@doorpi:8080
      54. r = requests.get('http://username:password@doorpi-url:port/control/trigger_event?event_name=OnKeyPressed_webservice.dooropen&event_source=doorpi.keyboard.from_filesystem')
      55. r.json()
      56. ## OPTIONAL stuff to secure the Transaction (future revisions)
      57. ##
      58. ## Loads the found template to charbuffer 1
      59. f.loadTemplate(positionNumber, 0x01)
      60. ## Downloads the characteristics of template loaded in charbuffer 1
      61. characterics = str(f.downloadCharacteristics(0x01))
      62. ## Hashes characteristics of template
      63. print('SHA-2 hash of template: ' + hashlib.sha256(characterics).hexdigest())
      64. except Exception as e:
      65. print('Operation failed!')
      66. print('Exception message: ' + str(e))
      67. exit(1)
      Display All

      Damit die Events von DoorPi verarbeitet werden können habe ich das "virtuelle Keyboard" aktiviert und mir folgende virtuelle Inputs erstellt (Kommentare mit "//" bitte bei allen folgenden Code's rauslöschen):

      Source Code: doorpi.ini

      1. [keyboards]
      2. onboardpins = piface
      3. webservice = filesystem
      4. [onboardpins_InputPins]
      5. 0 = call:11 // 1 und 2 sind die Türglocken
      6. 1 = call:12
      7. 3 = sleep:0 // Taster für den Start des Lesevorganges
      8. 4 = sleep:0 // Sabotagekontakt
      9. [onboardpins_OutputPins]
      10. 0 = Tueroeffner // Hier hängt der öffner
      11. 5 = greenled // Wie der Name schon sagt..
      12. 6 = redled // Dito.
      13. [webservice_InputPins] // Virtuele Inputs für die Anbindung des Fingerlesers (ohne weitere Funktion)
      14. dooropen = sleep:0
      15. redled = sleep:0
      16. [webservice_keyboard]
      17. base_path_input = /var/DoorPI/keyboard/inputs/
      18. base_path_output = /var/DoorPI/keyboard/outputs/
      19. bouncetime = 2000
      20. polarity = 0
      21. pressed_on_keydown = True
      22. reset_input = True
      Display All

      Die virtuellen Inputs lösen die folgenden Events aus:



      Source Code: doorpi.ini

      1. [EVENT_OnKeyPressed_onboardpins.3]
      2. 10 = os_execute:/usr/local/etc/DoorPi/scripts/finger.py
      3. [EVENT_OnKeyPressed_onboardpins.4]
      4. 10 = os_execute:/usr/local/etc/DoorPi/scripts/sabotage.sh
      5. 11 = break
      6. [EVENT_OnKeyPressed_webservice.dooropen]
      7. 10 = out:Tueroeffner,1,0,3
      8. 20 = out:greenled,1,0,3
      9. [EVENT_OnKeyPressed_webservice.redled]
      10. 10 = out:redled,1,0,1
      11. 15 = sleep:1
      12. 20 = out:redled,1,0,1
      Display All
      EVENT_OnKeyPressed_onboardpins.3:
      • Dieser Event wird vom Input 3 getriggert. Hier hängt der Taster zum starten des Fingerlesevorgangs dran


      EVENT_OnKeyPressed_onboardpins.4
      • Minimale Sicherheit: Wenn jemand das Lesergehäuse vor der Haustür öffnet, werde ich über das Script "sabotage.sh" via Telegram informiert, anschliessend stoppt DoorPi und nichts geht mehr (Vorsicht, In diesem Fall braucht's noch einen Schlüssel oder einen ssh-Zugang auf die DoorPi um neu zu starten).


      EVENT_OnKeyPressed_webservice.dooropen:
      • Dieser Event wird von "finger.py" angestossen, wenn der Lesevorgang erfolgreich war
      • Zugleich wird die grüne LED für 3s. eingeschaltet (zeigt den erfolgreichen Lesevorgang an)


      EVENT_OnKeyPressed_webservice.redled:
      • Dieser Event schaltet die rote LED, wenn der Lesevorgang zu lange kein Ergebnis bringt (der Vorgang bricht nach 10s ab), oder der vorgehaltene Finger nicht verzeichnet ist.


      Wenn dann alles aufgebaut ist, kann mittels Knopfdruck der Lesevorgang gestartet werden: Ist der Finger korrekt, wird die Türe freigegeben.


      Das System hat noch einige leaks, so sind teilweise Wartezeiten zwischen Knopfdruck und Lesevorgang (der Leser wird zuerst initialisiert) sowie nach Abschluss des Lesevorgangs bis zum öffnen der Tür in Kauf zu nehmen.
      • Das hat mit dem Verarbeiten der Events zu tun. Je nach dem was DoorPi sonst noch treibt, geht's schneller.
      • Dieser Tatsache könnte mit einem DoorPi-Keyboard sicher abgeholfen werden - Leider reichen meine Python-Kenntnisse dafür (noch) nicht aus


      Zum Thema Sicherheit ist vorweg zu nehmen, dies ist ein Experimental aufbau! Bitte nicht bei der nächsten Sparkasse verbauen :)
      • Tauscht jemand den Leser mit einem baugleichen Modell mit vorgespeicherten Fingern, kann die Tür problemlos geöffnet werden. Deshalb habe ich den Sabotagekontakt vorgesehen.
      • Hier würde das Speichern und Abgleichen des Hash's, welcher die Library anbietet, entgegenwirken. Da hänge ich mich dann mal dran.


      Kritik und Verbesserungsvorschläge sind willkommen. :)
      Files
      • finger.zip

        (1.36 kB, downloaded 109 times, last: )
    • Einbindung eines Fingerabdrucklesers des Typs ZFM-20 (auch bekannt als "Arduino fingerprint sensor") zur Öffnung der Türe

      Hi,
      dein Projekt klingt interessant. Hast du schon weitere Fortschritte machen können?
      Ich überlege mir damit meine Garagentür öffnen zu lassen. Eine Codeeingabe finde ich hierfür zu aufwendig, wenn jedesmal die Türe zufliegt