2 Author: Mitchell Pomery (bobgeorge33)
4 System to connect to OpenDispense2.
5 Most of this code has been copied out of VendServer.py, then had variables updated so that it runs.
6 This is so VendServer can easily operate regardless of the current accounting backend.
7 Documentation for this code can be found inder Dispence.DispenceInterface
10 from DispenseInterface import DispenseInterface
14 from subprocess import Popen, PIPE
15 from LDAPConnector import get_uid,get_uname, set_card_id
17 class OpenDispense(DispenseInterface):
23 def __init__(self, username=None, secret=False):
26 def authUserIdPin(self, userId, pin):
29 info = pwd.getpwuid(userId)
31 logging.info('getting pin for uid %d: user not in password file'%userId)
34 if info.pw_dir == None: return False
35 pinfile = os.path.join(info.pw_dir, '.pin')
39 logging.info('getting pin for uid %d: .pin not found in home directory'%userId)
42 logging.info('getting pin for uid %d: .pin has wrong permissions. Fixing.'%userId)
43 os.chmod(pinfile, 0600)
47 logging.info('getting pin for uid %d: I cannot read pin file'%userId)
49 pinstr = f.readline().strip()
51 if not re.search('^[0-9]{4}$', pinstr):
52 logging.info('getting pin for uid %d: %s not a good pin'%(userId,repr(pinstr)))
55 if pinstr == str(pin):
59 self._disabled = False
60 self._username = info.pw_name
66 def authMifareCard(self, cardId):
68 self._userid = get_uid(cardId)
70 # Check for thier username
73 info = pwd.getpwuid(userId)
75 logging.info('getting pin for uid %d: user not in password file'%uid)
78 # If we get this far all is good
80 self._disabled = False
81 self._username = info.pw_name
84 def addCard(self, cardId):
86 set_card_id(self._userId, cardId)
92 def getUsername(self):
98 acct, unused = Popen(['dispense', 'acct', self._username], close_fds=True, stdout=PIPE).communicate()
101 balance = acct[acct.find("$")+1:acct.find("(")].strip()
104 def getItemInfo(self, itemId):
105 itemId = OpenDispenseMapping.vendingMachineToOpenDispense(itemId)
106 args = ('dispense', 'iteminfo', itemId)
107 info, unused = Popen(args, close_fds=True, stdout=PIPE).communicate()
108 m = re.match("\s*[a-z]+:\d+\s+(\d+)\.(\d\d)\s+([^\n]+)", info)
111 cents = int(m.group(1))*100 + int(m.group(2))
112 # return (name, price in cents)
113 return (m.group(3), cents)
115 def isDisabled(self):
116 return self._disabled
118 def dispenseItem(self, itemId):
119 if not self.isLoggedIn() or self.getItemInfo(itemId)[0] == "dead":
122 print('dispense -u "%s" %s'%(self._username, itemId))
123 #os.system('dispense -u "%s" %s'%(self._username, itemId))
128 self._disabled = True
129 self._loggedIn = False
133 This class abstracts the idea of item numbers.
134 It removes the need for VendServer to know the mappings between inputted numbers
135 and the equivalent itemId in OpenDispense.
137 class OpenDispenseMapping():
140 def vendingMachineToOpenDispense(itemId):
141 _mappingFile = "OpenDispenseMappings.conf"
142 fh = open(_mappingFile)
146 if line.startswith(str(itemId) + " "):
147 map = line[len(str(itemId)) + 1:].strip()