class jAjax: def __init__(self): self.scheduler = Scheduler(rootLogger) self.JEXAM = JEXAM(rootLogger) self.running = True rootLogger.info("[jAJAX] Loading config") try: with open("config/config.json") as data_file: self.config = json.load(data_file) except FileNotFoundError: rootLogger.critical("[jAJAX] No config file was found !") sys.exit() except ValueError: rootLogger.critical("[jAJAX] Config file does not contain valid json !") sys.exit() rootLogger.info("[jAJAX] Finished loading config") with open(self.config['secret'], "rb") as fin: key = fin.readline() self.output = secureSave.SecureSave(key) self.knownCourses = self.config["known_courses"] # User initialisation self.users = [] f = [] filenames = [] for (dirpath, dirnames, filenames) in walk("config/users/"): f.extend(filenames) break for userFile in filenames: content = self.output.read("config/users/" + userFile) index = userFile.find(".") self.users.append(User(content, rootLogger, userFile[:index])) self.idsToWatch = [] self.chatids = [] # Collect all ToIDs to watch for user in self.users: self.chatids.append(user.getTelegramToken()) for course in user.courses: if self.idsToWatch.count(course) == 0: rootLogger.info(f"[jAJAX] Adding course number {course} to watch") self.idsToWatch.append(course) self.chatids = self.chatids + self.config["chatids"] self.chatids = list(set(self.chatids)) self.telegram = telegram.TelegramBot(self.chatids, self) rootLogger.info("[jAJAX] Finished initialisation") def run(self) -> None: rootLogger.info("[jAJAX] Started bot") while self.running: task = self.scheduler.getTask() if task: if task["taskType"] == Task.LOGIN: rootLogger.info(f"[jAJAX] Executing LOGIN task with params {task['params']}") user = task["params"]["user"] self.taskLogin(user) if task["taskType"] == Task.ENROLL: rootLogger.info(f"[jAJAX] Executing ENROLL task with params {task['params']}") user = task["params"]["user"] if not self.JEXAM.enroll(user, teachingOfferID=task["params"]["toID"], lectureID=task["params"]["lectureID"]): rootLogger.warning("[jAJAX] ENROLL task ") self.scheduler.addTask(Task.LOGIN, params=params) self.scheduler.addTask(Task.ENROLL, task["params"]) self.scheduler.addTask(Task.LOGOUT, task["params"]) else: params = { "user": user } self.scheduler.addTask(Task.SAVE, params) self.telegram.sendMessageTo(user, f'You have been enrolled into {task["params"]["name"]}') if task["taskType"] == Task.REMOVE: user = task["params"]["user"] if not self.JEXAM.cancelEnroll(user, teachingOfferID=task["params"]["toID"], lectureID=task["params"]["lectureID"]): self.scheduler.addTask(Task.LOGIN, params=params) self.scheduler.addTask(Task.REMOVE, task["params"]) self.scheduler.addTask(Task.LOGOUT, task["params"]) if task["taskType"] == Task.LOGOUT: user = task["params"]["user"] rootLogger.info(f"[jAJAX] Performing LOGOUT task on {user.getUsername()}") if not self.JEXAM.logout(user): self.scheduler.addTask(Task.LOGOUT, task["params"]) if task["taskType"] == Task.SAVE: user = task["params"]["user"] rootLogger.info(f"[jAJAX] Performing SAVE task on {user.getUsername()}") text = user.serialize() self.output.write("config/users/" + str(user.id) + ".json", text) rootLogger.info(f"[jAJAX] Done with SAVE task on {user.getUsername()}") if task["taskType"] == Task.RELOAD: rootLogger.info(f"[jAJAX] Performing lesson reload for ids: {self.idsToWatch}") for id in self.idsToWatch: lectures = self.JEXAM.getLectures(id) if not lectures: continue rootLogger.debug(f"[jAJAX] Received following lectures: \n {lectures}") flag_changed = False for lecture in lectures: rootLogger.info(f"[jAJAX] Checking lecture {lecture['id']}") rootLogger.debug(f"[jAJAX] Which looks like this: \n {json.dumps(lecture)}") # Check if course has been checked with users previously or is unknown if not id in self.config["known_courses"] or self.config["known_courses"][id].count( lecture["id"]) == 0: self.telegram.sendBroadcast( f"A new course has appeared on JEXAM. It has the name {lecture['name']}") # Check if id has existing list, otherwise create an empty list if not id in self.config["known_courses"]: self.config["known_courses"][id] = [] self.config["known_courses"][id].append(lecture["id"]) flag_changed = True rootLogger.info(f"[jAJAX] Found an unknown course with id {id}") for user in self.users: rootLogger.info(f"[jAJAX] Checking if user wants to enroll: {user.getUsername()}") if user.checkForEnroll(id, lecture["day"], lecture["slot"], lecture["room"]["building"]["abbreviation"] + "/" + lecture["room"]["roomNo"]): rootLogger.info( f"[jAJAX] User {user.getUsername()} wants to enroll into {id}") if lecture["freeForEnrollCandidates"]["start"] / 1000 > floor(time.time()): rootLogger.info(f"[jAJAX] Enrollment for {id} for {user.getUsername()}" f" is in the future, at" f" {datetime.fromtimestamp(lecture['freeForEnrollCandidates']['start'] / 1000).strftime('%m/%d/%Y, %H:%M:%S')}") rootLogger.debug(f'[jAJAX] Corresponding timestamp is ' f'{lecture["freeForEnrollCandidates"]["start"]}') rootLogger.debug(f"[jAJAX] Current timestamp is {floor(time.time())}") params = { "user": user, "timestamp": int( lecture["freeForEnrollCandidates"]["start"]) / 1000 - 30 } self.scheduler.addTask(Task.LOGIN, params) params2 = { "user": user, "timestamp": int(lecture["freeForEnrollCandidates"]["start"]) / 1000, "toID": id, "lectureID": lecture["id"], "name": lecture["name"] } self.scheduler.addTask(Task.ENROLL, params2) params3 = { "user": user, "timestamp": int( lecture["freeForEnrollCandidates"]["start"]) / 1000 + 30 } self.scheduler.addTask(Task.LOGOUT, params3) else: rootLogger.info(f"[jAJAX] User {user.getUsername()} can enroll right away") params = { "user": user, "timestamp": 0 } rootLogger.info(f"[jAJAX] Scheduling ENROLL series for user" f" {user.getUsername()}") self.scheduler.addTask(Task.LOGIN, params) params2 = { "user": user, "timestamp": 0, "toID": id, "lectureID": lecture["id"], "name": lecture["name"] } self.scheduler.addTask(Task.ENROLL, params2) params3 = { "user": user, "timestamp": 0 } self.scheduler.addTask(Task.LOGOUT, params3) if flag_changed: rootLogger.info(f"[jAJAX] Saving configfile") with open("config/config.json", "w") as outfile: json.dump(self.config, outfile) self.scheduler.addTask(Task.RELOAD, {"timestamp": time.time() + 15 * 60}) if not len(self.users) == 0: self.scheduler.addTask(Task.LOGIN, {"timestamp": time.time() + 60, "user": self.users[0]}) self.scheduler.addTask(Task.CHECKID, {"timestamp": time.time() + 90, "user": self.users[0]}) self.scheduler.addTask(Task.LOGOUT, {"timestamp": time.time() + 120, "user": self.users[0]}) if task["taskType"] == Task.CHECKID: rootLogger.info(f"[jAJAX] Performing id check") if self.JEXAM.ping(user): rootLogger.info(f"[jAJAX] User has valid ping for id check") html = self.JEXAM.getSchedulerPage(task["params"]["user"]) newIDs = idChecker.getnewIDs(html, self.config["knownIDs"]) rootLogger.info(f"[jAJAX] newIDs are these: {newIDs}") if not len(newIDs) == 0: # There have been new IDs sighted rootLogger.info(f"[jAJAX] At least one new ID found") if self.config["neverAny"] and len(self.config["knownIDs"]) == 0: rootLogger.info(f"[jAJAX] First contact with IDs; NeverAny will be set to false") self.config["neverAny"] = False self.config["knownIDs"] = newIDs else: for ID in newIDs: self.telegram.sendBroadcast(f"Name: {ID['name']} \n" f"ID: {ID['id']} \n" f"A new module has been added to JEXAM!") self.config["knownIDs"].append(ID) rootLogger.info(f"[jAJAX] Saving configfile") with open("config/config.json", "w") as outfile: json.dump(self.config, outfile) else: rootLogger.warning(f"[jAJAX] ID check user had no valid ping. Aborting") else: print(f"\r There are currently {len(self.scheduler.criticalQ) + len(self.scheduler.downtimeQ)} " f"entries in the queue. But none are scheduled for now.", end="") time.sleep(1) rootLogger.info("[jAJAX] Bot is shutting down!") self.telegram.tb.stop_bot() rootLogger.info("[jAJAX] Telegram api was stopped.") rootLogger.info("[jAJAX] Saving config") with open("config/config.json", "w") as outfile: json.dump(self.config, outfile) rootLogger.info("[jAJAX] Config saved. Stopping...") def taskLogin(self, user: User) -> None: rootLogger.info("[jAJAX] Starting login procedure for " + user.getUsername()) if not user.getSession() is None: if self.JEXAM.ping(user): rootLogger.info(f"[jAJAX] LOGIN successful for {user.getUsername()}") return True returncode = self.JEXAM.login(user) if returncode == False: rootLogger.info(f"[jAJAX] LOGIN failed due to unknown reasons for {user.getUsername()}") params = { "timestamp": 0, "user": user } rootLogger.info(f"[jAJAX] Retrieing LOGIN procedure for {user.getUsername()}") self.scheduler.addTask(Task.LOGIN, params=params) if returncode == 2: rootLogger.info(f"[jAJAX] LOGIN failed due to concurrentLogin for {user.getUsername()}") params = { "timestamp": time.time() + 60, "user": user } rootLogger.info(f"[jAJAX] Retrieing LOGIN procedure for {user.getUsername()}") self.scheduler.addTask(Task.LOGIN, params=params) if returncode == 3: rootLogger.warning(f"[jAJAX] Login credentials are wrong for user {user.getUsername()}") rootLogger.warning(f"[jAJAX] Removing user {user.getUsername()}") self.removeUser(user, "Invalid login credentials") def stop(self) -> None: time.sleep(5) self.running = False def addChatID(self, chatid: int) -> None: self.chatids.append(chatid) self.config["chatids"] = self.chatids with open("config/config.json", "w") as outfile: json.dump(self.config, outfile) def addClassToUser(self, chatid: int, classID: int, day: int, slot: int, room: int) -> None: sendingUser = None for user in self.users: if chatid == user.getTelegramToken(): sendingUser = user if sendingUser is None: self.telegram.sendMessageTo(chatid, "You dont have a connected JEXAM account!") return r = sendingUser.addClassToEnroll(classID, day, slot, room) if r: self.telegram.sendMessageTo(sendingUser, "Class was successfully added!") if classID not in self.idsToWatch: self.idsToWatch.append(classID) self.scheduler.addTask(Task.SAVE, params={"user": sendingUser}) else: self.telegram.sendMessageTo(sendingUser, "You have already added that class!") def addUser(self, chatid: int, username: str, password: str) -> None: for user in self.users: # if user.getTelegramToken() == chatid: # self.telegram.sendMessageTo(chatid, "You already have an account connected to your telegram account!") # return if user.getUsername() == username: self.telegram.sendMessageTo(chatid, "There is already a user with that name!") return obj = {"username": username, "password": password, "telegramToken": chatid, "courses": {}} f = [] filenames = [] allIds = [] for (dirpath, dirnames, filenames) in walk("config/users/"): f.extend(filenames) break for userFile in filenames: index = userFile.find(".") allIds.append(userFile[:index]) user = None for i in range(0, len(allIds) + 1): if i not in allIds: self.output.write("config/users/" + str(i) + ".json", json.dumps(obj)) user = User(json.dumps(obj), rootLogger, i) break for course in user.courses: if self.idsToWatch.count(course) == 0: rootLogger.info(f"[jAJAX] Adding course number {course} to watch") self.idsToWatch.append(course) self.users.append(user) self.telegram.sendMessageTo(chatid, "The user has been successfully connected to your account! \n" "Please delete the /register message now!") def listAllCourses(self, chatid: int) -> None: sendingUser = None for user in self.users: if chatid == user.getTelegramToken(): sendingUser = user if sendingUser is None: self.telegram.sendMessageTo(chatid, "You dont have a connected JEXAM account!") return message = "" for course in sendingUser.courses: message += f"{course}: \n" for entry in sendingUser.courses[course]: message += f"\t\t{entry['day']} {entry['slot']} {entry['room']}\n" if message == "": message = "You have no added classes!" self.telegram.sendMessageTo(sendingUser, message) def removeClassFromUser(self, chatid: int, classID: int, day: int, slot: int, room: int) -> None: sendingUser = None for user in self.users: if chatid == user.getTelegramToken(): sendingUser = user if sendingUser is None: self.telegram.sendMessageTo(chatid, "You dont have a connected JEXAM account!") return r = sendingUser.removeClassToEnroll(classID, day, slot, room) if r: self.telegram.sendMessageTo(sendingUser, "The class has been succesfully removed!") self.scheduler.addTask(Task.SAVE, {"user": sendingUser}) else: self.telegram.sendMessageTo(sendingUser, "No such class was found!") def removeChatid(self, chatid: int): rootLogger.info(f"[jAJAX] Removing chatid {chatid} from chatids") self.chatids.remove(chatid) def removeUser(self, user: Union[User, int], reason): if isinstance(user, int): sendingUser = None for entry in self.users: if user == entry.getTelegramToken(): sendingUser = entry if sendingUser is None: self.telegram.sendMessageTo(user, "You dont have a connected JEXAM account! So only removing your chat") self.chatids.remove(user) return user = sendingUser self.telegram.sendMessageTo(user, f"Your user is removed due to {reason}!") self.chatids.remove(user.getTelegramToken()) self.users.remove(user) self.scheduler.removeEntriesByUser(user) remove(f"config/users/{user.id}.json")
class Framework(object): def __init__(self, *argv): super(Framework, self).__init__() self.packages = {} self.paths = {} self.callbacks = {} self.layers = {} self.shortcuts = {} self.base = None self.window = None self.displayRegion = None self.camera = None self.cameraMask = 0x700000FF self.scheduler = None self.eventManager = None self.gui = None self.world = None self.activeLayer = None self.captureTask = None self.frame = 0 self.configuration = Configuration() self.parser = OptionParser(version = self.configuration.fullName, description = ("%s Copyright by %s. For additional help, contact "+ "the authors at <%s> or visit the project homepage under %s.") % \ (self.configuration.summary, self.configuration.authors, self.configuration.contact, self.configuration.home), usage = "usage: %prog [OPT1 [OPT2 [...]]] [FILE1 [FILE2 [...]]", add_help_option = False) self.parser.add_option("-h", "--help", dest = "help", default = False, action = "store_true", help = "show this help message and exit") group = OptionGroup(self.parser, "Options that control the simulation") group.add_option("--framerate", dest = "framerate", type = "float", metavar = "FPS", default = 60.0, action = "store", help = "maximum framerate in frames/s [%default]") group.add_option("-f", "--fullscreen", dest = "fullscreen", default = False, action = "store_true", help = "startup in fullscreen mode") group.add_option("-p", "--pause", dest = "pause", default = False, action = "store_true", help = "immediately pause simulation on startup") self.parser.add_option_group(group) group = OptionGroup(self.parser, "Framework configuration options") group.add_option("-i", "--include", dest = "include", metavar = "PACKAGE", action = "append", help = "include a list of packages") self.parser.add_option_group(group) group = OptionGroup(self.parser, "Output and debugging options") group.add_option("-v", "--verbose", dest = "verbose", default = False, action = "store_true", help = "enable verbose output") group.add_option("-d", "--debug", dest = "debug", default = False, action = "store_true", help = "enable debugging output") self.parser.add_option_group(group) group = OptionGroup(self.parser, "Options that provide information") group.add_option("--build", dest = "build", default = False, action = "store_true", help = "print build information and exit") group.add_option("--defaults", dest = "defaults", default = False, action = "store_true", help = "print default paths and exit") self.parser.add_option_group(group) (self.options, self.arguments) = self.parser.parse_args() self.verbose = self.options.verbose self.debug = self.options.debug self.include("morsel") self.addPath("conf", self.configuration.configurationPath) self.configFiles = ["defaults.conf"] self.windowTitle = self.configuration.fullName if self.options.include: for include in self.options.include: self.include(include) reparse = False for package in self.packages: if self.packages[package].options: group = OptionGroup(self.parser, "Options defined by "+package) group.add_options(self.packages[package].options) self.parser.add_option_group(group) reparse = True if reparse: (self.options, self.arguments) = self.parser.parse_args() if self.options.help: self.parser.print_help() exit(0) if self.options.build: print "Build system: %s" % self.configuration.buildSystem print "Build architecture: %s" % self.configuration.buildArchitecture print "Build type: %s" % self.configuration.buildType exit(0) if self.options.defaults: for package in self.packages: print "Package "+package+":" print " System path: "+self.getSystemDir(package) print " Configuration path: "+self.getConfigDir(package) print " User path: "+self.getUserDir(package) exit(0) for argument in self.arguments: matched = False for package in self.packages: if self.packages[package].arguments: for dest in self.packages[package].arguments: match = re.match(self.packages[package].arguments[dest], argument) if match: if len(match.groups()) > 1: value = list(match.groups()) else: value = match.group(1) setattr(self.packages[package].configuration, dest, value) matched = True if not matched: self.configFiles.append(argument) #------------------------------------------------------------------------------- def getSystemDir(self, package = "morsel"): try: return os.environ[self.packages[package].homeVar] except KeyError: return self.packages[package].systemDir systemDir = property(getSystemDir) #------------------------------------------------------------------------------- def getConfigDir(self, package = "morsel"): return self.packages[package].configDir configDir = property(getConfigDir) #------------------------------------------------------------------------------- def getUserDir(self, package = "morsel"): return self.packages[package].userDir userDir = property(getUserDir) #------------------------------------------------------------------------------- def getGUI(self): if hasattr(self, "_gui") and self._gui: return self._gui else: return None def setGUI(self, gui): if not hasattr(self, "_gui") or not self._gui: self._gui = gui else: self.error("GUI already initialized.") gui = property(getGUI, setGUI) #------------------------------------------------------------------------------- def getWorld(self): if hasattr(self, "_world") and self._world: return self._world else: return None def setWorld(self, world): if not hasattr(self, "_world") or not self._world: self._world = world else: self.error("World already initialized.") world = property(getWorld, setWorld) #------------------------------------------------------------------------------- def getConfigVariable(self, variable, types): variable = panda.ConfigVariable(variable) if not isinstance(types, list): types = [types] values = [] for i in range(len(types)): if types[i] == bool: values.append(bool(variable.getBoolWord(i))) elif types[i] == float: values.append(float(variable.getDoubleWord(i))) elif types[i] == int: values.append(int(variable.getIntWord(i))) elif types[i] == str: values.append(str(variable.getStringWord(i))) if len(values) == 1: return values[i] elif not values: return None else: return values def setConfigVariable(self, variable, values): variable = panda.ConfigVariable(variable) if not isinstance(values, list): values = [values] for i in range(len(values)): if type(values[i]) == bool: variable.setBoolWord(i, values[i]) elif type(values[i]) == float: variable.setDoubleWord(i, values[i]) elif type(values[i]) == int: variable.setIntWord(i, values[i]) elif type(values[i]) == str: variable.setStringWord(i, values[i]) #------------------------------------------------------------------------------- def getFullscreen(self): return self.getConfigVariable("fullscreen", bool) def setFullscreen(self, fullscreen): self.setConfigVariable("fullscreen", fullscreen) if self.window: properties = panda.WindowProperties(self.window.getProperties()) properties.setFullscreen(fullscreen) self.window.requestProperties(properties) fullscreen = property(getFullscreen, setFullscreen) #------------------------------------------------------------------------------- def getWindowPosition(self): return self.getConfigVariable("win-origin", [float, float]) def setWindowPosition(self, position): self.setConfigVariable("win-origin", position) if self.window: properties = panda.WindowProperties(self.window.getProperties()) properties.setOrigin(position[0], position[1]) self.window.requestProperties(properties) windowPosition = property(getWindowPosition, setWindowPosition) #------------------------------------------------------------------------------- def getWindowSize(self): return self.getConfigVariable("win-size", [float, float]) def setWindowSize(self, size): self.setConfigVariable("win-size", size) if self.window: properties = panda.WindowProperties(self.window.getProperties()) properties.setSize(size[0], size[1]) self.window.requestProperties(properties) windowSize = property(getWindowSize, setWindowSize) #------------------------------------------------------------------------------- def getWindowTitle(self): return self.getConfigVariable("window-title", str) def setWindowTitle(self, title): self.setConfigVariable("window-title", title) if self.window: properties = panda.WindowProperties(self.window.getProperties()) properties.setTitle(title) self.window.requestProperties(properties) windowTitle = property(getWindowTitle, setWindowTitle) #------------------------------------------------------------------------------- def getBackgroundColor(self): return self.getConfigVariable("background-color", [float, float, float, float]) def setBackgroundColor(self, color): self.setConfigVariable("background-color", color) if self.displayRegion: self.displayRegion.setClearColorActive(True) self.displayRegion.setClearColor(panda.Vec4(*color)) backgroundColor = property(getBackgroundColor, setBackgroundColor) #------------------------------------------------------------------------------- def getShowFrameRate(self): return self.getConfigVariable("show-frame-rate-meter", bool) def setShowFrameRate(self, show): self.setConfigVariable("show-frame-rate-meter", show) if self.base: self.base.setFrameRateMeter(show) showFrameRate = property(getShowFrameRate, setShowFrameRate) #------------------------------------------------------------------------------- def getMaxFrameRate(self): mode = self.getConfigVariable("clock-mode", str) if mode == "normal": return None else: return self.getConfigVariable("clock-frame-rate", float) def setMaxFrameRate(self, frameRate): if frameRate: self.setConfigVariable("clock-mode", "limited") self.setConfigVariable("clock-frame-rate", frameRate) if self.scheduler: self.scheduler.clock.setMode(panda.ClockObject.MLimited) self.scheduler.clock.setFrameRate(frameRate) else: self.setConfigVariable("clock-mode", "normal") if self.scheduler: self.scheduler.clock.setMode(panda.ClockObject.MNormal) maxFrameRate = property(getMaxFrameRate, setMaxFrameRate) #------------------------------------------------------------------------------- def getCameraMask(self): return self._cameraMask def setCameraMask(self, cameraMask): self._cameraMask = cameraMask if self.camera: self.camera.setCameraMask(panda.BitMask32(self._cameraMask)) cameraMask = property(getCameraMask, setCameraMask) #------------------------------------------------------------------------------- def getActiveLayer(self): return self._activeLayer def setActiveLayer(self, layer): if not layer or self.layers.has_key(layer): self._activeLayer = layer if self.world and self.world.scene: self.world.scene.activeLayer = layer else: self.error("Layer '"+layer+"' is undefined.") activeLayer = property(getActiveLayer, setActiveLayer) #------------------------------------------------------------------------------- def include(self, package, **kargs): package = package.replace("-", "_") if package in self.packages.keys(): return self.info("Including package: "+package) try: self.packages[package] = Package(package, **kargs) except Exception as includeError: self.error("Failed to include package "+package+": "+str(includeError)) if self.packages[package].requires: for required in self.packages[package].requires: self.include(required) packageModule = __import__(self.packages[package].module) packagePath = os.path.dirname(packageModule.__file__) modules = [name for _, name, _ in pkgutil.iter_modules([packagePath])] if "facade" in modules: facade = __import__(self.packages[package].module+".facade", __builtin__.globals(), __builtin__.locals(), ["*"]) for expression in dir(facade): if not __builtin__.__dict__.has_key(expression): __builtin__.__dict__[expression] = getattr(facade, expression) #------------------------------------------------------------------------------- def addPath(self, extension, *args): if not self.paths.has_key(extension): self.paths[extension] = [] for path in args: if not path in self.paths[extension]: self.paths[extension].append(path) #------------------------------------------------------------------------------- def addLayer(self, layer, description): self.layers[layer] = description if len(self.layers) == 1: self.activeLayer = layer #------------------------------------------------------------------------------- def addShortcut(self, key, function, description): if not key in self.shortcuts: self.shortcuts[key] = description handler = EventHandler(function) self.eventManager.addHandler(key, handler) else: self.error("Duplicate shortcut for '"+key+"' key.") #------------------------------------------------------------------------------- def error(self, message): raise RuntimeError(message) #------------------------------------------------------------------------------- def info(self, message): if self.verbose or self.debug: message = message.strip().split("\n") message = string.join(message, "\nInfo: ") print "Info: "+message #------------------------------------------------------------------------------- def spam(self, message): if self.debug: message = message.strip().split("\n") message = string.join(message, "\nDebug: ") print "Debug: "+message #------------------------------------------------------------------------------- def findConfigFile(self, filename, package = None): if os.path.exists(filename): return os.path.abspath(filename) if package: packages = [package] else: packages = self.packages.keys() for package in reversed(packages): resultPath = os.path.join(self.getConfigDir(package), filename) if os.path.exists(resultPath): return os.path.abspath(resultPath) return None #------------------------------------------------------------------------------- def findFile(self, filename, package = None): if os.path.exists(filename): return os.path.abspath(filename) name, extension = os.path.splitext(filename) extension = extension[1:] if self.paths.has_key(extension): if package: packages = [package] else: packages = self.packages.keys() for path in self.paths[extension]: if not os.path.isabs(path): for package in reversed(packages): for dir in [self.getUserDir(package), self.getSystemDir(package)]: resultPath = os.path.join(dir, path, filename) if os.path.exists(resultPath): return os.path.abspath(resultPath) else: resultPath = os.path.join(path, filename) if os.path.exists(resultPath): return os.path.abspath(resultPath) return None #------------------------------------------------------------------------------- def loadConfigFile(self, filename, package = None): configFile = self.findConfigFile(filename, package) if configFile: self.info("Loading configuration file: "+configFile) context = inspect.stack()[1][0].f_globals execfile(configFile, context) else: self.error("Configuration file '"+filename+"' not found.") #------------------------------------------------------------------------------- def executeFile(self, filename, package = None, **kargs): filePath = self.findFile(filename, package) if filePath: context = inspect.stack()[1][0].f_globals parameters = {} execfile(filePath, context, parameters) parameters.update(kargs) return parameters else: self.error("File '"+filename+"' not found.") #------------------------------------------------------------------------------- def createInstance(self, module, type, **kargs): for package in reversed(self.packages.keys()): try: imported = __import__(self.packages[package].module+"."+module, __builtin__.globals(), __builtin__.locals(), [type]) instance = getattr(imported, type) except ImportError as importError: self.spam("Importing type "+type+" from "+ self.packages[package].module+"."+module+" failed: "+ str(importError)) self.spam(traceback.format_exc()) except AttributeError as attributeError: self.spam("Importing type "+type+" from "+ self.packages[package].module+"."+module+" failed: "+ str(attributeError)) self.spam(traceback.format_exc()) else: self.spam("Importing type "+type+" from "+ self.packages[package].module+"."+module+" succeeded") return instance(**kargs) error = "Failed to import "+type+" from module "+module+"." if self.debug: error = error+" See debugging output for details." else: error = error+" Enable debugging output for details." self.error(error) #------------------------------------------------------------------------------- def loadInstance(self, module, filename = None, **kargs): if filename: parameters = self.executeFile(filename, **kargs) else: parameters = kargs if parameters.has_key("type"): type = parameters["type"] del parameters["type"] return self.createInstance(module, type, **parameters) else: self.error("Missing type parameter.") #------------------------------------------------------------------------------- def importPhysics(self, name, module = None): if module: if not self.world: self.error("Failed to import physics class "+name+ " from module "+module+": World not initialized.") submodules = name.split(".") if len(submodules) > 1: module = module+"."+self.world.physics+"."+string.join( submodules[0:len(submodules)-1], ".") name = submodules[-1] else: module = module+"."+self.world.physics module = __import__(module, fromlist=[name]) return getattr(module, name) else: if not self.world: self.error("Failed to import physics module "+module+ ": World not initialized.") return __import__(name+"."+self.world.physics) #------------------------------------------------------------------------------- def run(self): if not self.base: self.base = ShowBase() self.window = self.base.win self.camera = self.base.camera.getChild(0).node() self.displayRegion = self.camera.getDisplayRegion(0) self.scheduler = Scheduler(pause = self.options.pause) self.eventManager = EventManager() for configFile in self.configFiles: self.loadConfigFile(configFile) self.locals = inspect.stack()[0][0].f_globals self.maxFrameRate = self.options.framerate self.fullscreen = self.options.fullscreen self.camera.setCameraMask(panda.BitMask32(self.cameraMask)) self.camera.getDisplayRegion(0).setDrawCallback( panda.PythonCallbackObject(self.drawCallback)) self.base.run() else: self.error("Framework already running.") #------------------------------------------------------------------------------- def exit(self): sys.exit() #------------------------------------------------------------------------------- def toggleLayer(self): layers = self.layers.keys() index = layers.index(self.activeLayer) self.activeLayer = layers[(index+1)%len(layers)] #------------------------------------------------------------------------------- def saveScreen(self, filename = "frame-%.jpg"): if self.window: filename = filename.replace("%", "%06d" % (self.frame)) self.window.saveScreenshot(filename) self.frame += 1 #------------------------------------------------------------------------------- def toggleCaptureScreen(self, framerate = 24): if not self.captureTask: self.captureTask = self.scheduler.addTask("CaptureScreen", self.captureScreen, period = 1.0/framerate) else: self.scheduler.removeTask(self.captureTask) #------------------------------------------------------------------------------- def captureScreen(self, time): self.saveScreen() return True #------------------------------------------------------------------------------- def addDrawCallback(self, name, callback): self.callbacks[name] = callback #------------------------------------------------------------------------------- def drawCallback(self, data): for callback in self.callbacks.itervalues(): callback() data.upcall()
for scene in scenes: if scene[0] == sceneToApply: print "Scene", sceneToApply, "found !" self.setLightsTo(scene[1],scene[2],scene[3],scene[4]) return True print "This scene doesn't exist" return False port = int(raw_input("Entrez le port d'ecoute : ")) tcpsock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) tcpsock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) tcpsock.bind(("127.0.0.1",port)) while True: tcpsock.listen(10) print( "En écoute...") if not scheduler: sunset = getSunsetTime().split(" ") task = [sunset[0],sunset[2],"lightsOn"] print "Creation of task :",task scheduler = Scheduler(port,"") scheduler.addTask(task) scheduler.addDailyTask("01:46","updateSunsetTask") scheduler.start() (clientsocket, (ip, port)) = tcpsock.accept() newthread = ClientThread(ip, port, clientsocket) newthread.start()