EmlaLockBox - The Code
Posted: 03 May 2016, 17:15
In the DIY forum I posted on the EmlaLockBox I had created and offered to post the code. Sorry its taken a while - issues with having the right computer in the correct country!
Naturally you use it at your own risk and don't come crying to me if it goes horribly wrong and you can't get your keys back!
I'm not a native python developer, so you can probably suggest a hundred ways it could be improved!
Naturally you use it at your own risk and don't come crying to me if it goes horribly wrong and you can't get your keys back!
Code: Select all
#Import the modules
import requests
import json
import sys
import time
import Adafruit_CharLCD as LCD
from Adafruit_PWM_Servo_Driver import PWM
def setServoPulse(channel, pulse):
pulseLength = 1000000 # 1,000,000 us per second
pulseLength /= 60 # 60 Hz
print "%d us per period" % pulseLength
pulseLength /= 4096 # 12 bits of resolution
print "%d us per bit" % pulseLength
pulse *= 1000
pulse /= pulseLength
pwm.setPWM(channel, 0, pulse)
def lock(combination):
global servoMax
global pwm
pwm.setPWM(0, 0, servoMax)
print("Click "+str(combination))
return True;
def unlock(combination):
global servoMin
global pwm
pwm.setPWM(0, 0, servoMin)
print("Clack "+str(combination))
return True;
def random():
value=123456
return value
def handleResult(t):
global status
global startDate
global elError
data = json.loads(t)
print(data)
try:
status=data['ERR']
print ('Error: ', status)
elError=status
return False
except KeyError:
status="not an error"
try:
status = data['INFO']
return True
except KeyError:
status="No Info"
try:
status = data['sessionactive']
except KeyError:
status="No Info"
elError=""
return True
def currentTime():
t = requests.get("http://www.timeapi.org/utc/now")
return t.text
#########################################################
# Routines that handle communication with EMLALOCK.COM
#########################################################
def info():
global userid
global apikey
global device
r = requests.get("https://www.emlalock.com?client=api&userid="+str(userid)+"&apikey="+str(apikey)+"&job=info")
r.text
if handleResult(r.text):
return True
else:
return False
def checkDevice():
global userid
global apikey
global device
r = requests.get("https://www.emlalock.com?client=api&userid="+str(userid)+"&apikey="+str(apikey)+"&job=checkUserDevice&deviceid="+str(device))
r.text
print(r.text)
if handleResult(r.text):
return True
else:
return False
def registerDevice():
global userid
global apikey
global device
r = requests.get("https://www.emlalock.com?client=api&userid="+str(userid)+"&apikey="+str(apikey)+"&job=activateDeviceID&deviceid="+str(device)+"&session=1&description=Auto Lock Box&cleaning=1")
r.text
if handleResult(r.text):
return True
else:
return False
def startSession():
global userid
global apikey
global device
combination=random()
r = requests.get("https://www.emlalock.com?client=api&userid="+str(userid)+"&apikey="+str(apikey)+"&job=activateDeviceSession&deviceid="+str(device)+"&combination="+str(combination))
r.text
if handleResult(r.text):
lock(combination)
return True
else:
return False
def endSession():
global userid
global apikey
r = requests.get("https://www.emlalock.com?client=api&userid="+str(userid)+"&apikey="+str(apikey)+"&job=endDeviceSession")
r.text
if handleResult(r.text):
data = json.loads(r.text)
unlock(data['CODE'])
return True
else:
return False
def emergency(pw):
global userid
global apikey
r = requests.get("https://www.emlalock.com?client=api&userid="+str(userid)+"&apikey="+str(apikey)+"&job=emergencyEndDeviceSession&keyword="+str(pw)+"&failed=FAILED")
r.text
if handleResult(r.text):
data = json.loads(r.text)
unlock(data['CODE'])
return True
else:
return False
def startHygiene():
global userid
global apikey
r = requests.get("https://www.emlalock.com?client=api&userid="+str(userid)+"&apikey="+str(apikey)+"&job=startDeviceHygieneopening")
r.text
if handleResult(r.text):
data = json.loads(r.text)
unlock(data['CODE'])
return True
else:
return False
def endHygiene():
global userid
global apikey
global device
combination=random()
r = requests.get("https://www.emlalock.com?client=api&userid="+str(userid)+"&apikey="+str(apikey)+"&job=endDeviceHygieneopening&deviceid="+str(device)+"&combination="+str(combination))
r.text
if handleResult(r.text):
lock(combination)
return True
else:
return False
###############################################################
# Routines that handle the menus and options
###############################################################
def waitForStart():
global message
global commands
global elError
commands=['Start','Settings']
if len(elError)>0:
message[0]=elError
else:
message[0]='Select to Start'
lcd.set_color(0.0, 0.0, 1.0) # Blue
option=waitForSelect()
if option==0:
if startSession():
return 1 #1 = sessionRunning
if option==1:
return 4
return 0
def sessionRunning():
global message
global commands
global elError
commands=['Initiate Hygiene','End Session','Emergency Quit']
if len(elError)>0:
message[0]=elError
else:
message[0]='Session Running'
lcd.set_color(0.0, 1.0, 0.0) # Green
option=waitForSelect()
if option==0:
if startHygiene():
return 2 # 2 = Hygiene Session
if option==1:
if endSession():
return 3 # 0 = wait for session
if option==2:
if emergency('HELP'):
return 3 # 0 = wait for session
return 1
def hygieneSession():
global message
global commands
global elError
commands=['End Cleaning','End Session','Emergency Quit']
if len(elError)>0:
message[0]=elError
else:
message[0]='Hygiene Running'
lcd.set_color(1.0, 1.0, 0.0) # Yellow
option=waitForSelect()
if option==0:
if endHygiene():
return 1 # 1 = sessionRunningn
if option==1:
if endSession():
return 3 # 0 = wait for session
if option==2:
if emergency('HELP'):
return 3 # 0 = wait for session
return 2
def noSession():
global message
global commands
global elError
commands=['Check for session','Settings']
if len(elError)>0:
message[0]=elError
else:
message[0]='No session available'
lcd.set_color(1.0, 0.0, 0.0) # Red
option=waitForSelect()
if option==0:
if info():
if status==True:
return 1 # Active session exists: sessionRunning
else:
return 0 # Session exists but not active: waitForSession
if option==1:
return 4 # Go to the settings menu
return 3 # Still no session - stay in this mode
def settings():
global message
global commands
global elError
commands=['Set servo lock','Set servo unlock','Quit settings']
if len(elError)>0:
message[0]=elError
else:
message[0]='Settings'
lcd.set_color(1.0, 1.0, 1.0) # White
option=waitForSelect()
if option==0:
return 5 # 5 = Set servo lock position
if option==1:
return 6 # 6 = Set servo unlock position
if option==2:
if info():
if status==True:
return 1 # Active session exists: sessionRunning
else:
return 0 # Session exists but not active: waitForSession
return 3
return 4
def waitForSelect():
buttons=(LCD.SELECT,LCD.UP,LCD.DOWN)
currentOption=0
global message
global commands
message[1]=commands[currentOption]
lcd.clear()
lcd.message(message[0]+"\n"+commands[currentOption])
while not lcd.is_pressed(buttons[0]):
if lcd.is_pressed(buttons[1]):
if currentOption==0:
currentOption=len(commands)-1
else:
currentOption-=1
print('currentOption=',currentOption)
message[1]=commands[currentOption]
lcd.clear()
lcd.message(message[0]+"\n"+message[1])
if lcd.is_pressed(buttons[2]):
currentOption+=1
if currentOption==len(commands):
currentOption=0
print('currentOption=',currentOption)
message[1]=commands[currentOption]
lcd.clear()
lcd.message(message[0]+"\n"+message[1])
return currentOption
def setServoLock():
print("servo lock")
global servoMax
buttons=(LCD.SELECT,LCD.LEFT,LCD.RIGHT)
value=servoMax
lcd.clear()
lcd.message('Set Servo Lock\nServo (150:600) '+str(value))
while not lcd.is_pressed(buttons[0]):
if lcd.is_pressed(buttons[1]):
if value>10:
value-=10
lcd.clear()
lcd.message('Set Servo Lock\nServo (150:600) '+str(value))
# Do something with the servo
pwm.setPWM(0, 0, value)
if lcd.is_pressed(buttons[2]):
if value<590:
value+=10
lcd.clear()
lcd.message('Set Servo Lock\nServo (150:600) '+str(value))
# Do something with the servo
pwm.setPWM(0, 0, value)
# Store value
servoMax=value
print("Servo unlock value ",str(servoMax))
return 4
def setServoUnlock():
print("Servo unlock")
global servoMin
buttons=(LCD.SELECT,LCD.LEFT,LCD.RIGHT)
value=servoMin
lcd.clear()
lcd.message('Set Servo Unlock\nServo (150:600) '+str(value))
while not lcd.is_pressed(buttons[0]):
if lcd.is_pressed(buttons[1]):
if value>0:
value-=10
lcd.clear()
lcd.message('Set Servo Lock\nServo (150:600) '+str(value))
# Do something with the servo
pwm.setPWM(0, 0, value)
if lcd.is_pressed(buttons[2]):
if value<590:
value+=10
lcd.clear()
lcd.message('Set Servo Lock\nServo (150:600) '+str(value))
# Do something with the servo
pwm.setPWM(0, 0, value)
# Store value
servoMin=value
print("Servo unlock value ",str(servoMin))
return 4
# initialise global variables
userid=""
apikey=""
device=""
status=""
message=['message','option']
elError=""
servoMax=600
servoMin=150
lcd = LCD.Adafruit_CharLCDPlate()
pwm = PWM(0x40)
pwm.setPWMFreq(60)
commands=('a','b')
# get the command line args
x=1 #ignore zero entry as it will be the program file
while x<len(sys.argv):
a=str(sys.argv[x])
print('arg=',a)
if a[:6]=='userid':
userid=a[7:]
if a[:6]=='apikey':
apikey=a[7:]
if a[:6]=='device':
device=a[7:]
if a[:8]=='servoMax':
servoMax=int(a[9:])
if a[:8]=='servoMin':
servoMin=int(a[9:])
x=x+1
#Check if the device is registered and if not register it
mustRegister=True
if checkDevice():
for cDevice in status:
if cDevice==device:
mustRegister=False
if mustRegister:
registerDevice()
# Check is a session is already running
if info():
print(status)
if status==True:
command=1
else:
command=0
else:
command=3
while True:
if command==0:
command=waitForStart()
if command==1:
command=sessionRunning()
if command==2:
command=hygieneSession()
if command==3:
command=noSession()
if command==4:
command=settings()
if command==5:
command=setServoLock()
if command==6:
command=setServoUnlock()