Last active
September 27, 2019 20:52
-
-
Save raypendergraph/08e50ff48d32beb039789c3afe291305 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env python | |
from __future__ import print_function | |
import json | |
import subprocess | |
import multiprocessing | |
import sys | |
import os | |
import signal | |
import threading | |
''' | |
This script will build and run all the configured Go services. Each service is defined by a definition (directly below) which fully describe | |
the location and naming conventions of the service. By default the script assumes that all the services are checked out into one parent | |
directory and with the default name from the Git repo. This script (by default) should run in that parent directory. | |
**Remember** - The ports here should line up with the dev proxy configuration. | |
Optional json keys: | |
'dir' - (defaults to relative name)if you put this key in the definition with the full path of the service root then that will be used | |
'exe' - (defaults to name) if the executable name produced by go build is not the same as the directory, this corrects that. | |
'env_file' - (defaults to dev.env) An env file for service env variables. | |
''' | |
def eprint(*args, **kwargs): | |
print(*args, file=sys.stderr, **kwargs) | |
def service_dir(svc): | |
return svc['dir'] if 'dir' in svc else os.path.join(os.getcwd(), svc['name']) | |
def read_env(env_file): | |
# By default each process gets a copy of the callers env, values can be added | |
# or overridden by providing an 'env_file' key in the service definition. | |
env = dict(os.environ) | |
if not os.path.isfile(env_file): | |
return env | |
print('Reading env file: {}'.format(env_file)) | |
with open(env_file, 'r') as f: | |
lines = f.readlines() | |
for l in lines: | |
sl = l.strip() | |
if sl.startswith('#'): | |
continue | |
parts = sl.split('=', 1) | |
if len(parts) != 2: | |
print('Ignoring badly formatted line {}'.format(sl)) | |
continue | |
k, v = parts | |
print(' {}={}'.format(k, v)) | |
env[k.strip()]=v.strip() | |
return env | |
def create_svc_target(svc, notify): | |
def run_svc(): | |
command = [ | |
'./{}'.format(svc.get('exe', svc['name'])), | |
'-{grpc_arg}'.format(**svc), | |
'{grpc_port}'.format(**svc), | |
'-{http_arg}'.format(**svc), | |
'{http_port}'.format(**svc)] | |
svc_path=service_dir(svc) | |
env_file=os.path.join(svc_path, svc.get('env_file', 'dev.env')) | |
env = read_env(env_file) | |
print('Starting {} in {}'.format(' '.join(command), svc_path)) | |
subprocess.call(command, cwd=svc_path, stderr=sys.stderr.fileno(), stdout=sys.stdout.fileno(), env=env) | |
return run_svc | |
if __name__ == '__main__': | |
with open('svc_config.json', 'r') as f: | |
config = json.load(f) | |
active_services = [s for s in config['services'] if s['launch'] == True] | |
for service in active_services: | |
svc_path = service_dir(service) | |
print('Building service {}...'.format(service['name'])) | |
try: | |
subprocess.check_call(['go', 'build'], stderr=sys.stderr.fileno(), stdout=sys.stdout.fileno(), cwd=svc_path) | |
except: | |
eprint('The {} service failed to build.'.format(s['name'])) | |
exit(-1) | |
svc_processes = [] | |
def notify_terminated(signal, frame): | |
print('Stopping services...') | |
return | |
signal.signal(signal.SIGINT, notify_terminated) | |
for service in active_services: | |
p = multiprocessing.Process(target=create_svc_target(service, notify_terminated), name=service['name']) | |
p.start() | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment