#! /usr/bin/env python
# -*- Mode: Python; tab-width: 4; indent-tabs-mode: nil; -*-

import argparse
import logging
import sys
import os

from syncless import coio

prefix = os.path.normpath(os.path.join(os.path.abspath(sys.argv[0]), os.pardir, os.pardir))
sys.path.insert(0, prefix)

from tako import configuration
from tako.proxyserver import ProxyServer
from tako.utils import debug
from tako.utils import convert

def makedirs(path):
    if not os.path.exists(path):
        os.makedirs(path)

def main():
    global prefix
    default_var_path = os.path.join(prefix, 'var', 'tako')

    parser = argparse.ArgumentParser(description="Tako Proxy")
    parser.add_argument('-p', '--port', help='port. Default = 8080', default=8080, type=int)
    parser.add_argument('-id', '--id', help='Proxy id. Default = p1', default='p1')
    parser.add_argument('-c', '--coordinator', help='Coordinator Server (address port)', nargs=2, action='append')
    parser.add_argument('-cfg','--config', help='Configuration file. For use without a coordinator.')
    parser.add_argument('-d', '--debug', help='Enable debug logging.', action='store_true')
    parser.add_argument('-prof', '--profiling-file', help='Enable performance profiling.')
    parser.add_argument('-l', '--log-file', help='Log file.')
    parser.add_argument('-v', '--var', help='var directory. Default = %s' % default_var_path, default=default_var_path)

    args = parser.parse_args()

    if args.profiling_file:
        import cProfile
        cProfile.runctx('_main(args)', globals(), locals(), args.profiling_file)
    else:
        _main(args)

def _main(args):
    level = logging.DEBUG if args.debug else logging.INFO
    debug.configure_logging('proxyserver', level, args.log_file)

    logging.info('Tako Proxy starting (pid:%d)', os.getpid())
    logging.info('Proxy id: %s', args.id)

    try:
        makedirs(os.path.join(args.var, 'data'))
        makedirs(os.path.join(args.var, 'etc'))
        makedirs(os.path.join(args.var, 'log'))
    except Exception, e:
        logging.critical("Failed to create var directories.")
        exit(1)

    config = None
    if args.config:
        config = configuration.try_load_file(args.config)
        if not config:
            logging.critical('Failed to load configuration file "%s"', args.config)
            exit(1)

    coordinators = []
    if args.coordinator:
        for address, port_string in args.coordinator:
            port = convert.try_int(port_string)
            if not port:
                logging.critical("Invalid port '%s'", port_string)
                exit(1)
            coordinators.append((address, port))
    try:
        server = ProxyServer(args.id, ('localhost', args.port), explicit_configuration=config,
                             coordinator_addresses=coordinators, var_directory=args.var)
        server.serve()
        while True:
            coio.sleep(1)
    except KeyboardInterrupt:
        logging.info('Keyboard interrupt received. Exiting...')
    except Exception, e:
        logging.exception(e)
        raise

if __name__ == '__main__':
    main()
