def __init__(self): try: global MySQLdb import MySQLdb except ImportError: logger.warn("The MySQLdb module is missing. Install this " \ "module to enable MySQL. Reverting to SQLite.") cherrystrap.DATABASE_TYPE = "sqlite" host = cherrystrap.MYSQL_HOST port = cherrystrap.MYSQL_PORT if port: try: port = int(cherrystrap.MYSQL_PORT) except: port = 3306 logger.error("The port number supplied is not an integer") else: port = 3306 if not host: host = 'localhost' user = cherrystrap.MYSQL_USER passwd = formatter.decode('obscure', cherrystrap.MYSQL_PASS) self.connection = MySQLdb.Connection(host=host, port=port, user=user, passwd=passwd, db=cherrystrap.APP_NAME, charset='utf8', use_unicode=True)
def ajaxMSG(status, status_msg): if status == 'success': logger.info(status_msg) elif status == 'failure': logger.warn(status_msg) return status, status_msg
def action(self, query, args=None): with db_lock: if query == None: return sqlResult = None attempt = 0 while attempt < 5: try: if args == None: #logger.debug(self.filename+": "+query) sqlResult = self.connection.execute(query) else: #logger.debug(self.filename+": "+query+" with args "+str(args)) sqlResult = self.connection.execute(query, args) self.connection.commit() break except sqlite3.OperationalError, e: if "unable to open database file" in e.message or "database is locked" in e.message: logger.warn('Database Error: %s' % e) attempt += 1 time.sleep(1) else: logger.error('Database error: %s' % e) raise except sqlite3.DatabaseError, e: logger.error('Fatal error executing %s :: %s' % (query, e)) raise
def action(self, query, args=None): with db_lock: if query == None: return sqlResult = None attempt = 0 while attempt < 5: try: if args == None: sqlResult = self.connection.execute(query) else: sqlResult = self.connection.execute(query, args) self.connection.commit() break except sqlite3.OperationalError, e: if "unable to open database file" in e.message or "database is locked" in e.message: logger.warn('Database Error: %s' % e) attempt += 1 time.sleep(1) else: logger.error('Database error: %s' % e) raise except sqlite3.DatabaseError, e: logger.error('Fatal error executing %s :: %s' % (query, e)) raise
def __init__(self): try: global MySQLdb import MySQLdb except ImportError: logger.warn("The MySQLdb module is missing. Install this " \ "module to enable MySQL. Reverting to SQLite.") cherrystrap.DATABASE_TYPE = "sqlite" host = cherrystrap.MYSQL_HOST port = cherrystrap.MYSQL_PORT if port: try: port = int(cherrystrap.MYSQL_PORT) except: port = 3306 logger.error("The port number supplied is not an integer") else: port = 3306 if not host: host = 'localhost' user = cherrystrap.MYSQL_USER passwd = formatter.decode('obscure', cherrystrap.MYSQL_PASS) self.connection = MySQLdb.Connection(host=host, port=port, user=user, passwd=passwd, charset='utf8', use_unicode=True)
def messaging(message_rule=None, custom_message=None, notify_msg=None, notify=False, health_list=None): if message_rule == "Send Custom Message": notify_msg = custom_message else: notify_msg = notify_msg if notify: notifiers.notify_health(formatter.now()+": "+notify_msg) logger.warn("%s" % notify_msg) health_array = collections.defaultdict() health_array['warning'] = notify_msg health_list.append(health_array)
def checkGithub(): cherrystrap.COMMITS_BEHIND = 0 # Get the latest version available from github logger.info('Retrieving latest version information from GitHub') url = 'https://api.github.com/repos/%s/%s/commits/%s' % (cherrystrap.GIT_USER, cherrystrap.GIT_REPO, cherrystrap.GIT_BRANCH) try: result = urllib2.urlopen(url).read() version = json.JSONDecoder().decode(result) except Exception, e: logger.warn('Could not get the latest version from GitHub. Are you running a local development version?: %s' % e) return cherrystrap.GIT_LOCAL
def sign(self, request, consumer, token): """Builds the base signature string.""" key, raw = self.signing_base(request, consumer, token) try: with open(jiraappy.RSA_PRIVATE_KEY, 'r') as f: data = f.read() privateKeyString = data.strip() privatekey = keyfactory.parsePrivateKey(privateKeyString) signature = str(privatekey.hashAndSign(raw)) return base64.b64encode(signature) except: logger.warn('Private Key File not found on server at location %s' % jiraappy.RSA_PRIVATE_KEY)
def check_setting_str(config, cfg_name, item_name, def_val): try: my_val = str(config[cfg_name][item_name]) except: my_val = def_val try: config[cfg_name][item_name] = ast.literal_eval(my_val) logger.warn("Bad value for %s in config.ini. Reverting to default" % item_name) except: config[cfg_name] = {} config[cfg_name][item_name] = my_val logger.error("Bad default value for %s. Application may break" % item_name) logger.debug(item_name + " -> " + str(my_val)) return my_val
def signing_base(self, request, consumer, token): if not hasattr(request, 'normalized_url') or request.normalized_url is None: logger.warn("Base URL for request is not set.") sig = ( oauth.escape(request.method), oauth.escape(request.normalized_url), oauth.escape(request.get_normalized_parameters()), ) key = '%s&' % oauth.escape(consumer.secret) if token: key += oauth.escape(token.secret) raw = '&'.join(sig) return key, raw
def createDb(DATABASE_TYPE, DATADIR, APP_NAME, MYSQL_HOST, MYSQL_PORT, MYSQL_USER, MYSQL_PASS): # User should have a choice between sqlite and mysql if DATABASE_TYPE == "sqlite": try: import sqlite3 except Exception, e: logger.warn("SQLite is not installed: %s" % e) try: DBFILE = os.path.join(DATADIR, '%s.db' % APP_NAME) conn = sqlite3.connect(DBFILE) c = conn.cursor() except Exception, e: logger.warn("Could not connect to SQLite database: %s" % e)
def check_oauth(): consumer = oauth.Consumer(jiraappy.CONSUMER_KEY, jiraappy.CONSUMER_SECRET) accessToken = oauth.Token(jiraappy.JIRA_OAUTH_TOKEN, jiraappy.JIRA_OAUTH_SECRET) client = oauth.Client(consumer, accessToken) client.set_signature_method(SignatureMethod_RSA_SHA1()) data_url = os.path.join(jiraappy.JIRA_BASE_URL, 'rest/api/2/myself') resp, content = client.request(data_url, "GET") if resp['status'] != '200': jiraappy.JIRA_LOGIN_STATUS = None jiraappy.JIRA_LOGIN_USER = None logger.warn("OAuth credentials missing or invalid") else: resp_dict = json.loads(content) jiraappy.JIRA_LOGIN_STATUS = True jiraappy.JIRA_LOGIN_USER = resp_dict['name'] logger.info("JIRA user %s verified login" % resp_dict['name'])
def bulkDeleteWorklogs(issue_list=None): status, msg = '', '' consumer, client = backend.stored_oauth() num_issues = 0 num_worklogs = 0 for issue in issue_list: num_issues += 1 data_url = os.path.join(jiraappy.JIRA_BASE_URL, 'rest/api/2/issue/' + issue + '/worklog') try: resp, content = client.request(data_url, "GET") if resp['status'] != '200': logger.warn("Request for %s failed with status code %s - %s" ( data_url, resp['status'], content)) else: resp_dict = json.loads(content) num_results = resp_dict['total'] if num_results != 0: for result in range(0, num_results): worklog_id = resp_dict['worklogs'][result]['id'] data_url = os.path.join( jiraappy.JIRA_BASE_URL, 'rest/api/2/issue/' + issue + '/worklog/' + worklog_id + '?adjustEstimate=leave') try: resp, content = client.request(data_url, "DELETE") if resp['status'] != '204': logger.warn( "Request for %s failed with status code %s - %s" ( data_url, resp['status'], content)) else: num_worklogs += 1 logger.info( "Worklog ID %s for issue %s has been deleted" % (worklog_id, issue)) except: logger.warn("Could not connect to %s" % data_url) status, msg = backend.ajaxMSG( 'success', '%d worklog(s) have been deleted for %d issues' % (num_worklogs, num_issues)) else: logger.info("No worklogs found for issue %s" % issue) except: logger.warn("Could not connect to %s" % data_url) return status, msg
def bulkDeleteWorklogs(issue_list=None): status, msg = '', '' consumer, client = backend.stored_oauth() num_issues = 0 num_worklogs = 0 for issue in issue_list: num_issues+=1 data_url = os.path.join(jiraappy.JIRA_BASE_URL, 'rest/api/2/issue/'+issue+'/worklog') try: resp, content = client.request(data_url, "GET") if resp['status'] != '200': logger.warn("Request for %s failed with status code %s - %s" (data_url, resp['status'], content)) else: resp_dict = json.loads(content) num_results = resp_dict['total'] if num_results != 0: for result in range(0, num_results): worklog_id = resp_dict['worklogs'][result]['id'] data_url = os.path.join(jiraappy.JIRA_BASE_URL, 'rest/api/2/issue/'+issue+'/worklog/'+worklog_id+'?adjustEstimate=leave') try: resp, content = client.request(data_url, "DELETE") if resp['status'] != '204': logger.warn("Request for %s failed with status code %s - %s" (data_url, resp['status'], content)) else: num_worklogs+=1 logger.info("Worklog ID %s for issue %s has been deleted" % (worklog_id, issue)) except: logger.warn("Could not connect to %s" % data_url) status, msg = backend.ajaxMSG('success', '%d worklog(s) have been deleted for %d issues' % (num_worklogs, num_issues)) else: logger.info("No worklogs found for issue %s" % issue) except: logger.warn("Could not connect to %s" % data_url) return status, msg
kwargs, errorList = injectApiConfigPut(kwargs, errorList) except Exception, e: logger.debug("There was a problem injection application variables into API-PUT: %s" % e) #================================================================ if len(kwargs) != 0: for key, value in kwargs.items(): errorList.append("Key %s not expected" % key) cherrystrap.config_write() if not errorList: logger.info("All configuration settings successfully updated") return "{\"status\": \"success\", \ \"message\": \"All configuration settings successfully updated\"}" else: logger.warn("The following error(s) occurred while attempting to update settings: %s" % errorList) return "{\"status\": \"warning\", \ \"message\": \"The following error(s) occurred while attempting to update settings: %s\"}" % errorList def DELETE(self, token=None): if token != cherrystrap.API_TOKEN: return "{\"status\": \"error\", \"message\": \"Invalid Token\"}" return "{\"status\": \"error\", \"message\": \"DELETE not available at this endpoint\"}" class log(object): exposed = True def GET(self, token=None, draw=1, start=0, length=100, **kwargs): if token != cherrystrap.API_TOKEN: return "{\"status\": \"error\", \"message\": \"Invalid Token\"}"
def initialize(options={}): https_enabled = options['https_enabled'] https_cert = options['https_cert'] https_key = options['https_key'] if https_enabled: # If either the HTTPS certificate or key do not exist, try to make # self-signed ones. if not (https_cert and os.path.exists(https_cert)) or not (https_key and os.path.exists(https_key)): if not create_https_certificates(https_cert, https_key): logger.warn("Unable to create certificate and key. Disabling " \ "HTTPS") https_enabled = False if not (os.path.exists(https_cert) and os.path.exists(https_key)): logger.warn("Disabled HTTPS because of missing certificate and " \ "key.") https_enabled = False options_dict = { 'log.screen': False, 'server.thread_pool': 10, 'server.socket_port': int(options['http_port']), 'server.socket_host': str(options['http_host']), 'engine.autoreload.on': False, } if https_enabled: options_dict['server.ssl_certificate'] = https_cert options_dict['server.ssl_private_key'] = https_key protocol = "https" else: protocol = "http" logger.info("Starting %s on %s://%s:%d/" % (cherrystrap.APP_NAME, protocol, options['http_host'], options['http_port'])) cherrypy.config.update(options_dict) webConf = { '/': { 'tools.staticdir.root': os.path.join(cherrystrap.PROG_DIR, 'static') }, '/interfaces':{ 'tools.staticdir.on': True, 'tools.staticdir.dir': "interfaces" }, '/images':{ 'tools.staticdir.on': True, 'tools.staticdir.dir': "images" }, '/css':{ 'tools.staticdir.on': True, 'tools.staticdir.dir': "css" }, '/js':{ 'tools.staticdir.on': True, 'tools.staticdir.dir': "js" }, '/fonts':{ 'tools.staticdir.on': True, 'tools.staticdir.dir': "fonts" }, '/favicon.ico':{ 'tools.staticfile.on': True, 'tools.staticfile.filename': os.path.join(cherrystrap.PROG_DIR, 'static/images/favicon.ico') } } # Prevent time-outs cherrypy.engine.timeout_monitor.unsubscribe() cherrypy.tree.mount(WebInterface(), options['http_root'], config = webConf) # Load API endpoints cherrypy.tree.mount(apiServe.settings(), cherrystrap.HTTP_ROOT+'/api/v1/settings', {'/': {'request.dispatch': cherrypy.dispatch.MethodDispatcher()}}) cherrypy.tree.mount(apiServe.log(), cherrystrap.HTTP_ROOT+'/api/v1/log', {'/': {'request.dispatch': cherrypy.dispatch.MethodDispatcher()}}) cherrypy.engine.autoreload.subscribe() try: cherrypy.process.servers.check_port(options['http_host'], options['http_port']) cherrypy.server.start() #cherrypy.engine.start() is good for dev mode, but breaks --daemon except IOError: print 'Failed to start on port: %i. Is something else running?' % (options['http_port']) sys.exit(0) cherrypy.server.wait()
def main(): # rename this thread threading.currentThread().name = "MAIN" # Set paths if hasattr(sys, 'frozen'): cherrystrap.FULL_PATH = os.path.abspath(sys.executable) else: cherrystrap.FULL_PATH = os.path.abspath(__file__) cherrystrap.PROG_DIR = os.path.dirname(cherrystrap.FULL_PATH) cherrystrap.ARGS = sys.argv[1:] cherrystrap.SYS_ENCODING = None try: locale.setlocale(locale.LC_ALL, "") cherrystrap.SYS_ENCODING = locale.getpreferredencoding() except (locale.Error, IOError): pass # for OSes that are poorly configured I'll just force UTF-8 if not cherrystrap.SYS_ENCODING or cherrystrap.SYS_ENCODING in ('ANSI_X3.4-1968', 'US-ASCII', 'ASCII'): cherrystrap.SYS_ENCODING = 'UTF-8' # Set arguments from optparse import OptionParser p = OptionParser() p.add_option('-d', '--daemon', action = "store_true", dest = 'daemon', help = "Run the server as a daemon") p.add_option('-q', '--quiet', action = "store_true", dest = 'quiet', help = "Don't log to console") p.add_option('--debug', action="store_true", dest = 'debug', help = "Show debuglog messages") p.add_option('--nolaunch', action = "store_true", dest = 'nolaunch', help="Don't start browser") p.add_option('--port', dest = 'port', default = None, help = "Force webinterface to listen on this port") p.add_option('--datadir', dest = 'datadir', default = None, help = "Path to the data directory") p.add_option('--config', dest = 'config', default = None, help = "Path to config.ini file") p.add_option('-p', '--pidfile', dest = 'pidfile', default = None, help = "Store the process id in the given file") options, args = p.parse_args() if options.debug: cherrystrap.LOGLEVEL = 2 if options.quiet: cherrystrap.LOGLEVEL = 0 if options.daemon: if not sys.platform == 'win32': cherrystrap.DAEMON = True cherrystrap.LOGLEVEL = 0 cherrystrap.daemonize() else: print "Daemonize not supported under Windows, starting normally" if options.nolaunch: cherrystrap.LAUNCH_BROWSER = False if options.datadir: cherrystrap.DATADIR = str(options.datadir) else: cherrystrap.DATADIR = cherrystrap.PROG_DIR if options.config: cherrystrap.CONFIGFILE = str(options.config) else: cherrystrap.CONFIGFILE = os.path.join(cherrystrap.DATADIR, "config.ini") if options.pidfile: if cherrystrap.DAEMON: cherrystrap.PIDFILE = str(options.pidfile) # create and check (optional) paths if not os.path.exists(cherrystrap.DATADIR): try: os.makedirs(cherrystrap.DATADIR) except OSError: raise SystemExit('Could not create data directory: ' + cherrystrap.DATADIR + '. Exit ...') if not os.access(cherrystrap.DATADIR, os.W_OK): raise SystemExit('Cannot write to the data directory: ' + cherrystrap.DATADIR + '. Exit ...') # import config cherrystrap.CFG = ConfigObj(cherrystrap.CONFIGFILE, encoding='utf-8') cherrystrap.initialize() if options.port: HTTP_PORT = int(options.port) logger.info('Starting cherrystrap on forced port: %s' % HTTP_PORT) else: HTTP_PORT = int(cherrystrap.HTTP_PORT) if cherrystrap.DAEMON: cherrystrap.daemonize() # Check if pyOpenSSL is installed. It is required for certificate generation # and for CherryPy. if cherrystrap.HTTPS_ENABLED: try: import OpenSSL except ImportError: logger.warn("The pyOpenSSL module is missing. Install this " \ "module to enable HTTPS. HTTPS will be disabled.") cherrystrap.HTTPS_ENABLED = False # Try to start the server. webStart.initialize({ 'httpPort': HTTP_PORT, 'httpHost': cherrystrap.HTTP_HOST, 'httpRoot': cherrystrap.HTTP_ROOT, 'httpUser': cherrystrap.HTTP_USER, 'httpPass': cherrystrap.HTTP_PASS, 'sslEnabled': cherrystrap.HTTPS_ENABLED, 'sslKey': cherrystrap.HTTPS_KEY, 'sslCert': cherrystrap.HTTPS_CERT, 'sslVerify': cherrystrap.VERIFY_SSL }) if cherrystrap.LAUNCH_BROWSER and not options.nolaunch: cherrystrap.launch_browser(cherrystrap.HTTP_HOST, cherrystrap.HTTP_PORT, cherrystrap.HTTP_ROOT) cherrystrap.start() while True: if not cherrystrap.SIGNAL: try: time.sleep(1) except KeyboardInterrupt: cherrystrap.shutdown() else: if cherrystrap.SIGNAL == 'shutdown': cherrystrap.shutdown() elif cherrystrap.SIGNAL == 'restart': cherrystrap.shutdown(restart=True) else: cherrystrap.shutdown(restart=True, update=True) cherrystrap.SIGNAL = None return
# Initialize the database try: createDb(DATABASE_TYPE, DATADIR, APP_NAME, MYSQL_HOST, MYSQL_PORT, MYSQL_USER, MYSQL_PASS) except Exception, e: logger.error("Error initializing the database: %s" % e) # Disable SSL verification for systems where SSL is broken if not VERIFY_SSL: try: import ssl ssl._create_default_https_context = ssl._create_unverified_context logger.info("SSL verification disabled per user preferences") except Exception, e: logger.warn( "There was an error disabling SSL verification: %s" % s) pass # Get the currently installed version. Returns None, 'win32' or the git # hash. GIT_LOCAL, GIT_BRANCH = versioncheck.getVersion() # Write current version to a file, so we know which version did work. # This allows one to restore to that version. The idea is that if we # arrive here, most parts of the app seem to work. if GIT_LOCAL: version_lock_file = os.path.join(DATADIR, "version.lock") try: with open(version_lock_file, "w") as fp: fp.write(GIT_LOCAL)
#=============================================================== # Import a schema injection system per your app's __init__.py try: from jiraappy import injectDbSchema injection = injectDbSchema() for table, schema in injection.items(): c.execute('CREATE TABLE IF NOT EXISTS %s (id INTEGER PRIMARY KEY)' % table) for columnName, columnFormat in schema.items(): try: c.execute('SELECT %s from %s' % (columnName, table)) except sqlite3.OperationalError: c.execute('ALTER TABLE %s ADD COLUMN %s %s' % (table, columnName, columnFormat)) logger.info('Column %s created in table %s' % (columnName, table)) except Exception, e: logger.warn("There was a problem initializing SQLite database schema: %s" % e) #=============================================================== conn.commit() c.close() elif DATABASE_TYPE == "mysql": try: import MySQLdb filterwarnings('ignore', category = MySQLdb.Warning) except ImportError: logger.warn("The MySQLdb module is missing. Install this " \ "module to enable MySQL. Please revert to SQLite.") try: conn_ini = MySQLdb.Connection(host=MYSQL_HOST, port=MYSQL_PORT,
# See how many commits behind we are if not cherrystrap.GIT_LOCAL: logger.info('You are running an unknown version of %s. Run the updater to identify your version' % cherrystrap.APP_NAME) return cherrystrap.GIT_UPSTREAM if cherrystrap.GIT_UPSTREAM == cherrystrap.GIT_LOCAL: logger.info('%s is up to date' % cherrystrap.APP_NAME) return cherrystrap.GIT_UPSTREAM logger.info('Comparing currently installed version with latest GitHub version') url = 'https://api.github.com/repos/%s/%s/compare/%s...%s' % (cherrystrap.GIT_USER, cherrystrap.GIT_REPO, cherrystrap.GIT_UPSTREAM, cherrystrap.GIT_LOCAL) try: result = urllib2.urlopen(url).read() commits = json.JSONDecoder().decode(result) except: logger.warn('Could not get commits behind from GitHub.') return cherrystrap.GIT_UPSTREAM try: cherrystrap.COMMITS_BEHIND = int(commits['behind_by']) logger.debug("In total, %d commits behind" % cherrystrap.COMMITS_BEHIND) except KeyError: logger.info('Cannot compare versions. Are you running a local development version?') cherrystrap.COMMITS_BEHIND = 0 if cherrystrap.COMMITS_BEHIND > 0: logger.info('New version is available. You are %s commits behind' % cherrystrap.COMMITS_BEHIND) elif cherrystrap.COMMITS_BEHIND == 0: logger.info('%s is up to date' % cherrystrap.APP_NAME) return cherrystrap.GIT_UPSTREAM
# Initialize the database try: createDb(DATABASE_TYPE, DATADIR, APP_NAME, MYSQL_HOST, MYSQL_PORT, MYSQL_USER, MYSQL_PASS) except Exception, e: logger.error("Error initializing the database: %s" % e) # Disable SSL verification for systems where SSL is broken if not VERIFY_SSL: try: import ssl ssl._create_default_https_context = ssl._create_unverified_context logger.info("SSL verification disabled per user preferences") except Exception, e: logger.warn("There was an error disabling SSL verification: %s" % s) pass # Get the currently installed version. Returns None, 'win32' or the git # hash. GIT_LOCAL, GIT_BRANCH = versioncheck.getVersion() # Write current version to a file, so we know which version did work. # This allows one to restore to that version. The idea is that if we # arrive here, most parts of the app seem to work. if GIT_LOCAL: version_lock_file = os.path.join(DATADIR, "version.lock") try: with open(version_lock_file, "w") as fp: fp.write(GIT_LOCAL)
% e) #================================================================ if len(kwargs) != 0: for key, value in kwargs.items(): errorList.append("Key %s not expected" % key) cherrystrap.config_write() if not errorList: logger.info("All configuration settings successfully updated") return "{\"status\": \"success\", \ \"message\": \"All configuration settings successfully updated\"}" else: logger.warn( "The following error(s) occurred while attempting to update settings: %s" % errorList) return "{\"status\": \"warning\", \ \"message\": \"The following error(s) occurred while attempting to update settings: %s\"}" % errorList def DELETE(self, token=None): if token != cherrystrap.API_TOKEN: return "{\"status\": \"error\", \"message\": \"Invalid Token\"}" return "{\"status\": \"error\", \"message\": \"DELETE not available at this endpoint\"}" class log(object): exposed = True def GET(self, token=None, draw=1, start=0, length=100, **kwargs):
def main(): # rename this thread threading.currentThread().name = "MAIN" # Set paths if hasattr(sys, 'frozen'): cherrystrap.FULL_PATH = os.path.abspath(sys.executable) else: cherrystrap.FULL_PATH = os.path.abspath(__file__) cherrystrap.PROG_DIR = os.path.dirname(cherrystrap.FULL_PATH) cherrystrap.ARGS = sys.argv[1:] cherrystrap.SYS_ENCODING = None try: locale.setlocale(locale.LC_ALL, "") cherrystrap.SYS_ENCODING = locale.getpreferredencoding() except (locale.Error, IOError): pass # for OSes that are poorly configured I'll just force UTF-8 if not cherrystrap.SYS_ENCODING or cherrystrap.SYS_ENCODING in ( 'ANSI_X3.4-1968', 'US-ASCII', 'ASCII'): cherrystrap.SYS_ENCODING = 'UTF-8' # Set arguments from optparse import OptionParser p = OptionParser() p.add_option('-d', '--daemon', action="store_true", dest='daemon', help="Run the server as a daemon") p.add_option('-q', '--quiet', action="store_true", dest='quiet', help="Don't log to console") p.add_option('--debug', action="store_true", dest='debug', help="Show debuglog messages") p.add_option('--nolaunch', action="store_true", dest='nolaunch', help="Don't start browser") p.add_option('--port', dest='port', default=None, help="Force webinterface to listen on this port") p.add_option('--datadir', dest='datadir', default=None, help="Path to the data directory") p.add_option('--config', dest='config', default=None, help="Path to config.ini file") p.add_option('-p', '--pidfile', dest='pidfile', default=None, help="Store the process id in the given file") options, args = p.parse_args() if options.debug: cherrystrap.LOGLEVEL = 2 if options.quiet: cherrystrap.LOGLEVEL = 0 if options.daemon: if not sys.platform == 'win32': cherrystrap.DAEMON = True cherrystrap.LOGLEVEL = 0 cherrystrap.daemonize() else: print "Daemonize not supported under Windows, starting normally" if options.nolaunch: cherrystrap.LAUNCH_BROWSER = False if options.datadir: cherrystrap.DATADIR = str(options.datadir) else: cherrystrap.DATADIR = cherrystrap.PROG_DIR if options.config: cherrystrap.CONFIGFILE = str(options.config) else: cherrystrap.CONFIGFILE = os.path.join(cherrystrap.DATADIR, "config.ini") if options.pidfile: if cherrystrap.DAEMON: cherrystrap.PIDFILE = str(options.pidfile) # create and check (optional) paths if not os.path.exists(cherrystrap.DATADIR): try: os.makedirs(cherrystrap.DATADIR) except OSError: raise SystemExit('Could not create data directory: ' + cherrystrap.DATADIR + '. Exit ...') if not os.access(cherrystrap.DATADIR, os.W_OK): raise SystemExit('Cannot write to the data directory: ' + cherrystrap.DATADIR + '. Exit ...') # import config cherrystrap.CFG = ConfigObj(cherrystrap.CONFIGFILE, encoding='utf-8') cherrystrap.initialize() if options.port: HTTP_PORT = int(options.port) logger.info('Starting cherrystrap on forced port: %s' % HTTP_PORT) else: HTTP_PORT = int(cherrystrap.HTTP_PORT) if cherrystrap.DAEMON: cherrystrap.daemonize() # Check if pyOpenSSL is installed. It is required for certificate generation # and for CherryPy. if cherrystrap.HTTPS_ENABLED: try: import OpenSSL except ImportError: logger.warn("The pyOpenSSL module is missing. Install this " \ "module to enable HTTPS. HTTPS will be disabled.") cherrystrap.HTTPS_ENABLED = False # Try to start the server. webStart.initialize({ 'http_port': HTTP_PORT, 'http_host': cherrystrap.HTTP_HOST, 'http_root': cherrystrap.HTTP_ROOT, 'http_user': cherrystrap.HTTP_USER, 'http_pass': cherrystrap.HTTP_PASS, 'https_enabled': cherrystrap.HTTPS_ENABLED, 'https_key': cherrystrap.HTTPS_KEY, 'https_cert': cherrystrap.HTTPS_CERT, 'verify_ssl': cherrystrap.VERIFY_SSL }) if cherrystrap.LAUNCH_BROWSER and not options.nolaunch: cherrystrap.launch_browser(cherrystrap.HTTP_HOST, cherrystrap.HTTP_PORT, cherrystrap.HTTP_ROOT) cherrystrap.start() while True: if not cherrystrap.SIGNAL: try: time.sleep(1) except KeyboardInterrupt: cherrystrap.shutdown() else: if cherrystrap.SIGNAL == 'shutdown': cherrystrap.shutdown() elif cherrystrap.SIGNAL == 'restart': cherrystrap.shutdown(restart=True) else: cherrystrap.shutdown(restart=True, update=True) cherrystrap.SIGNAL = None return