diff --git a/AATC_Client_Text_UI.py b/AATC_Client_Text_UI.py index 165f260..de8a284 100644 --- a/AATC_Client_Text_UI.py +++ b/AATC_Client_Text_UI.py @@ -361,17 +361,14 @@ def GetMonitorPermissionUser(self): ################################################# def Call_Exit(self): - Choice = input("Exit? (Y/N) >>").upper() - if Choice == "Y": - print("Exiting..") - try: - Sucess,Message = self.UserInterface.Exit() - self.DisplayResults(Sucess,Message) - except: - print("Unable to close server connection") - self.Exit = True - else: - print("Exit cancelled") + print("Exiting..") + try: + Sucess,Message = self.UserInterface.Exit() + self.DisplayResults(Sucess,Message) + except: + print("Unable to close server connection") + self.Exit = True + @@ -386,7 +383,13 @@ def Call_Exit(self): TextUI = UserTextUI(U,MenuOptions) TextUI.Main_Loop() - Exit = True #When user selects exit + + Choice = input("Exit? (Y/N) >>").upper() + if Choice == "Y": + print("Exiting") + Exit = True #When user selects exit + else: + print("Exit cancelled") except Exception as e: print("Error occured creating user interface",e) diff --git a/AATC_Config.py b/AATC_Config.py index 0b7764c..d6230f7 100644 --- a/AATC_Config.py +++ b/AATC_Config.py @@ -29,4 +29,5 @@ DRONE_BATTERY_DRAIN_MULT = 1 + NOFLYZONE_THRESHOLD_COST = 50 diff --git a/AATC_Crypto.py b/AATC_Crypto.py index 5933aa4..30c3cd5 100644 --- a/AATC_Crypto.py +++ b/AATC_Crypto.py @@ -120,6 +120,7 @@ def ServerGenerateKey(self): data = self.Recv() Command, Arguments = data[0],data[1] + if Command == "GenerateKey": Sucess,Message,Data = self.ServerGenerateKeys(Arguments) @@ -128,6 +129,7 @@ def ServerGenerateKey(self): elif Command == "SetKey": Sucess,Message,Data = self.ServerSetKey(Arguments) + elif Command == "Exit": diff --git a/AATC_DB.py b/AATC_DB.py index d183c97..82f7025 100644 --- a/AATC_DB.py +++ b/AATC_DB.py @@ -183,7 +183,7 @@ def GetFlightsAll(self): def AddFlight(self,UserID,DroneID,StartCoords,EndCoords,StartTime,ETA,EndTime,Distance,XOffset,YOffset,ZOffset): self.cur.execute("SELECT 1 FROM User,Drone WHERE Drone.DroneID = %s AND Drone.UserID = %s",(DroneID,UserID)) if self.cur.fetchall() !=(): - self.cur.execute("INSERT INTO Flight(DroneID,StartCoords,EndCoords,StartTime,ETA,EndTime,Distance,XOffset,YOffset,ZOffset,Completed) VALUES(%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,0)",(DroneID,str(StartCoords),str(EndCoords),StartTime,ETA,EndTime,Distance,XOffset,YOffset,ZOffset)) + self.cur.execute("INSERT INTO Flight(DroneID,StartCoords,EndCoords,StartTime,ETA,EndTime,Distance,XOffset,YOffset,ZOffset,Completed) VALUES(%s,%s,%s,%s,%s,%s,%s,%s,%s,%s,0)",(DroneID,str(StartCoords),str(EndCoords),int(StartTime),int(ETA),int(EndTime),Distance,XOffset,YOffset,ZOffset)) self.db_con.commit() return True,"Flight added" else: @@ -200,7 +200,7 @@ def RemoveFlight(self,UserID,FlightID): def CheckForFlight(self,DroneID,MaxLookAheadTime): InvalidateDelay = 1800 - self.cur.execute("SELECT FlightID FROM Flight WHERE DroneID = %s AND StartTime < (%s+%s) AND StartTime > (%s-%s) ORDER BY StartTime ASC LIMIT 1",(DroneID,GetTime(),MaxLookAheadTime, GetTime(),InvalidateDelay)) + self.cur.execute("SELECT FlightID FROM Flight WHERE DroneID = %s AND StartTime < (%s+%s) AND StartTime > (%s-%s) AND Completed = 0 ORDER BY StartTime ASC LIMIT 1",(DroneID,GetTime(),MaxLookAheadTime, GetTime(),InvalidateDelay)) FlightIDFetch = self.cur.fetchall() self.db_con.commit() if FlightIDFetch != (): @@ -227,11 +227,11 @@ def MarkFlightComplete(self,DroneID,FlightID,Code): return False,"You do not have permission to mark this flight complete" def GetCompletedFlightIDs(self,EndTimeThreshold): - self.cur.execute("SELECT FlightID FROM Flight WHERE Completed > 0 AND (EndTime + %s) > %s",(EndTimeThreshold,GetTime())) + self.cur.execute("SELECT FlightID FROM Flight WHERE (Completed > 0 AND (EndTime + %s) < %s) OR (EndTime+ %s) < %s",(EndTimeThreshold,GetTime(),EndTimeThreshold*3,GetTime())) return True,"['FlightID']",self.cur.fetchall() - def CleanCompletedFlights(self,EndTimeThreshold): - self.cur.execute("DELETE FROM Flight WHERE Completed > 0 AND (EndTime + %s) > %s",(EndTimeThreshold,GetTime())) + def CleanFlights(self,FlightIDList): + self.cur.executemany("DELETE FROM Flight WHERE FlightID = %s",FlightIDList) self.db_con.commit() return True,"Deleted completed flights above threshold" @@ -251,7 +251,7 @@ def GetFlightWaypointsAll(self): def AddWaypoint(self,UserID,FlightID,WaypointNumber,Coords,ETA,BlockTime=0): self.cur.execute("SELECT 1 FROM User,Flight,Drone WHERE User.UserID = %s AND User.UserID = Drone.UserID AND Drone.DroneID = Flight.DroneID AND Flight.FlightID = %s",(UserID,FlightID)) if self.cur.fetchall() !=(): - self.cur.execute("INSERT INTO FlightWaypoints(FlightID,WaypointNumber,Coords,ETA,BlockTime) VALUES(%s,%s,%s,%s,%s)",(FlightID,WaypointNumber,str(Coords),ETA,BlockTime)) + self.cur.execute("INSERT INTO FlightWaypoints(FlightID,WaypointNumber,Coords,ETA,BlockTime) VALUES(%s,%s,%s,%s,%s)",(FlightID,WaypointNumber,str(Coords),int(ETA),BlockTime)) self.db_con.commit() return True,"Added Waypoint" else: @@ -307,11 +307,12 @@ def GetMonitorFlightWaypoints(self,MonitorID): def GetMonitorID(self,MonitorName): self.cur.execute("SELECT MonitorID FROM Monitor WHERE MonitorName = %s",(MonitorName,)) - if len(self.cur.fetchall()) != 0: + result = self.cur.fetchall() + if len(result) != 0: Sucess = True else: Sucess = False - return Sucess,"['MonitorID']",self.cur.fetchall() + return Sucess,"['MonitorID']",result def GetMonitorName(self,MonitorID): self.cur.execute("SELECT MonitorName FROM Monitor WHERE MonitorID = %s",(MonitorID,)) return True,"['MonitorName']",self.cur.fetchall() diff --git a/AATC_Server_002.py b/AATC_Server_002.py index c42a1e3..c39f063 100644 --- a/AATC_Server_002.py +++ b/AATC_Server_002.py @@ -1,5 +1,5 @@ import codecs,ast,socket,recvall,os,math,random,time,pickle -import AATC_AStar,AATC_DB, AATC_Crypto +import AATC_AStar,AATC_DB, AATC_Crypto,AATC_Config from AATC_Coordinate import * def GetTime(): @@ -18,69 +18,76 @@ def CoordLessThanOrEqual(Coord1,Coord2):# True if Coord1 <= Coord2 - - - -class UserConnection: +class ClientConnection: + """This is the base class for Connections, all other connection objects will inherit from this object. + Will contain all similar components i.e. send, receive + + """ def __init__(self,Thread_Name,Thread_Queue,Connection): self.DB = AATC_DB.DBConnection() self.Thread_Name = Thread_Name self.Thread_Queue = Thread_Queue self.con = Connection self.Crypto = AATC_Crypto.Crypter(self.con, mode = "SERVER" ) - self.UserID = -1 #Used to identify if has logged in yet - self.NOFLYZONE_THRESHOLD_COST = 50 - def Send(self,data): - self.con.sendall(self.Crypto.Encrypt(codecs.encode(str(data)))) - def Recv(self): - try: - data = self.Crypto.Decrypt(recvall.recvall(self.con)) - data = ast.literal_eval(codecs.decode(data)) - # (Command,Arguments) - return data - #return data[0],data[1],data[2] - except Exception as e: - print("UserID:",self.UserID," Socket data recive error",e) - data = ("",())#Never references a command + self.ClientID = -1 #Used to identify if has logged in yet def Connection_Loop(self): """ - Keeps looping in request for user, + Keeps looping in request for Client, Recived data in format (CommandString,(Arg1,Arg2...)) Calls function in format FunctionX(ArgumentTuple) This is to move argument processing to the specific Section - UserID is passed as argument on server side only for security + Drone is passed as argument on server side only for security Arguments may be converted from Tuple to Dict in future for clarity """ - Exit = False - while not Exit: + self.ExitLoop = False + while not self.ExitLoop: try: data = self.Recv() Command,Arguments = data[0],data[1] Sucess,Message,Data = self.ProcessCommand(Command,Arguments) - + except Exception as e: Sucess,Message,Data = False,"An Error occured"+str(e),[] - print("Error occured with UserID:",str(self.UserID),". Error :",str(e),". Sending failure message") - + print("Error occured with",self.Thread_Name,":",str(self.ClientID),"Error :",str(e)," Sending failure message") try: self.Send((Sucess,Message,Data)) except Exception as e: - print("UserID:",self.UserID," disconnected") - Exit = True - + print(self.Thread_Name,self.ClientID," disconnected") + self.ExitLoop = True + if not self.Thread_Queue.empty(): data = Thread_Queue.get() Command,Arguments = data[0],data[1] if Command == "Exit": - Exit = True + self.ExitLoop = True + self.DB.Exit() - print("Process will now exit") + print("Process is exiting") + def Send(self,data): + self.con.sendall(self.Crypto.Encrypt(codecs.encode(str(data)))) + def Recv(self): + try: + data = self.Crypto.Decrypt(recvall.recvall(self.con)) + data = ast.literal_eval(codecs.decode(data)) + return data + except Exception as e: + return ("",())#Never references a command + + def Exit(self,Arguments = None): + #self.DB.db_con.close() + print("Process for ",self.Thread_Name,":",self.ClientID," is exiting..") + return True,"Server process is exiting. Ok to disconnect",[] + + + +class UserConnection(ClientConnection): + def ProcessCommand(self,Command,Arguments): - if self.UserID == -1: + if self.ClientID == -1: if Command == "Login": Sucess,Message,Data = self.Login(Arguments) elif Command == "AddUser": # If adding a new user, one must create it first, then log in seperatly @@ -161,7 +168,7 @@ def ProcessCommand(self,Command,Arguments): elif Command == "Exit": Sucess,Message,Data = self.Exit(Arguments) - Exit = True + self.ExitLoop = True #Else if command doesnt exist send back Failure else: Sucess,Message,Data = False,"Command does not exist",[] @@ -170,7 +177,7 @@ def ProcessCommand(self,Command,Arguments): def Login(self,Arguments): Username,Password = Arguments[0],Arguments[1] - Sucess,Message,self.UserID = self.DB.CheckCredentials(Username,Password) + Sucess,Message,self.ClientID = self.DB.CheckCredentials(Username,Password) return Sucess,Message,[] ######################################################## @@ -182,46 +189,46 @@ def AddNoFlyZone(self,Arguments): if len(Arguments) == 3: Coord1,Coord2,Level = Arguments[0],Arguments[1],Arguments[2] Coord1,Coord2 = ast.literal_eval(Coord1),ast.literal_eval(Coord2) - Sucess,Message = self.DB.AddNoFlyZone(Coord1,Coord2,Level,self.UserID) + Sucess,Message = self.DB.AddNoFlyZone(Coord1,Coord2,Level,self.ClientID) else: Sucess,Message = False,"Incorrect Argument format" return Sucess,Message,[] def RemoveNoFlyZone(self,Arguments): ZoneID = Arguments[0] - Sucess,Message = self.DB.RemoveNoFlyZone(self.UserID,ZoneID) + Sucess,Message = self.DB.RemoveNoFlyZone(self.ClientID,ZoneID) return Sucess,Message,[] def ModifyNoFlyZoneLevel(self,Arguments): ZoneID,Level = Arguments[0],Arguments[1] - Sucess,Message = self.DB.ModifyNoFlyZoneLevel(self.UserID,ZoneID,Level) + Sucess,Message = self.DB.ModifyNoFlyZoneLevel(self.ClientID,ZoneID,Level) return Sucess,Message,[] ######################################################## def AddDrone(self,Arguments): DroneName,DronePassword,DroneType,DroneSpeed,DroneRange,DroneWeight = Arguments[0],Arguments[1],Arguments[2],Arguments[3],Arguments[4],Arguments[5] - Sucess,Message = self.DB.AddDrone(self.UserID,DroneName,DronePassword,DroneType,DroneSpeed,DroneRange,DroneWeight) + Sucess,Message = self.DB.AddDrone(self.ClientID,DroneName,DronePassword,DroneType,DroneSpeed,DroneRange,DroneWeight) return Sucess,Message,[] def RemoveDrone(self,Arguments): DroneID = Arguments[0] - Sucess,Message = self.DB.RemoveDrone(self.UserID,DroneID) + Sucess,Message = self.DB.RemoveDrone(self.ClientID,DroneID) return Sucess,Message,[] def GetDroneID(self,Arguments): DroneName = Arguments[0] - Sucess,Message,Data = self.DB.GetDroneID(self.UserID,DroneName) + Sucess,Message,Data = self.DB.GetDroneID(self.ClientID,DroneName) return Sucess,Message,Data def GetDroneCredentials(self,Arguments): DroneID = Arguments[0] - Sucess,Message,Data = self.DB.GetDroneCredentials(self.UserID,DroneID) + Sucess,Message,Data = self.DB.GetDroneCredentials(self.ClientID,DroneID) return Sucess,Message,Data def SetDroneCredentials(self,Arguments): DroneID,DronePassword = Arguments[0],Arguments[1] - Sucess,Message = self.DB.SetDroneCredentials(self.UserID,DroneID,DronePassword) + Sucess,Message = self.DB.SetDroneCredentials(self.ClientID,DroneID,DronePassword) return Sucess,Message,[] def CheckDroneOwnership(self,Arguments): @@ -231,11 +238,11 @@ def CheckDroneOwnership(self,Arguments): def GetDroneInfo(self,Arguments): DroneID = Arguments[0] - Sucess,Message,Data = self.DB.GetDroneInfo(self.UserID,DroneID) + Sucess,Message,Data = self.DB.GetDroneInfo(self.ClientID,DroneID) return Sucess,Message,Data def GetDronesUser(self,Arguments = None): - Sucess,Message,Data = self.DB.GetDronesUser(self.UserID) + Sucess,Message,Data = self.DB.GetDronesUser(self.ClientID) return Sucess,Message,Data def GetDronesAll(self,Arguments = None): @@ -266,20 +273,20 @@ def AddUser(self,Arguments): def SetUserPublicVisibleFlights(self,Arguments): Value = Arguments[0] - Sucess,Message = self.DB.SetUserPublicVisibleFlights(self.UserID,Value) + Sucess,Message = self.DB.SetUserPublicVisibleFlights(self.ClientID,Value) return Sucess,Message,[] def SetAccountType(self,Arguments): Permission,Value = Arguments[0],Arguments[1] - Sucess,Message = self.DB.SetAccountType(self.UserID,Permission,Value) + Sucess,Message = self.DB.SetAccountType(self.ClientID,Permission,Value) return Sucess,Message,[] ####################################################### def GetFlightsUser(self,Arguments = None): - Sucess,Message,Data = self.DB.GetFlightsUser(self.UserID) + Sucess,Message,Data = self.DB.GetFlightsUser(self.ClientID) return Sucess,Message,Data def GetFlightsAll(self,Arguments = None): @@ -297,30 +304,24 @@ def AddFlight(self,Arguments): graph = AATC_AStar.DynoGraph() graph.ImportGraph() - temp = [] - for point in HighPoints: - temp.append(ast.literal_eval(point)) - HighPoints = temp - - - HighPointOK = [] + tempHighPoints = HighPoints + HighPoints = [] try: - for point in HighPoints: #Checks all points are not NoFlyZones + for rawPoint in tempHighPoints: + point = ast.literal_eval(rawPoint) + HighPoints.append(point) NodeID = graph.Find_NodeID(*point) - if graph.GetNode(NodeID).Cost > self.NOFLYZONE_THRESHOLD_COST: #If it exceeds Threshold one cannot go through here - HighPointOK.append(False) - else: - HighPointOK.append(True) - except Exception as e: - print(e) - HighPointOK.append(False) #If out of bounds the loop will generate an exception. This will then cause the program to return. + if graph.GetNode(NodeID).Cost > AATC_Config.NOFLYZONE_THRESHOLD_COST: #If it exceeds Threshold one cannot go through here + return False,"A point in this set is in a restricted area or not in service area. Flight denied.",[] - if not all(HighPointOK): + except Exception as e: + print(self.Thread_Name,":",self.ClientID,"Error in AddFlight HighPointOK assesment",e) return False,"A point in this set is in a restricted area or not in service area. Flight denied.",[] + - S_,M_,Result = self.DB.CheckDroneOwnership(self.UserID,DroneID) - if Result != []: + S_,M_,Result = self.DB.CheckDroneOwnership(self.ClientID,DroneID) + if len(Result) !=0: Start = 0 Next = 1 Max = len(HighPoints) @@ -351,7 +352,7 @@ def AddFlight(self,Arguments): CoordList.append({"Coords":Coords}) Time = StartTime - _,Columns,DroneData = self.DB.GetDroneInfo(self.UserID,DroneID) + _,Columns,DroneData = self.DB.GetDroneInfo(self.ClientID,DroneID) Columns = ast.literal_eval(Columns) DroneData = DroneData[0] SpeedIndex,RangeIndex = Columns.index("DroneSpeed"),Columns.index("DroneRange") @@ -371,7 +372,7 @@ def AddFlight(self,Arguments): #Adding Flight to Database - self.DB.AddFlight(self.UserID,DroneID,HighPoints[0],HighPoints[len(HighPoints)-1],StartTime,EndTime,EndTime,TotalDistance,XOffset,YOffset,ZOffset) + self.DB.AddFlight(self.ClientID,DroneID,HighPoints[0],HighPoints[len(HighPoints)-1],StartTime,EndTime,EndTime,TotalDistance,XOffset,YOffset,ZOffset) ###################### ###################### TEMP WORKAROUND ########## @@ -381,7 +382,7 @@ def AddFlight(self,Arguments): ###################### for WaypointNumber in range(len(CoordList)): - self.DB.AddWaypoint(self.UserID,FlightID,WaypointNumber+1,CoordList[WaypointNumber]["Coords"],CoordList[WaypointNumber]["Time"]) + self.DB.AddWaypoint(self.ClientID,FlightID,WaypointNumber+1,CoordList[WaypointNumber]["Coords"],CoordList[WaypointNumber]["Time"]) return True,"['FlightID','NumberOfWaypoints','StartTime','EndTime','Distance']",[(FlightID,len(CoordList),StartTime,EndTime,TotalDistance)] #Returns data about the flight @@ -398,13 +399,13 @@ def AddFlight(self,Arguments): def RemoveFlight(self,Arguments): FlightID = Arguments[0] - Sucess,Message = self.DB.RemoveFlight(self.UserID,FlightID) + Sucess,Message = self.DB.RemoveFlight(self.ClientID,FlightID) return Sucess,Message,[] ####################################################### def GetFlightWaypointsUser(self,Arguments = None): - Sucess,Message,Data = self.DB.GetFlightWaypointsUser(self.UserID) + Sucess,Message,Data = self.DB.GetFlightWaypointsUser(self.ClientID) return Sucess,Message,Data @@ -430,33 +431,29 @@ def GetMonitorName(self,Arguments): def AddMonitorPermission(self,Arguments): MonitorID,ExpiryDate = Arguments[0],Arguments[1] - Sucess,Message = self.DB.AddMonitorPermission(self.UserID,MonitorID,ExpiryDate) + Sucess,Message = self.DB.AddMonitorPermission(self.ClientID,MonitorID,ExpiryDate) return Sucess,Message,[] def RemoveMonitorPermission(self,Arguments): MonitorID = Arguments[0] - Sucess,Message = self.DB.RemoveMonitorPermission(self.UserID,MonitorID) + Sucess,Message = self.DB.RemoveMonitorPermission(self.ClientID,MonitorID) return Sucess,Message,[] def ModifyMonitorPermissionDate(self,Arguments): MonitorID,NewDate = Arguments[0],Arguments[1] - Sucess,Message = self.DB.ModifyMonitorPermissionDate(self.UserID,MonitorID,NewDate) + Sucess,Message = self.DB.ModifyMonitorPermissionDate(self.ClientID,MonitorID,NewDate) return Sucess,Message,[] def GetMonitorPermissionUser(self,Arguments = None): - Sucess,Message,Data = self.DB.GetMonitorPermissionUser(self.UserID) + Sucess,Message,Data = self.DB.GetMonitorPermissionUser(self.ClientID) return Sucess,Message,Data ################################################# - def Exit(self,Arguments = None): - self.DB.db_con.close() - print("Process for UserID:",self.UserID," is exiting..") - return True,"Server process is exiting",[] @@ -466,12 +463,11 @@ def Exit(self,Arguments = None): class BotConnection(UserConnection): def __init__(self,UserID,chat_id,packet,OutputQueue): - self.UserID = UserID + self.ClientID = UserID self.chat_id = chat_id self.OutputQueue = OutputQueue self.DB = AATC_DB.DBConnection() - self.NOFLYZONE_THRESHOLD_COST = 50 - + Command, Arguments = packet[0],packet[1] self.Main(Command,Arguments) @@ -481,7 +477,7 @@ def Main(self,Command,Arguments): except Exception as e: Sucess,Message,Data = False,"An Error occured"+str(e),[] - print("Error occured with UserID:",str(self.UserID),". Error :",str(e),". Sending failure message") + print("Error occured with UserID:",str(self.ClientID),". Error :",str(e),". Sending failure message") try: self.Send((Sucess,Message,Data)) @@ -517,194 +513,68 @@ def Login(self,Arguments): -class MonitorConnection: - def __init__(self,Thread_Name,Thread_Queue,Connection): - self.DB = AATC_DB.DBConnection() - self.Thread_Name = Thread_Name - self.Thread_Queue = Thread_Queue - self.con = Connection - self.Crypto = AATC_Crypto.Crypter(self.con, mode = "SERVER") - self.MonitorID = -1 #Used to identify if has logged in yet - def Send(self,data): - self.con.sendall(self.Crypto.Encrypt(codecs.encode(str(data)))) - def Recv(self): - try: - data = self.Crypto.Decrypt(recvall.recvall(self.con)) - data = ast.literal_eval(codecs.decode(data)) - # (Command,Arguments) - return data - #return data[0],data[1],data[2] - except Exception as e: - print("MonitorID:",self.MonitorID," Socket data recive error") +class MonitorConnection(ClientConnection): + def ProcessCommand(self,Command,Arguments): + if self.ClientID == -1: + if Command == "Login": + Sucess,Message,Data = self.Login(Arguments) + elif Command == "AddMonitor": # If adding a new Monitor, one must create it first, then log in seperatly + Sucess,Message,Data = self.AddMonitor(Arguments) + elif Command == "Exit": + Sucess,Message,Data = self.Exit(Arguments) + Exit = True + else: + Sucess,Message,Data = False,"Command does not exist",[] - def Connection_Loop(self): - """ - Keeps looping in request for Monitor, - Recived data in format (CommandString,(Arg1,Arg2...)) - Calls function in format FunctionX(ArgumentTuple) - This is to move argument processing to the specific Section - Monitor is passed as argument on server side only for security + else: + if Command == "GetNoFlyZones": + Sucess,Message,Data = self.GetNoFlyZones(Arguments) + + elif Command == "GetDronesAll": + Sucess,Message,Data = self.GetDronesAll(Arguments) + + elif Command == "GetUserID": + Sucess,Message,Data = self.GetUserID(Arguments) + elif Command == "GetUsername": + Sucess,Message,Data = self.GetUsername(Arguments) - Arguments may be converted from Tuple to Dict in future for clarity - """ - Exit = False - while not Exit: - try: - data = self.Recv() - Command,Arguments = data[0],data[1] - if self.MonitorID == -1: - if Command == "Login": - Sucess,Message,Data = self.Login(Arguments) - elif Command == "AddMonitor": # If adding a new Monitor, one must create it first, then log in seperatly - Sucess,Message,Data = self.AddMonitor(Arguments) - elif Command == "Exit": - Sucess,Message,Data = self.Exit(Arguments) - Exit = True - else: - Sucess,Message,Data = False,"Command does not exist",[] + elif Command == "GetMonitorDrones": + Sucess,Message,Data = self.GetMonitorDrones(Arguments) + elif Command == "GetMonitorFlights": + Sucess,Message,Data = self.GetMonitorFlights(Arguments) + elif Command == "GetMonitorFlightWaypoints": + Sucess,Message,Data = self.GetMonitorFlightWaypoints(Arguments) - else: - if Command == "GetNoFlyZones": - Sucess,Message,Data = self.GetNoFlyZones(Arguments) - - elif Command == "GetDronesAll": - Sucess,Message,Data = self.GetDronesAll(Arguments) - - elif Command == "GetUserID": - Sucess,Message,Data = self.GetUserID(Arguments) - elif Command == "GetUsername": - Sucess,Message,Data = self.GetUsername(Arguments) - - elif Command == "GetMonitorDrones": - Sucess,Message,Data = self.GetMonitorDrones(Arguments) - elif Command == "GetMonitorFlights": - Sucess,Message,Data = self.GetMonitorFlights(Arguments) - elif Command == "GetMonitorFlightWaypoints": - Sucess,Message,Data = self.GetMonitorFlightWaypoints(Arguments) - - elif Command == "GetMonitorID": - Sucess,Message,Data = self.GetMonitorID(Arguments) - elif Command == "GetMonitorName": - Sucess,Message,Data = self.GetMonitorName(Arguments) - - elif Command == "RemoveMonitorPermission": - Sucess,Message,Data = self.RemoveMonitorPermission(Arguments) - elif Command == "GetMonitorPermissionMonitor": - Sucess,Message,Data = self.GetMonitorPermissionMonitor(Arguments) - - elif Command == "GetFlightsAll": - Sucess,Message,Data = self.GetFlightsAll(Arguments) - - elif Command == "GetFlightWaypointsAll": - Sucess,Message,Data = self.GetFlightWaypointsAll(Arguments) - - elif Command == "Exit": - Sucess,Message,Data = self.Exit(Arguments) - Exit = True + elif Command == "GetMonitorID": + Sucess,Message,Data = self.GetMonitorID(Arguments) + elif Command == "GetMonitorName": + Sucess,Message,Data = self.GetMonitorName(Arguments) - #Else if command doesnt exist send back Failure - else: - Sucess,Message,Data = False,"Command does not exist",[] - print("Monitor tried to use unregistered command") - except Exception as e: - Sucess,Message,Data = False,"An Error occured"+str(e),[] - print("Error occured with MonitorID:",str(self.MonitorID),"Error :",str(e)," Sending failure message") - try: - self.Send((Sucess,Message,Data)) - except Exception as e: - print("MonitorID:",self.MonitorID," disconnected") - Exit = True + elif Command == "RemoveMonitorPermission": + Sucess,Message,Data = self.RemoveMonitorPermission(Arguments) + elif Command == "GetMonitorPermissionMonitor": + Sucess,Message,Data = self.GetMonitorPermissionMonitor(Arguments) - if not self.Thread_Queue.empty(): - data = Thread_Queue.get() - Command,Arguments = data[0],data[1] - if Command == "Exit": - Exit = True - + elif Command == "GetFlightsAll": + Sucess,Message,Data = self.GetFlightsAll(Arguments) - -## try: -## Exit = False -## while self.MonitorID == -1 and not Exit:#Repeats until logs in -## data = self.Recv() -## try: -## Command,Arguments = data[0],data[1] -## if Command == "Login": -## Sucess,Message,Data = self.Login(Arguments) -## elif Command == "AddMonitor": # If adding a new Monitor, one must create it first, then log in seperatly -## Sucess,Message,Data = self.AddMonitor(Arguments) -## else: -## Sucess,Message,Data = False,"Command does not exist",[] -## except Exception as e: -## Sucess,Message,Data = False,"An Error occured"+str(e),[] -## print("Error occured with MonitorID:",str(self.MonitorID),"Error :",str(e)," Sending failure message") -## self.Send((Sucess,Message,Data)) -## -## -## while not Exit: -## data = self.Recv() -## try: -## Command,Arguments = data[0],data[1] -## if Command == "GetNoFlyZones": -## Sucess,Message,Data = self.GetNoFlyZones(Arguments) -## -## elif Command == "GetDronesAll": -## Sucess,Message,Data = self.GetDronesAll(Arguments) -## -## elif Command == "GetUserID": -## Sucess,Message,Data = self.GetUserID(Arguments) -## elif Command == "GetUsername": -## Sucess,Message,Data = self.GetUsername(Arguments) -## -## elif Command == "GetMonitorDrones": -## Sucess,Message,Data = self.GetMonitorDrones(Arguments) -## elif Command == "GetMonitorFlights": -## Sucess,Message,Data = self.GetMonitorFlights(Arguments) -## elif Command == "GetMonitorFlightWaypoints": -## Sucess,Message,Data = self.GetMonitorFlightWaypoints(Arguments) -## -## elif Command == "GetMonitorID": -## Sucess,Message,Data = self.GetMonitorID(Arguments) -## elif Command == "GetMonitorName": -## Sucess,Message,Data = self.GetMonitorName(Arguments) -## -## elif Command == "RemoveMonitorPermission": -## Sucess,Message,Data = self.RemoveMonitorPermission(Arguments) -## elif Command == "GetMonitorPermissionMonitor": -## Sucess,Message,Data = self.GetMonitorPermissionMonitor(Arguments) -## -## elif Command == "GetFlightsAll": -## Sucess,Message,Data = self.GetFlightsAll(Arguments) -## -## elif Command == "GetFlightWaypointsAll": -## Sucess,Message,Data = self.GetFlightWaypointsAll(Arguments) -## -## elif Command == "Exit": -## Sucess,Message,Data = self.Exit(Arguments) -## Exit = True -## -## #Else if command doesnt exist send back Failure -## else: -## Sucess,Message,Data = False,"Command does not exist",[] -## print("Monitor tried to use unregistered command") -## except Exception as e: -## Sucess,Message,Data = False,"An Error occured"+str(e),[] -## print("Error occured with MonitorID:",str(self.MonitorID),"Error :",str(e)," Sending failure message") -## ## print(Message,str(Data)) -## self.Send((Sucess,Message,Data)) -## -## except Exception as e: -## if type(e) == BrokenPipeError: -## print("MonitorID:",self.MonitorID," disconnected") -## else: -## print("Serious exception occured with MonitorID ",self.MonitorID," Error",e) - self.DB.Exit() - print("Process is exiting") + elif Command == "GetFlightWaypointsAll": + Sucess,Message,Data = self.GetFlightWaypointsAll(Arguments) + + elif Command == "Exit": + Sucess,Message,Data = self.Exit(Arguments) + self.ExitLoop = True + + #Else if command doesnt exist send back Failure + else: + Sucess,Message,Data = False,"Command does not exist",[] + print("Monitor tried to use unregistered command") + return Sucess,Message,Data ################################ def Login(self,Arguments): MonitorName,MonitorPassword = Arguments[0],Arguments[1] - Sucess,Message,self.MonitorID = self.DB.MonitorCheckCredentials(MonitorName,MonitorPassword) + Sucess,Message,self.ClientID = self.DB.MonitorCheckCredentials(MonitorName,MonitorPassword) return Sucess,Message,[] ######### No Fly Zone ################## @@ -739,15 +609,15 @@ def AddMonitor(self,Arguments): return Sucess,Message,[] def GetMonitorDrones(self,Arguments = None): - Sucess,Message,Data = self.DB.GetMonitorDrones(self.MonitorID) + Sucess,Message,Data = self.DB.GetMonitorDrones(self.ClientID) return Sucess,Message,Data def GetMonitorFlights(self,Arguments = None): - Sucess,Message,Data = self.DB.GetMonitorFlights(self.MonitorID) + Sucess,Message,Data = self.DB.GetMonitorFlights(self.ClientID) return Sucess,Message,Data def GetMonitorFlightWaypoints(self,Arguments = None): - Sucess,Message,Data = self.DB.GetMonitorFlightWaypoints(self.MonitorID) + Sucess,Message,Data = self.DB.GetMonitorFlightWaypoints(self.ClientID) return Sucess,Message,Data def GetMonitorID(self,Arguments): @@ -764,11 +634,11 @@ def GetMonitorName(self,Arguments): def RemoveMonitorPermission(self,Arguments): UserID = Arguments[0] - Sucess,Message = self.DB.RemoveMonitorPermission(UserID,self.MonitorID) + Sucess,Message = self.DB.RemoveMonitorPermission(UserID,self.ClientID) return Sucess,Message,[] def GetMonitorPermissionMonitor(self,Arguments = None): - Sucess,Message,Data = self.DB.GetMonitorPermissionMonitor(self.MonitorID) + Sucess,Message,Data = self.DB.GetMonitorPermissionMonitor(self.ClientID) return Sucess,Message,Data ################################################### @@ -782,206 +652,92 @@ def GetFlightWaypointsAll(self,Arguments = None): ############################################# - def Exit(self,Arguments = None): - self.DB.db_con.close() - print("Process for MonitorID:",self.MonitorID," is exiting..") - return True,"Server process is exiting",[] -class DroneConnection: - def __init__(self,Thread_Name,Thread_Queue,Connection): - self.DB = AATC_DB.DBConnection() - self.Thread_Name = Thread_Name - self.Thread_Queue = Thread_Queue - self.con = Connection - self.Crypto = AATC_Crypto.Crypter(self.con, mode = "SERVER") - self.DroneID = -1 #Used to identify if has logged in yet - def Send(self,data): - self.con.sendall(self.Crypto.Encrypt(codecs.encode(str(data)))) - def Recv(self): - try: - data = self.Crypto.Decrypt(recvall.recvall(self.con)) - data = ast.literal_eval(codecs.decode(data)) - # (Command,Arguments) - return data - #return data[0],data[1],data[2] - except Exception as e: - print("DroneID:",self.DroneID," Socket data recive error") - - def Connection_Loop(self): - """ - Keeps looping in request for Drone, - Recived data in format (CommandString,(Arg1,Arg2...)) - Calls function in format FunctionX(ArgumentTuple) - This is to move argument processing to the specific Section - Drone is passed as argument on server side only for security +class DroneConnection(ClientConnection): - Arguments may be converted from Tuple to Dict in future for clarity - """ - Exit = False - while not Exit: - try: - data = self.Recv() - Command,Arguments = data[0],data[1] - if self.DroneID == -1: - if Command == "Login": - Sucess,Message,Data = self.Login(Arguments) - elif Command == "Exit": - Sucess,Message,Data = self.Exit(Arguments) - Exit = True - else: - Sucess,Message,Data = False,"Command does not exist",[] + def ProcessCommand(self,Command,Arguments): + if self.ClientID == -1: + if Command == "Login": + Sucess,Message,Data = self.Login(Arguments) + elif Command == "Exit": + Sucess,Message,Data = self.Exit(Arguments) + Exit = True + else: + Sucess,Message,Data = False,"Command does not exist",[] - else: - if Command == "UpdateDroneStatus": - Sucess,Message,Data = self.UpdateDroneStatus(Arguments) - - elif Command == "DroneGetDroneInfo": - Sucess,Message,Data = self.DroneGetDroneInfo(Arguments) - - elif Command == "CheckForFlight": - Sucess,Message,Data = self.CheckForFlight(Arguments) - elif Command == "GetFlight": - Sucess,Message,Data = self.GetFlight(Arguments) - elif Command == "GetFlightWaypoints": - Sucess,Message,Data = self.GetFlightWaypoints(Arguments) - elif Command == "MarkFlightComplete": - Sucess,Message,Data = self.MarkFlightComplete(Arguments) - - elif Command == "Exit": - Sucess,Message,Data = self.Exit(Arguments) - Exit = True + else: + if Command == "UpdateDroneStatus": + Sucess,Message,Data = self.UpdateDroneStatus(Arguments) - #Else if command doesnt exist send back Failure - else: - Sucess,Message,Data = False,"Command does not exist",[] - print("Drone tried to use unregistered command") + elif Command == "DroneGetDroneInfo": + Sucess,Message,Data = self.DroneGetDroneInfo(Arguments) + + elif Command == "CheckForFlight": + Sucess,Message,Data = self.CheckForFlight(Arguments) + elif Command == "GetFlight": + Sucess,Message,Data = self.GetFlight(Arguments) + elif Command == "GetFlightWaypoints": + Sucess,Message,Data = self.GetFlightWaypoints(Arguments) + elif Command == "MarkFlightComplete": + Sucess,Message,Data = self.MarkFlightComplete(Arguments) - except Exception as e: - Sucess,Message,Data = False,"An Error occured"+str(e),[] - print("Error occured with DroneID:",str(self.DroneID),"Error :",str(e)," Sending failure message") - try: - self.Send((Sucess,Message,Data)) - except Exception as e: - print("DroneID:",self.DroneID," disconnected") - Exit = True + elif Command == "Exit": + Sucess,Message,Data = self.Exit(Arguments) + self.ExitLoop = True - if not self.Thread_Queue.empty(): - data = Thread_Queue.get() - Command,Arguments = data[0],data[1] - if Command == "Exit": - Exit = True - - - -## try: -## Exit = False -## while self.DroneID == -1 and not Exit:#Repeats until logs in -## data = self.Recv() -## try: -## Command,Arguments = data[0],data[1] -## if Command == "Login": -## Sucess,Message,Data = self.Login(Arguments) -## -## else: -## Sucess,Message,Data = False,"Command does not exist",[] -## except Exception as e: -## Sucess,Message,Data = False,"An Error occured"+str(e),[] -## print("Error occured with DroneID:",str(self.DroneID),"Error :",str(e)," Sending failure message") -## self.Send((Sucess,Message,Data)) -## -## -## while not Exit: -## data = self.Recv() -## try: -## Command,Arguments = data[0],data[1] -## if Command == "UpdateDroneStatus": -## Sucess,Message,Data = self.UpdateDroneStatus(Arguments) -## -## elif Command == "DroneGetDroneInfo": -## Sucess,Message,Data = self.DroneGetDroneInfo(Arguments) -## -## elif Command == "CheckForFlight": -## Sucess,Message,Data = self.CheckForFlight(Arguments) -## elif Command == "GetFlight": -## Sucess,Message,Data = self.GetFlight(Arguments) -## elif Command == "GetFlightWaypoints": -## Sucess,Message,Data = self.GetFlightWaypoints(Arguments) -## elif Command == "MarkFlightComplete": -## Sucess,Message,Data = self.MarkFlightComplete(Arguments) -## -## elif Command == "Exit": -## Sucess,Message,Data = self.Exit(Arguments) -## -## #Else if command doesnt exist send back Failure -## else: -## Sucess,Message,Data = False,"Command does not exist",[] -## print("Drone tried to use unregistered command") -## except Exception as e: -## if type(e) != TypeError:# if this error type occurs connection has failed and would otherwise flood console with irrelevant errors -## print("Error occured with DroneID:",str(self.DroneID),"Error :",str(e)," Sending failure message") -## Sucess,Message,Data = False,"An Error occured"+str(e),[] -## -## self.Send((Sucess,Message,Data)) -## -## except Exception as e: -## if type(e) == BrokenPipeError: -## print("DroneID:",self.DroneID," disconnected") -## else: -## print("Serious exception occured with DroneID ",self.DroneID," Error",e) - self.DB.Exit() - print("Process is exiting") + #Else if command doesnt exist send back Failure + else: + Sucess,Message,Data = False,"Command does not exist",[] + print("Drone tried to use unregistered command") + return Sucess,Message,Data def Login(self,Arguments): DroneID,DronePassword = Arguments[0],Arguments[1] - Sucess,Message,self.DroneID = self.DB.DroneCheckCredentials(DroneID,DronePassword) + Sucess,Message,self.ClientID = self.DB.DroneCheckCredentials(DroneID,DronePassword) return Sucess,Message,[] ######################################################## def UpdateDroneStatus(self,Arguments): LastCoords,LastBattery = Coordinate(*Arguments[0]),Arguments[1] - Sucess,Message = self.DB.UpdateDroneStatus(self.DroneID,LastCoords,LastBattery) + Sucess,Message = self.DB.UpdateDroneStatus(self.ClientID,LastCoords,LastBattery) return Sucess,Message,[] ######################################################## def DroneGetDroneInfo(self,Arguments): DroneID = Arguments[0] - Sucess,Message,Data = self.DB.DroneGetDroneInfo(self.DroneID) + Sucess,Message,Data = self.DB.DroneGetDroneInfo(self.ClientID) return Sucess,Message,Data ########################################################## def CheckForFlight(self,Arguments): MaxLookAheadTime = Arguments[0] # How many seconds until flight start should the search allow. Would lead to the drone being locked into that flight most likely. - Sucess,Message,Data = self.DB.CheckForFlight(self.DroneID,MaxLookAheadTime) + Sucess,Message,Data = self.DB.CheckForFlight(self.ClientID,MaxLookAheadTime) return Sucess,Message,Data def GetFlight(self,Arguments): FlightID = Arguments[0] - Sucess,Message,Data = self.DB.GetFlight(self.DroneID,FlightID) + Sucess,Message,Data = self.DB.GetFlight(self.ClientID,FlightID) return Sucess,Message,Data def GetFlightWaypoints(self,Arguments): FlightID = Arguments[0] - Sucess,Message,Data = self.DB.GetFlightWaypoints(self.DroneID,FlightID) + Sucess,Message,Data = self.DB.GetFlightWaypoints(self.ClientID,FlightID) return Sucess,Message,Data def MarkFlightComplete(self,Arguments): FlightID,Code = Arguments[0],Arguments[1] - Sucess,Message = self.DB.MarkFlightComplete(self.DroneID,FlightID,Code) + Sucess,Message = self.DB.MarkFlightComplete(self.ClientID,FlightID,Code) return Sucess,Message,[] ###################################################### - def Exit(self,Arguments = None): - self.DB.db_con.close() - print("Process for DroneID:",self.DroneID," is exiting..") - return True,"Server process is exiting",[] @@ -997,7 +753,8 @@ def Cleaner(Thread_Name,Thread_Queue,Interval = 36000,EndTimeThreshold = 72000): DB.CleanMonitorPermissions() Sucess,Message,FlightIDs = DB.GetCompletedFlightIDs(EndTimeThreshold) - DB.CleanCompletedFlights(EndTimeThreshold) + print(FlightIDs) + DB.CleanFlights(FlightIDs) for WrappedID in FlightIDs: #Wrapped as will be in for FlightIDs = [[a,],[b,],[c,]] where letters mean flightIDs DB.CleanCompletedFlightWaypoints(WrappedID[0]) @@ -1031,34 +788,34 @@ def Cleaner(Thread_Name,Thread_Queue,Interval = 36000,EndTimeThreshold = 72000): -if __name__ == "__main__": #For testing purposes - HOST = '' - PORT = 8000 - - s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) - s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) - print( 'Socket created') - - try: - s.bind((HOST, PORT)) - except: - print("Error binding port") - s.close() - sys.exit() - - print( 'Socket bind complete') - s.listen(10) - print( 'Socket now listening') - - - while 1: - try: - conn, addr = s.accept() - print( '\nConnected with ' + addr[0] + ':' + str(addr[1])) - UConn = MonitorConnection(conn) - UConn.Connection_Loop() - except Exception as e: - print(str(e)) +##if __name__ == "__main__": #For testing purposes +## HOST = '' +## PORT = 8000 +## +## s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) +## s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) +## print( 'Socket created') +## +## try: +## s.bind((HOST, PORT)) +## except: +## print("Error binding port") +## s.close() +## sys.exit() +## +## print( 'Socket bind complete') +## s.listen(10) +## print( 'Socket now listening') +## +## +## while 1: +## try: +## conn, addr = s.accept() +## print( '\nConnected with ' + addr[0] + ':' + str(addr[1])) +## UConn = MonitorConnection(conn) +## UConn.Connection_Loop() +## except Exception as e: +## print(str(e)) diff --git a/AATC_Server_Starter.py b/AATC_Server_Starter.py index 9e2fe47..5368fe4 100644 --- a/AATC_Server_Starter.py +++ b/AATC_Server_Starter.py @@ -153,7 +153,7 @@ def ProcessSpawner(Name,Communications_Queue,Port,Type,Target): data = Communications_Queue.get() Command,Arguments = data[0],data[1] if Command == "Exit": - self.Exit = True + Exit = True except Exception as e: @@ -163,9 +163,7 @@ def ProcessSpawner(Name,Communications_Queue,Port,Type,Target): def StartProcesses(Control_Queue): Control_Queue.put(("Controller","Create_Process",("USpawner",ProcessSpawner,(8000,"User",MakeUserConnection)))) - Control_Queue.put(("Controller","Create_Process",("MSpawner",ProcessSpawner,(8001,"Monitor",MakeMonitorConnection)))) - Control_Queue.put(("Controller","Create_Process",("DSpawner",ProcessSpawner,(8002,"Drone",MakeDroneConnection)))) @@ -178,45 +176,12 @@ def StartProcesses(Control_Queue): if __name__ == "__main__": print("Server is starting") -## KillSwitch = multiprocessing.Event() -## HighProcessList = [] -## #Launch UserProcess spawner -## UPS = multiprocessing.Process(target = ProcessSpawner,args = (8000,"User",MakeUserConnection,KillSwitch)) -## HighProcessList.append(UPS) -## UPS.start() -## -## #Launch MonitorPerocess spawner -## MPS = multiprocessing.Process(target = ProcessSpawner,args = (8001,"Monitor",MakeMonitorConnection,KillSwitch)) -## HighProcessList.append(MPS) -## MPS.start() -## -## #Launch DroneProcess Spawner -## DPS = multiprocessing.Process(target = ProcessSpawner,args = (8002,"Drone",MakeDroneConnection,KillSwitch)) -## HighProcessList.append(DPS) -## DPS.start() -## -## #Launch NoFlyZoneGrapher -## NFZG = multiprocessing.Process(target = AATC_NoFlyZoneGrapher.NoFlyZoneGrapher, args = (KillSwitch,)) -## HighProcessList.append(NFZG) -## NFZG.start() -## -## CLN = multiprocessing.Process(target = AATC_Server.Cleaner,args = (KillSwitch,)) -## HighProcessList.append(CLN) -## CLN.start() Control_Queue = AATC_GPIO.Create_Controller() StartProcesses(Control_Queue) - - - - - - - - Main_Command = "" while Main_Command != "EXIT":