diff --git a/README.ru.md b/README.ru.md index 022ddc4..66adf3f 100644 --- a/README.ru.md +++ b/README.ru.md @@ -1,5 +1,5 @@ # Surok -[![Build Status](https://travis-ci.org/Difrex/surok.svg?branch=master)](https://travis-ci.org/Difrex/surok) +[![Build Status](https://travis-ci.org/Surkoveds/surok.svg?branch=master)](https://travis-ci.org/Surkoveds/surok) Обнаружение сервисов для Apache Mesos. @@ -17,10 +17,27 @@ cd build deb-пакет будет лежать в build/out Сборка базового docker-образа surok +Ubuntu Xenial ``` cd build ./build.sh surok_image ``` +Alpine image +``` +cd build +./build.sh alpine +``` +CentOS image +``` +cd build +./build.sh centos +``` + +ENTRYPOINT : ```cd /opt/surok && pytho3 surok.py -c /etc/surok/conf/surok.json``` + +## Документация + +[Wiki](https://github.com/Surkoveds/surok/wiki) ## Известные проблемы diff --git a/build/tests.py b/build/tests.py index ece5c7b..3828fe4 100644 --- a/build/tests.py +++ b/build/tests.py @@ -3,7 +3,6 @@ import json import os import re - class TestLoadConfig(unittest.TestCase): def test_main_conf(self): @@ -16,7 +15,6 @@ class TestLoadConfig(unittest.TestCase): self.assertIn('confd', conf) self.assertTrue(os.path.isdir(conf['confd'])) - self.assertIn('domain', conf) self.assertIn('wait_time', conf) self.assertIn('lock_dir', conf) self.assertTrue(os.path.isdir(conf['lock_dir'])) @@ -24,48 +22,59 @@ class TestLoadConfig(unittest.TestCase): class TestLogger(unittest.TestCase): + def test_debug(self): + from surok.logger import Logger + m = Logger() + self.assertIn('DEBUG', m.testing('debug','log message')) + def test_info(self): - from surok.logger import make_message - m = make_message - self.assertIn('INFO', m({'level': 'INFO', 'raw': 'log message'})) + from surok.logger import Logger + m = Logger() + self.assertIn('INFO', m.testing('info','log message')) def test_warning(self): - from surok.logger import make_message - m = make_message - self.assertIn('WARNING', m({'level': 'WARNING', 'raw': 'log message'})) + from surok.logger import Logger + m = Logger() + self.assertIn('WARNING', m.testing('warning','log message')) def test_error(self): - from surok.logger import make_message - m = make_message - self.assertIn('ERROR', m({'level': 'ERROR', 'raw': 'log message'})) - - def test_info(self): - from surok.logger import make_message - m = make_message - self.assertIn('DEBUG', m({'level': 'DEBUG', 'raw': 'log message'})) + from surok.logger import Logger + m = Logger() + self.assertIn('ERROR', m.testing('error','log message')) class TestMemcachedDiscovery(unittest.TestCase): def test_discovery_memcache(self): from surok.system import discovery_memcached - + from surok.discovery import Discovery # Load base configurations surok_conf = '/etc/surok/conf/surok.json' # Read config file f = open(surok_conf, 'r') conf = json.loads(f.read()) f.close() - + d=Discovery(conf) self.assertEqual(discovery_memcached(conf), []) class TestGetGroup(unittest.TestCase): - def test_get_group(self): - from surok.discovery import get_group - self.assertFalse(get_group({}, {'env': os.environ})) - + def test_get_group_from_service(self): + from surok.discovery import DiscoveryTemplate + d=DiscoveryTemplate({}) + self.assertEqual('xxx.yyy.zzz',d.get_group({'group':'xxx.yyy.zzz'}, {})) + + def test_get_group_from_env(self): + from surok.discovery import DiscoveryTemplate + d=DiscoveryTemplate({}) + self.assertEqual('xxx.yyy.zzz',d.get_group({}, {'env':{'SUROK_DISCOVERY_GROUP':'xxx.yyy.zzz'}})) + + def test_get_group_from_marathon_id(self): + from surok.discovery import DiscoveryTemplate + d=DiscoveryTemplate({}) + self.assertEqual('xxx.yyy.zzz',d.get_group({}, {'env':{'MARATHON_APP_ID':'/zzz/yyy/xxx/www'}})) + if __name__ == '__main__': unittest.main() diff --git a/conf/surok.json b/conf/surok.json index c48ef84..e1c58f2 100644 --- a/conf/surok.json +++ b/conf/surok.json @@ -1,26 +1,31 @@ { "marathon": { - "force": true, - "host": "http://marathon.mesos:8080", - "enabled": false - }, + "enabled": false, + "restart": false, + "force": true, + "host": "http://marathon.mesos:8080" + }, "consul": { "enabled": false, "domain": "service.dc1.consul" }, + "mesos":{ + "enabled": true, + "domain": "marathon.mesos" + }, + "default_discovery": "mesos_dns", "confd": "/etc/surok/conf.d", - "domain": "marathon.mesos", "wait_time": 20, "lock_dir": "/var/tmp", "loglevel": "info", - "container": false, - "memcached": { - "enabled": false, - "discovery": { - "enabled": false, - "service": "memcached", - "group": "system" - }, - "hosts": ["localhost:11211"] - } + "container": false, + "memcached": { + "enabled": false, + "discovery": { + "enabled": false, + "service": "memcached", + "group": "system" + }, + "hosts": ["localhost:11211"] + } } diff --git a/docs/App-config-file.html b/docs/App-config-file.html index 8c0bd6e..8b5c2bc 100644 --- a/docs/App-config-file.html +++ b/docs/App-config-file.html @@ -34,9 +34,9 @@ } * services. List of hashes with required services for app. - 1. name - string. App name in Marathon. + 1. name - string. App name in Marathon. If you use a Marathon discovery, you can use the "*" at the end of the string to indicate any character. 2. group - string. App group in Marathon. Optional. Discovery policy: 1) config 2) SUROKDISCOVERYGROUP environment variable 3) Marathon API - 3. ports - list. Name of opened port. In marathon of course. Optional. + 3. ports - list. Name of opened port. In marathon of course. If you use a Marathon discovery, you can use the "*" at the end of the string to indicate any character. Optional. * confname. Unique app config name. * template. Jinja2 template location. * dest. Destination config path. diff --git a/docs/App-config-file.md b/docs/App-config-file.md index 60b63bd..5156e5a 100644 --- a/docs/App-config-file.md +++ b/docs/App-config-file.md @@ -21,9 +21,9 @@ conf.d/myapp.json } ``` * **services**. List of hashes with required services for app. - 1. _name_ - string. App name in Marathon. + 1. _name_ - string. App name in Marathon. If you use a Marathon discovery, you can use the "*" at the end of the string to indicate any character. 2. _group_ - string. App group in Marathon. Optional. Discovery policy: 1) config 2) SUROK_DISCOVERY_GROUP environment variable 3) Marathon API - 3. _ports_ - list. Name of opened port. In marathon of course. Optional. + 3. _ports_ - list. Name of opened port. In marathon of course. If you use a Marathon discovery, you can use the "*" at the end of the string to indicate any character. Optional. * **conf_name**. Unique app config name. * **template**. Jinja2 template location. * **dest**. Destination config path. diff --git a/docs/Main-config-file.html b/docs/Main-config-file.html index ff6c3da..e14bd5c 100644 --- a/docs/Main-config-file.html +++ b/docs/Main-config-file.html @@ -19,12 +19,21 @@ { "marathon": { - "force": true, - "host": "http://marathon.mesos:8080", - "enabled": false + "enabled": false, + "restart": false, + "force": true, + "host": "http://marathon.mesos:8080" }, + "consul": { + "enabled": false, + "domain": "service.dc1.consul" + }, + "mesos":{ + "enabled": true, + "domain": "marathon.mesos" + }, + "default_discovery": "mesos_dns", "confd": "/etc/surok/conf.d", - "domain": "marathon.mesos", "wait_time": 20, "lock_dir": "/var/tmp", "loglevel": "info", diff --git a/docs/Main-config-file.md b/docs/Main-config-file.md index 431fb44..db2efd6 100644 --- a/docs/Main-config-file.md +++ b/docs/Main-config-file.md @@ -6,24 +6,33 @@ conf/surok.json ``` { "marathon": { - "force": true, - "host": "http://marathon.mesos:8080", - "enabled": false - }, + "enabled": false, + "restart": false, + "force": true, + "host": "http://marathon.mesos:8080" + }, + "consul": { + "enabled": false, + "domain": "service.dc1.consul" + }, + "mesos":{ + "enabled": true, + "domain": "marathon.mesos" + }, + "default_discovery": "mesos_dns", "confd": "/etc/surok/conf.d", - "domain": "marathon.mesos", "wait_time": 20, "lock_dir": "/var/tmp", "loglevel": "info", "container": false, "memcached": { - "enabled": false, - "discovery": { - "enabled": false, - "service": "memcached", - "group": "system" - }, - "hosts": ["localhost:11211"] + "enabled": false, + "discovery": { + "enabled": false, + "service": "memcached", + "group": "system" + }, + "hosts": ["localhost:11211"] } } ``` diff --git a/surok.py b/surok.py index 31f3dc3..4429e19 100755 --- a/surok.py +++ b/surok.py @@ -7,10 +7,11 @@ from os.path import isfile, join import json import argparse from surok.templates import gen -from surok.discovery import resolve +from surok.discovery import Discovery from surok.system import reload_conf +from surok.logger import Logger - +logger=Logger() # Load base configurations surok_conf = '/etc/surok/conf/surok.json' @@ -47,28 +48,34 @@ def load_app_conf(app): return c +logger.set_level(conf.get('loglevel','info')) # Main loop ########### +discovery=Discovery() + while 1: confs = get_configs() + + # Update config from discovery object + discovery.set_config(conf) + + # Update discovery data + discovery.update_data() + for app in confs: app_conf = load_app_conf(app) - # Will be removed later - # For old configs - loglevel = 'info' - if 'loglevel' in conf: - loglevel = conf['loglevel'] - # Resolve services - app_hosts = resolve(app_conf, conf) + app_hosts = discovery.resolve(app_conf) # Populate my dictionary my = {"services": app_hosts, "conf_name": app_conf['conf_name']} + logger.debug('my=',my) + # Generate config from template service_conf = gen(my, app_conf['template']) diff --git a/surok/discovery.py b/surok/discovery.py index ff494fa..429e51b 100644 --- a/surok/discovery.py +++ b/surok/discovery.py @@ -1,78 +1,270 @@ import dns.resolver import dns.query from dns.exception import DNSException -from .logger import info, warning, error, debug +from .logger import Logger import sys +import requests +# Default config for Discovery class +_config={ + 'default_discovery':'mesos_dns' # Default discovery system +} -# Resolve service from mesos-dns SRV record -# return dict {"servicename": [{"name": "service.f.q.d.n.", "port": 9999}]} -def resolve(app, conf): - hosts = {} - services = app['services'] - domain = conf['domain'] +# Discoveries objects +_discoveries={} - for service in services: - hosts[service['name']] = [] +#Logger +logger=Logger() - group = get_group(service, app) - if group is False: - error('Group is not defined in config, SUROK_DISCOVERY_GROUP and MARATHON_APP_ID') - error('Not in Mesos launch?') +class DiscoveryTemplate: + # Default config values for discovery template + _config={} + _defconfig={'enabled':False} + + def __init__(self,conf): + for key in self._defconfig.keys(): + if key not in self._config.keys(): + self._config[key]=self._defconfig[key] + self.set_config(conf) + + def set_config(self,conf): + pass + + def enabled(self): + return self._config['enabled'] + + def update_data(self): + pass + + def get_group(self,service, app): + # Check group in app conf + if 'group' in service: + return service['group'] + + # Check environment variable + elif app['env'].get('SUROK_DISCOVERY_GROUP'): + return app['env']['SUROK_DISCOVERY_GROUP'] + + # Check marathon environment variable + elif app['env'].get('MARATHON_APP_ID'): + return ".".join(app['env']['MARATHON_APP_ID'].split('/')[-2:0:-1]) + + else: + logger.error('Group is not defined in config, SUROK_DISCOVERY_GROUP and MARATHON_APP_ID') + logger.error('Not in Mesos launch?') sys.exit(2) - # Port name from app config - ports = None - if 'ports' in service: - ports = service['ports'] - # "service-with-defined-ports": - # [ - # { - # "name": "example1.com", - # "ip": ["10.10.10.1"], - # "ports": { - # "rpc": 12342, - # "web": 12341 - # } - # }, - # { - # "name": "example2.com", - # "ports": { - # "rpc": 12344, - # "web": 12343 - # } - # } - # ] - fqdn = '' +class Discovery: + def __init__(self,*conf): + for __conf in conf: + self.set_config(__conf) - # Discovery over Consul DNS - if 'consul' in conf and conf['consul']['enabled']: - fqdn = '_' + service['name'] + '._tcp.' + conf['consul']['domain'] - hosts[service['name']].append(do_query(fqdn, conf['loglevel'])) - continue - - if ports is not None: - for port_name in ports: - fqdn = '_' + port_name + '.' + '_' + service['name'] + '.' + group + '._tcp.' + domain # Need support for udp ports. See #16 - discovered = do_query(fqdn, conf['loglevel']) - for d in discovered: - to_append = {} - to_append['name'] = d['name'] - to_append['ip'] = d['ip'] - to_append['ports'][port_name] = d['port'] - hosts[service['name']].append(to_append) + def set_config(self,conf): + global _discoveries + #Get discoveries objects + if not _discoveries.get('mesos_dns'): + _discoveries['mesos_dns']=DiscoveryMesos(conf) else: - fqdn = '_' + service['name'] + '.' + group + '._tcp.' + domain - hosts[service['name']] = do_query(fqdn, conf['loglevel']) + _discoveries['mesos_dns'].set_config(conf) - return hosts + if not _discoveries.get('marathon_api'): + _discoveries['marathon_api']=DiscoveryMarathon(conf) + else: + _discoveries['marathon_api'].set_config(conf) + + if not _discoveries.get('consul_dns'): + _discoveries['consul_dns']=DiscoveryConsul(conf) + else: + _discoveries['consul_dns'].set_config(conf) + + global _config + if conf.get('default_discovery'): + discovery=conf.get('default_discovery') + if discovery in list(_discoveries.keys()): + _config['default_discovery']=discovery + else: + logger.error('Default discovery "'+discovery+'" is not present') + logger.debug('Conf=',conf) + + def resolve(self,app): + __discovery=_config.get('default_discovery') + if app.get('discovery'): + discovery=app.get('discovery') + if discovery in list(_discoveries.keys()): + __discovery=discovery + else: + logger.warning('Discovery "'+discovery+'" is not present') + logger.debug('App=',app) + return {} + if _discoveries[__discovery].enabled(): + return _discoveries[__discovery].resolve(app) + else: + logger.error('Discovery "'+__discovery+'" is disabled') + return {} + + def update_data(self): + global _discoveries + for d in list(_discoveries.keys()): + if _discoveries[d].enabled(): + _discoveries[d].update_data() + + +class DiscoveryMesos(DiscoveryTemplate): + _config={ + 'domain':'marathon.mesos' # Default domain + } + + def set_config(self,conf): + # For old version config + if conf.get('domain'): + self._config['domain']=conf.get('domain') + self._config['enabled']=True + # For current version config + if conf.get('mesos'): + _conf=conf['mesos'] + for p in ['domain','enabled']: + if _conf.get(p): + self._config[p]=_conf.get(p) + + def resolve(self,app): + hosts = {} + services = app['services'] + domain = self._config['domain'] + for service in services: + group = self.get_group(service, app) + ports = service.get('ports') + name = service['name'] + hosts[name] = {} + serv = hosts[name] + if ports is not None: + hosts[name] = {} + serv = hosts[name] + for prot in ['tcp','udp']: + for port_name in ports: + for d in do_query('_'+port_name+'._'+name+'.'+group+'._'+prot+'.'+domain): + hostname=d['name'] + if serv.get(hostname) is None: + serv[hostname]={"name":hostname,"ip":d['ip']} + if serv[hostname].get(prot) is None: + serv[hostname][prot]={} + serv[hostname][prot][port_name]=d['port'] + hosts[name]=list(hosts[name].values()) + else: + hosts[name]=do_query('_'+name+'.'+group+'._tcp.'+domain) + + return hosts + + +class DiscoveryMarathon(DiscoveryTemplate): + _config={ + 'host':'http://marathon.mesos:8080', + 'force':True + } + __tasks = [] + __ports = {} + def set_config(self,conf): + # For current version config + if conf.get('marathon'): + _conf=conf['marathon'] + for p in ['host','enabled','force']: + if _conf.get(p): + self._config[p]=_conf.get(p) + + def update_data(self): + try: + apps = requests.get(self._config['host']+'/v2/apps').json()['apps'] + ports = {} + for app in apps: + ports[app['id']] = {} + if app.get('container') is not None and app['container']['type'] == 'DOCKER': + ports[app['id']] = app['container']['docker'].get('portMappings',[]) + self.__ports=ports + except: + logger.warning('Apps ('+self._config['host']+'/v2/apps) request from Marathon API is failed') + pass + try: + self.__tasks = requests.get(self._config['host']+'/v2/tasks').json()['tasks'] + except: + logger.warning('Tasks ('+self._config['host']+'/v2/tasks) request from Marathon API is failed') + pass + + def resolve(self, app): + hosts={} + serv_conf = app['services'] + if not serv_conf: + serv_conf = [{'name':'*','ports':['*']}] + for serv in serv_conf: + # Convert xxx.yyy.zzz to /zzz/yyy/xxx/ format + group = '/'.join(['']+self.get_group(serv, app).split('.')[::-1]+['']) + mask = group+serv['name'] + for task in self.__tasks: + if (mask.endswith('*') and task['appId'].startswith(mask[:-1])) or task['appId'] == mask: + name='.'.join(task['appId'][len(group):].split('/')[::-1]) + if 'ports' in serv: + hosts[name]={} + for port in self.__ports[task['appId']]: + for pp in serv['ports']: + if (pp.endswith('*') and port['name'].startswith(pp[:-1])) or port['name'] == pp: + if hosts[name].get(task['host']) is None: + hosts[name][task['host']]={'name':task['host'], + 'ip':do_query_a(task['host'])} + if hosts[name][task['host']].get(port['protocol']) is None: + hosts[name][task['host']][port['protocol']]={} + hosts[name][task['host']][port['protocol']][port['name']]=task['ports'][task['servicePorts'].index(port['servicePort'])] + hosts[name]=list(hosts[name].values()) + else: + hosts[name]=[] + for port in self.__ports[task['appId']]: + hosts[name].append({'name':task['host'], + 'port':task['ports'][task['servicePorts'].index(port['servicePort'])], + 'ip':do_query_a(task['host'])}) + + return hosts + + +class DiscoveryConsul(DiscoveryTemplate): + _config={ + 'enabled':False, + 'domain':None + } + def set_config(self,conf): + # For current version config + if conf.get('consul'): + _conf=conf['consul'] + for p in ['domain','enabled']: + if _conf.get(p): + self._config[p]=_conf.get(p) + + def resolve(self,app): + hosts = {} + services = app['services'] + domain = self._config['domain'] + for service in services: + name = service['name'] + hosts[name]=do_query('_'+name+'._tcp.'+domain) + return hosts + + +# Do DNS queries +# Return array: +# ["10.10.10.1", "10.10.10.2"] +def do_query_a(fqdn): + servers = [] + try: + resolver = dns.resolver.Resolver() + for a_rdata in resolver.query(fqdn, 'A'): + servers.append(a_rdata.address) + except DNSException as e: + logger.error("Could not resolve "+fqdn) + + return servers # Do DNS queries # Return array: # [{"name": "f.q.d.n", "port": 8876, "ip": ["10.10.10.1", "10.10.10.2"]}] -def do_query(fqdn, loglevel): +def do_query(fqdn): servers = [] try: resolver = dns.resolver.Resolver() @@ -83,40 +275,8 @@ def do_query(fqdn, loglevel): info = str(rdata).split() name = info[3][:-1] port = info[2] - server = {'name': name, 'port': port, 'ip': []} - a_query = resolver.query(name, 'A') - for a_rdata in a_query: - server['ip'].append(a_rdata.address) - servers.append(server) + servers.append({'name': name, 'port': port, 'ip': do_query_a(name)}) except DNSException as e: - if loglevel != 'info': - error("Could not resolve " + fqdn) + logger.error("Could not resolve " + fqdn) return servers - - -# Groups switch -# Priority: config, environment, marathon environment -def get_group(service, app): - # Check group in app conf - if 'group' in service: - return service['group'] - # Check environment variable - elif app['env'].get('SUROK_DISCOVERY_GROUP'): - return app['env']['SUROK_DISCOVERY_GROUP'] - # Check marathon environment variable - elif app['env'].get('MARATHON_APP_ID'): - group = parse_marathon_app_id(app['env']['MARATHON_APP_ID']) - return group - else: - return False - - -# Parse MARATHON_APP_ID -# Return marathon.group -def parse_marathon_app_id(marathon_app_id): - marathon_app_id = marathon_app_id.split('/') - del(marathon_app_id[-1]) - marathon_app_id.reverse() - group = ".".join(marathon_app_id)[:-1] - return(group) diff --git a/surok/logger.py b/surok/logger.py index e9baf26..7cee349 100644 --- a/surok/logger.py +++ b/surok/logger.py @@ -1,36 +1,51 @@ import sys +import json from time import time +_loglevel='info' +msg_level={'debug':'DEBUG', + 'info':'INFO', + 'warning':'WARNING', + 'error':'ERROR'} +class Logger: + def __init__(self,*args): + if args: + self.set_level(args[0]) -def make_message(message): - cur_time = str(time()) - m = '[' + cur_time + '] ' + message['level'] + ': ' + message['raw'] + "\n" - return m + def set_level(self,level): + if level in ['debug','info','warning','error']: + global _loglevel + _loglevel=level + def get_level(self): + return _loglevel -def info(message): - req = {'level': 'INFO', 'raw': message} - m = make_message(req) + def __make_message(self,message): + r=[] + l=self.get_level() + for m in message: + if type(m).__name__=='str': + r.append(m) + else: + r.append(json.dumps(m,sort_keys=True,indent=2)) + return '[' + str(time()) + '] ' + msg_level[l] + ': ' + ''.join(r) + "\n" - sys.stdout.write(m) + def debug(self,*message): + if self.get_level() in ['debug']: + sys.stderr.write(self.__make_message(message)) + def info(self,*message): + if self.get_level() in ['debug','info']: + sys.stdout.write(self.__make_message(message)) -def warning(message): - req = {'level': 'WARNING', 'raw': message} - m = make_message(req) + def warning(self,*message): + if self.get_level() in ['debug','info','warning']: + sys.stderr.write(self.__make_message(message)) - sys.stderr.write(m) + def error(self,*message): + sys.stderr.write(self.__make_message(message)) + def testing(self,level,message): + self.set_level(level) + return self.__make_message(message) -def error(message): - req = {'level': 'ERROR', 'raw': message} - m = make_message(req) - - sys.stderr.write(m) - - -def debug(message): - req = {'level': 'DEBUG', 'raw': message} - m = make_message(req) - - sys.stderr.write(m) diff --git a/surok/system.py b/surok/system.py index 324961b..89b1466 100644 --- a/surok/system.py +++ b/surok/system.py @@ -1,20 +1,19 @@ import os import sys import requests -from .discovery import resolve -from .logger import info, warning, error, debug - +from .discovery import Discovery +from .logger import Logger +logger=Logger() # Get old configuration def get_old(name, service_conf): - try: path = '/var/tmp/surok.' + name f = open(path, 'r') old = f.read() f.close() except Exception as e: - print(str(e)) + logger.error(str(e)) return 0 if old == service_conf: @@ -53,7 +52,7 @@ def write_lock(name, service_conf): def do_reload(service_conf, app_conf): - warning('Write new configuration of ' + app_conf['conf_name']) + logger.warning('Write new configuration of ' + app_conf['conf_name']) f = open(app_conf['dest'], 'w') f.write(service_conf) @@ -68,6 +67,7 @@ def do_reload(service_conf, app_conf): # Discovery memcached servers def discovery_memcached(conf): + discovery=Discovery() memcache = conf['memcached'] app_conf = { "services": [ @@ -78,7 +78,7 @@ def discovery_memcached(conf): ] } - hosts = resolve(app_conf, conf) + hosts = discovery.resolve(app_conf) mc_servers = [] for server in hosts[memcache['discovery']['service']]: @@ -91,7 +91,7 @@ def discovery_memcached(conf): # !!! NEED REFACTORING !!! def reload_conf(service_conf, app_conf, conf, app_hosts): # Check marathon enabled in configuration - if conf['marathon']['enabled'] is True: + if conf['marathon'].get('restart',False): if get_old(app_conf['conf_name'], service_conf) != 1: restart_self_in_marathon(conf['marathon']) @@ -105,47 +105,38 @@ def reload_conf(service_conf, app_conf, conf, app_hosts): mc_hosts = None if conf['memcached']['discovery']['enabled'] is True: mc_hosts = discovery_memcached(conf) - info('Discovered memcached hosts: ' + str(mc_hosts)) + logger.info('Discovered memcached hosts: ' + str(mc_hosts)) else: mc_hosts = conf['memcached']['hosts'] try: mc = memcache.Client(mc_hosts) if get_old_from_memcache(mc, app_conf['conf_name'], app_hosts) != 1: stdout = do_reload(service_conf, app_conf) - info(stdout) + logger.info(stdout) return True except Exception as e: - error('Cannot connect to memcached: ' + str(e)) + logger.error('Cannot connect to memcached: ' + str(e)) else: - warning('DEPRECATED main conf file. Please use new syntax!') + logger.warning('DEPRECATED main conf file. Please use new syntax!') # End of memcache block ####################### if get_old(app_conf['conf_name'], service_conf) != 1: stdout = do_reload(service_conf, app_conf) - info(stdout) + logger.info(stdout) return True else: - if conf['loglevel'] == 'debug': - debug('Same config ' + app_conf['conf_name'] + ' Skip reload') + logger.debug('Same config ' + app_conf['conf_name'] + ' Skip reload') return False - # Do POST request to marathon API # /v2/apps//app/name/restart def restart_self_in_marathon(marathon): - host = marathon['host'] - # Check MARATHON_APP_ID environment varible - if os.environ.get('MARATHON_APP_ID') is not True: - error('Cannot find MARATHON_APP_ID. Not in Mesos?') + if not os.environ.get('MARATHON_APP_ID',False): + logger.error('Cannot find MARATHON_APP_ID. Not in Mesos?') sys.exit(2) - app_id = os.environ['MARATHON_APP_ID'] - uri = 'http://' + host + '/v2/apps/' + app_id + '/restart' - # Ok. In this step we made restart request to Marathon - if marathon['force'] is True: - r = requests.post(uri, data = {'force': 'true'}) - else: - r = requests.post(uri, data = {'force': 'false'}) + r = requests.post('http://'+marathon['host']+'/v2/apps/'+os.environ['MARATHON_APP_ID']+'/restart', + data={'force': marathon.get('force',False)})