def restartWithCommands(commands, logger): """ Restart Lunchinator and execute commands in background while it is stopped. commands: lunchinator.commands.Commands instance """ from lunchinator import get_server try: # copy restart script to safe place shutil.copy(get_settings().get_resource("bin", "restart.py"), get_settings().get_main_config_dir()) startCmd = _getStartCommand(logger) args = [_getPythonInterpreter(), get_settings().get_config("restart.py"), "--lunchinator-path", get_settings().get_main_package_path(), "--start-cmd", json.dumps(startCmd), "--pid", str(os.getpid())] if commands != None: args.extend(["--commands", commands.toString()]) spawnProcess(args, logger) except: logger.exception("Error in restartWithCommands") return if get_server().getController() != None: get_server().getController().shutdown() else: sys.exit(0)
def changeNextLunchTime(self, begin = None, end = None): if begin == None: if self.mainWindow == None: getCoreLogger().error("mainWindow is not initialized") return from lunchinator.timespan_input_dialog import TimespanInputDialog dialog = TimespanInputDialog(self.mainWindow, "Change Lunch Time", "When are you free for lunch today?", get_settings().get_next_lunch_begin(), get_settings().get_next_lunch_end()) dialog.exec_() if dialog.result() == QDialog.Accepted: get_settings().set_next_lunch_time(dialog.getBeginTimeString(), dialog.getEndTimeString()) else: return else: get_settings().set_next_lunch_time(begin, end) if self.resetNextLunchTimeTimer != None: self.resetNextLunchTimeTimer.stop() self.resetNextLunchTimeTimer.deleteLater() td = get_settings().get_next_lunch_reset_time() if td > 0: self.resetNextLunchTimeTimer = QTimer(getValidQtParent()) self.resetNextLunchTimeTimer.timeout.connect(self._resetNextLunchTime) self.resetNextLunchTimeTimer.setSingleShot(True) self.resetNextLunchTimeTimer.start(abs(td) + 1000) get_server().call_info()
def __setLevel(self, loggerName, args): if len(args) == 0: self.printHelp(u"logging") return try: level = self.__getLoggingLevelFromText(args[0]) except ValueError: print "Invalid logging level:", args[0] if loggerName is None: if level is None: print "Invalid default logging level:", args[0] return if level == logging.DEBUG: get_settings().set_logging_level(u"DEBUG") elif level == logging.INFO: get_settings().set_logging_level(u"INFO") elif level == logging.WARNING: get_settings().set_logging_level(u"WARNING") elif level == logging.ERROR: get_settings().set_logging_level(u"ERROR") elif level == logging.CRITICAL: get_settings().set_logging_level(u"CRITICAL") else: setLoggingLevel(loggerName, level)
def __init__(self, parent): super(ErrorMessageDialog, self).__init__(parent) self._errorPixmap = None self._warningPixmap = None self._infoPixmap = None try: from PyQt4.QtGui import QCommonStyle, QStyle style = QCommonStyle() self._errorPixmap = style.standardIcon(QStyle.SP_MessageBoxCritical).pixmap(14,14) if self._errorPixmap.isNull(): self._errorPixmap = None self._warningPixmap = style.standardIcon(QStyle.SP_MessageBoxWarning).pixmap(14,14) if self._warningPixmap.isNull(): self._warningPixmap = None self._infoPixmap = style.standardIcon(QStyle.SP_MessageBoxInformation).pixmap(14,14) if self._infoPixmap.isNull(): self._infoPixmap = None except: pass if self._errorPixmap is None: self._errorPixmap = QIcon(get_settings().get_resource("images", "error.png")).pixmap(14,14) if self._warningPixmap is None: self._warningPixmap = QIcon(get_settings().get_resource("images", "warning.png")).pixmap(14,14) if self._infoPixmap is None: self._infoPixmap = QIcon(get_settings().get_resource("images", "warning.png")).pixmap(14,14) layout = QVBoxLayout(self) self._initInputUI(layout) self.__createBottomLayout(layout) self._initDone() size = self.sizeHint() self.setMaximumHeight(size.height())
def sendMessage(msg, cli): if msg == None: msg = "lunch" get_settings().set_plugins_enabled(False) recv_nr = get_server().perform_call(msg, peerIDs=[], peerIPs=[cli]) print "sent to", recv_nr, "clients"
def _init_plugin_objects(self): if len(self.conn_plugins)==0: self.conn_properties_lock.acquire() '''fill the only known property for now: the type of every connection and store the instance''' try: for conn_name in get_settings().get_available_db_connections(): section_name = "DB Connection: "+str(conn_name) plugin_type = self.STANDARD_PLUGIN plugin_type = get_settings().read_value_from_config_file(plugin_type, section_name, "plugin_type") p = self.plugin_manager.getPluginByName(plugin_type, "db") if p != None and p.plugin_object.is_activated: self.conn_plugins[conn_name] = p.plugin_object else: # TODO should this be a warning? self.logger.error("DB Connection %s requires plugin of type "\ "%s which is not available. \n Delete the connection from the Settings "\ "or install the DB plugin again.", conn_name, plugin_type) continue p_options = p.plugin_object.options.copy() for k,v in p_options.items(): '''this takes care of the option-type''' p_options[k] = get_settings().read_value_from_config_file(v, section_name, k) p_options["plugin_type"]=plugin_type self.conn_properties[conn_name] = p_options.copy() except: raise finally: self.conn_properties_lock.release()
def _setIcon(self, baseName): if baseName is None: self._button.setStyleSheet(""" QPushButton {min-width: 15px; max-width: 15px; min-height: 15px; max-height: 15px; margin: 0px; padding: 0px; border:none; } """) else: defPath = get_settings().get_resource("images", "%s32.png" % baseName) pressPath = get_settings().get_resource("images", "%s32p.png" % baseName) self._button.setStyleSheet(""" QPushButton {min-width: 15px; max-width: 15px; min-height: 15px; max-height: 15px; margin: 0px; padding: 0px; border:none; border-image: url(%s); } QPushButton:pressed { border-image: url(%s); } """ % (defPath, pressPath) )
def serverStopped(self, _exit_code): get_settings().write_config_to_hd() if get_settings().get_plugins_enabled(): get_plugin_manager().deactivatePlugins(get_plugin_manager().getAllPlugins(), save_state=False) get_notification_center().disconnectPluginActivated(self._checkSendInfoDict) get_notification_center().disconnectPluginDeactivated(self._checkSendInfoDict) get_notification_center().finish() DataReceiverThread.cleanup()
def setCustomPeerName(self, peerID, customName): """This method might occasionally raise an exception""" if self.isMe(pID=peerID): # special case: it doesn't make sense to use the custom name for myself get_settings().set_user_name(customName) else: with self._lock: infoDict = self.getPeerInfo(pID=peerID, lock=False) self._peerNames.setCustomName(peerID, customName, infoDict)
def _initLayout(self): layout = QVBoxLayout(self) layout.setContentsMargins(5, 5, 5, 5) layout.setSpacing(0) nameLayout = QHBoxLayout() nameLayout.setContentsMargins(0, 0, 0, 0) self._fileIconLabel = QLabel(self) nameLayout.addWidget(self._fileIconLabel, 0, Qt.AlignLeft) self._nameLabel = QLabel(self) nameLayout.addSpacing(5) nameLayout.addWidget(self._nameLabel, 1, Qt.AlignLeft) layout.addLayout(nameLayout) progressWidget = QWidget(self) progressLayout = QHBoxLayout(progressWidget) progressLayout.setSpacing(5) progressLayout.setContentsMargins(0, 0, 0, 0) iconLabel = QLabel(progressWidget) if self._down: picFile = get_settings().get_resource("images", "down.png") else: picFile = get_settings().get_resource("images", "up.png") iconLabel.setPixmap(QPixmap(picFile)) iconLabel.setFixedSize(15,15) progressLayout.addWidget(iconLabel, 0, Qt.AlignBottom) self._progress = QProgressBar(progressWidget) self._progress.setMinimum(0) self._progress.setMaximum(100) if getPlatform() == PLATFORM_MAC: self._progress.setAttribute(Qt.WA_MacMiniSize) self._progress.setMaximumHeight(16) progressLayout.addWidget(self._progress, 1) self._button = QPushButton(progressWidget) self._button.clicked.connect(self._buttonClicked) progressLayout.addSpacing(5) progressLayout.addWidget(self._button, 0, Qt.AlignCenter) layout.addWidget(progressWidget, 0, Qt.AlignBottom) self._statusLabel = QLabel(self) if getPlatform() == PLATFORM_MAC: self._statusLabel.setAttribute(Qt.WA_MacSmallSize) layout.addWidget(self._statusLabel) self.setObjectName(u"__transfer_widget") self.setFrameShape(QFrame.StyledPanel) self.setStyleSheet("QFrame#__transfer_widget{border-width: 1px; border-top-style: none; border-right-style: none; border-bottom-style: solid; border-left-style: none; border-color:palette(mid)}"); self.setSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.Fixed)
def __init__(self, controller): super(LunchinatorWindow, self).__init__(None) self.guiHandler = controller self.setWindowTitle("Lunchinator") self.setWindowIcon(QIcon(get_settings().get_resource("images", "lunchinator.png"))) self.setDockNestingEnabled(True) self.setTabPosition(Qt.AllDockWidgetAreas, QTabWidget.North) self.pluginNameToDockWidget = {} self.objectNameToPluginName = {} self.pluginNameToMenus = {} self.settings = QSettings(get_settings().get_config("gui_settings.ini"), QSettings.IniFormat) savedGeometry = self.settings.value("geometry", None) savedState = self.settings.value("state", None) self.locked = self.settings.value("locked", QVariant(False)).toBool() self._prepareMenuBar() if savedState == None: # first run, create initial state get_plugin_manager().activatePluginByName(u"Simple View", "gui") get_plugin_manager().activatePluginByName(u"Auto Update", "general") # add plugins try: if get_settings().get_plugins_enabled(): for pluginInfo in get_plugin_manager().getPluginsOfCategory("gui"): if pluginInfo.plugin_object.is_activated: self.addPluginWidget(pluginInfo.plugin_object, pluginInfo.name, noTabs=True) except: getCoreLogger().exception("while including plugins %s", str(sys.exc_info())) if savedGeometry != None: self.restoreGeometry(savedGeometry.toByteArray()) else: self.centerOnScreen() if savedState != None: self.restoreState(savedState.toByteArray()) get_notification_center().connectPluginActivated(self._pluginActivated) get_notification_center().connectPluginWillBeDeactivated(self._pluginWillBeDeactivated) if len(self.pluginNameToDockWidget) == 0 and get_settings().get_plugins_enabled(): # no gui plugins activated, show about plugins get_plugin_manager().activatePluginByName(u"About Plugins", "gui") if self.locked: self.lockDockWidgets() # prevent from closing twice self.closed = False
def get_supported_connections(self): from lunchinator import get_settings if not self._supported_dbms or u"default" in self._supported_dbms: return get_settings().get_available_db_connections() conns = [] for connName in get_settings().get_available_db_connections(): connType = get_connection_type(self.logger, connName) if connType in self._supported_dbms: conns.append(connName) return conns
def save_options_widget_data(self, **_kwargs): from PyQt4.QtCore import Qt from logging_level_settings.logging_level_gui import LogLevelModel get_settings().set_logging_level(self._ui.getGlobalLevelText()) model = self._ui.getModel() for row in xrange(model.rowCount()): loggerName = convert_string(model.item(row, LogLevelModel.NAME_COLUMN).data(LogLevelModel.KEY_ROLE).toString()) levelText = convert_string(model.item(row, LogLevelModel.LEVEL_COLUMN).data(Qt.DisplayRole).toString()) level = self._getLevelFromText(levelText) setLoggingLevel(loggerName, level)
def use_as_avatar(self, file_path): if not os.path.exists(file_path): self.logger.error("no image found at %s, exiting", file_path) return tmpPath = os.path.join(get_settings().get_avatar_dir(), "tmp.png") self.scale_image(file_path, tmpPath) avatar_name = unicode(self.md5_for_file(file_path) + ".png") shutil.move(tmpPath, os.path.join(get_settings().get_avatar_dir(), avatar_name)) get_settings().set_avatar_file(avatar_name) return os.path.join(get_settings().get_avatar_dir(), avatar_name)
def audioFileChanged(self,_setting,new_value): audio_file=self.options[u"audio_file"] if os.path.exists(new_value): audio_file = new_value elif os.path.exists(get_settings().get_main_config_dir()+"/sounds/"+new_value): audio_file= get_settings().get_main_config_dir()+"/sounds/"+new_value else: try: # get_resource will raise if the resource does not exist. audio_file = get_settings().get_resource("sounds", new_value) except: self.logger.warning("configured audio file %s does not exist in sounds folder, using old one", new_value) # don't set the new value, keep old value return audio_file
def __init__(self, peers): self._s = None try: self._s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) except: self._s = None raise self._peers = peers self._port = get_settings().get_udp_port() self._max_msg_length = get_settings().get_max_fragment_length() self._incomplete_messages = {} self._incMsgLock = loggingMutex("dropIncompleteMsg", logging=get_settings().get_verbose())
def __init__(self): super(db_connections, self).__init__() self.plugin_manager = get_plugin_manager() self.conn_properties_lock = loggingMutex("db_conn_properties", logging=get_settings().get_verbose()) self.open_connections = {} self.conn_properties = {} self.conn_plugins = {} #will be filled later (init plugin obejcts) self.options = [(("default_connection","Default Connection", self.conn_properties.keys(), get_settings().set_default_db_connection), get_settings().get_default_db_connection())] self.force_activation = True
def getDBConnection(self, logger, name=""): """returns tuple (connection_handle, connection_type) of the given connection""" if len(name)==0: name = get_settings().get_default_db_connection() if name not in get_settings().get_available_db_connections(): return None, None ob, props = self.getProperties(name) if name not in self.open_connections: self.logger.debug("DB Connections: opening connection %s of type %s", name, props["plugin_type"]) self.open_connections[name] = ob.create_connection(props) return _LoggerWrapper(self.open_connections[name], logger), props["plugin_type"]
def _writePeersToFile(self): try: with self._lock: for ip in self._peer_info: try: hostname = socket.gethostbyaddr(ip)[0] except: hostname = ip self._potentialPeers.add(hostname) with codecs.open(get_settings().get_peers_file(), "w", "utf-8") as f: f.truncate() f.write(u"\n".join(sorted(self._potentialPeers))) except: self.logger.exception("Could not write peers to %s", get_settings().get_peers_file())
def settingsDialogAction(self, saved): if not get_settings().get_plugins_enabled(): return for pluginInfo in get_plugin_manager().getAllPlugins(): if pluginInfo.plugin_object.is_activated and self.settingsWindow.isOptionsWidgetLoaded(pluginInfo.name): if saved: try: pluginInfo.plugin_object.save_options_widget_data(sendInfoDict=False) except: getCoreLogger().exception("was not able to save data for plugin %s", pluginInfo.name) else: pluginInfo.plugin_object.discard_changes() get_settings().write_config_to_hd() get_server().call_info()
def process_event(self, cmd, value, ip, peerInfo, _prep): if cmd.startswith("HELO_LOGFILE"): if self.w == None: return from lunchinator.datathread.dt_qthread import DataReceiverThread #someone will send me his logfile on tcp values = value.split() file_size=int(values[0]) tcp_port = 0 if len(values) > 1: tcp_port = int(values[1]) pID = peerInfo.get(LunchPeers.PEER_ID_KEY, ip) logDir = os.path.join(get_settings().get_main_config_dir(), "logs", pID) if not os.path.exists(logDir): os.makedirs(logDir) if cmd.startswith("HELO_LOGFILE_TGZ"): file_name= os.path.join(logDir, "tmp.tgz") else: file_name= os.path.join(logDir, "tmp.log") dr = DataReceiverThread.receiveSingleFile(ip, file_name, file_size, tcp_port, self.logger, "log%s"%ip, parent=self.w) dr.successfullyTransferred.connect(self.w.membersWidget.cb_log_transfer_success) dr.errorOnTransfer.connect(self.w.membersWidget.cb_log_transfer_error) dr.finished.connect(dr.deleteLater) dr.start()
def _prepareInstallation(self, localFile, commands): path = getApplicationBundle() if path == None: self._setStatus("Could not find application bundle. Cannot update.", True) else: installer = get_settings().get_resource("bin", "mac_installer.sh") commands.addShellCommand([installer, localFile, path, str(os.getpid())])
def listLogFilesForMember(self, member): if member is None: return [] logDir = os.path.join(get_settings().get_main_config_dir(), "logs", member) if not os.path.exists(logDir): return [] return self.listLogfiles(logDir)
def __init__(self): cmd.Cmd.__init__(self) LunchServerController.__init__(self) self.logger = newLogger("cli") self.prompt = "> " self.commands = set(["exit"]) self.addModule(CLIMessageHandling()) self.addModule(CLIOptionHandling()) self.addModule(CLIPluginHandling(self)) self.addModule(CLIPrivacyHandling()) self.addModule(CLILoggingHandling()) get_server().initialize(self) if get_settings().get_plugins_enabled(): for pluginInfo in get_plugin_manager().getAllPlugins(): if pluginInfo.plugin_object.is_activated: self.addModule(pluginInfo.plugin_object) get_notification_center().connectApplicationUpdate(self.notifyUpdates) self.exitCode = 0 # if serverStopped is called, we can determine if it was a regular exit. self.cleanExit = False self.initialized = False
def _loadIndex(self): try: self.settings = QSettings(get_settings().get_config("remote_pictures", "index"), QSettings.NativeFormat) storedThumbnails = self.settings.value("categoryThumbnails", None) if storedThumbnails != None: storedThumbnails = storedThumbnails.toMap() for aCat in storedThumbnails: thumbnailPath = convert_string(storedThumbnails[aCat].toString()) aCat = convert_string(aCat) if aCat == u"Not Categorized": aCat = PrivacySettings.NO_CATEGORY self._addCategory(aCat, thumbnailPath) categoryPictures = self.settings.value("categoryPictures", None) if categoryPictures != None: tmpDict = categoryPictures.toMap() added = time() for aCat in tmpDict: newKey = convert_string(aCat) if newKey == u"Not Categorized": newKey = PrivacySettings.NO_CATEGORY picTupleList = tmpDict[aCat].toList() for picTuple in picTupleList: tupleList = picTuple.toList() picURL = convert_string(tupleList[0].toString()) picDesc = convert_string(tupleList[1].toString()) self.addPicture(newKey, picURL, picDesc, None, added, None, None) if not picDesc: picDesc = None except: self.logger.exception("Could not load thumbnail index.")
def request_avatar(self, ip): info = self._peers.getPeerInfo(pIP=ip) if info and u"avatar" in info and not os.path.exists(os.path.join(get_settings().get_avatar_dir(), info[u"avatar"])): openPort = self.controller.getOpenPort(ip) self.call("HELO_REQUEST_AVATAR " + str(openPort), peerIPs=[ip]) return True return False
def testMemberRemovalLock(self): get_notification_center().connectMemberRemoved(self.connect_testMemberRemovalLock) print "Removing myself as Member" mIPs = get_peers().getPeerIPs(get_settings().get_ID()) print "Using IPs:", mIPs get_peers().removeMembersByIP(mIPs)
def setOtherIconPath(self, iconPath): if not iconPath: iconPath = get_settings().get_resource("images", "lunchinator.png") self._otherIconPath = iconPath self._otherIcon = QIcon(iconPath) self._otherPicLabel.setPixmap(QPixmap(self._otherIconPath).scaled(24,24, Qt.KeepAspectRatio, Qt.SmoothTransformation)) self._model.setOtherIcon(self._otherIcon)
def _resendUndeliveredMessages(self, curTime, partner=None, force=False): if not partner and not self._hasUndelivered: return undelivered = self._getStorage().getRecentUndeliveredMessages(partner) if not partner and not undelivered: self._hasUndelivered=False for msgTuple in undelivered: msgTime = msgTuple[ChatMessagesStorage.MSG_TIME_COL] if not force: timeout = int(curTime - msgTime) if timeout > get_settings().get_peer_timeout(): continue msgID = msgTuple[ChatMessagesStorage.MSG_ID_COL] if msgID in self._waitingForAck: # already resent and waiting for ACK continue # check if partner is online otherID = msgTuple[ChatMessagesStorage.MSG_PARTNER_COL] if get_peers().isPeerID(pID=otherID): self.logger.debug("Resending undelivered message %d to peer '%s'", msgID, otherID) # partner is online, resend message msgHTML = msgTuple[ChatMessagesStorage.MSG_TEXT_COL] self.sendMessage(otherID, msgHTML, msgID, msgTime)
def __init__(self, logging): self.logger = newLogger("Core Messages") self._lock = loggingMutex("messages", logging=logging) self._db, plugin_type = get_db_connection(self.logger) if self._db is None: self._length = 0 self._latest = None return if plugin_type != "SQLite Connection": self.logger.warning("Your standard connection is not of type SQLite." + \ "Loading messages from another type is experimental.") if not self._db.existsTable("CORE_MESSAGE_VERSION"): self._db.execute("CREATE TABLE CORE_MESSAGE_VERSION(VERSION INTEGER)") self._db.execute("INSERT INTO CORE_MESSAGE_VERSION(VERSION) VALUES(?)", self._DB_VERSION_CURRENT) if not self._db.existsTable("CORE_MESSAGES"): self._db.execute("CREATE TABLE CORE_MESSAGES(SENDER TEXT, TIME REAL, MESSAGE TEXT)") self._db.execute("CREATE INDEX CORE_MESSAGE_TIME_INDEX on CORE_MESSAGES(TIME ASC)") self._length = 0 self._latest = None self.importOld(get_settings().get_legacy_messages_file()) else: self._latest = self._getLatest() self._length = self._getNumMessages()
def __init__(self): super(raspicam, self).__init__() self.options = [(("picture_path", "Folder where pics are stored"), os.path.join(get_settings().get_main_config_dir(),"raspicam")), (("http_server", "start http server to enable remote pics"), True), (("http_hostname", "hostname/IP of this lunchinator"), socket.getfqdn()), (("http_port", "Port where pictures can be accessed"), 5000)] self.s_thread = None