#!/usr/bin/env python # vim: set shiftwidth=4 softtabstop=4: """Script to run test with local modules """ # Version 2.17 import argparse import logging import os from subprocess import call import sys import ConfigParser # local file import docker_dev_start _logger = logging.getLogger(__name__) __version__ = '0.0.2' __date__ = '2018-04-13' __updated__ = '2018-06-25' def main(argv=None): # IGNORE:C0111 """Parse arguments and docker build """ program_version = __version__ program_build_date = str(__updated__) program_version_message = '%%(prog)s %s (%s)' % ( program_version, program_build_date) program_shortdesc = __doc__.split(".")[0] program_license = '''%s Created by Vincent Hatakeyama on %s. Copyright 2018 XCG Consulting. All rights reserved. Licensed under the MIT License Distributed on an "AS IS" basis without warranties or conditions of any kind, either express or implied. USAGE ''' % (program_shortdesc, str(__date__)) # TODO the script assume it is launched from the parent super project project_path = os.path.realpath('.') project_name = os.path.basename(project_path) if project_name == 'odoo_scripts': logging.fatal( "You must run this script from the super project" " (./odoo_scripts/docker_build.py)") return 1 setup_path = 'setup.cfg' # TODO add a way to store configuration options in a project file # Argument parsing parser = argparse.ArgumentParser( description=program_license, formatter_class=argparse.RawDescriptionHelpFormatter) parser.add_argument( '-V', '--version', action='version', version=program_version_message) parser.add_argument( '-v', '--verbose', dest='verbose', action='count', help="set verbosity level [default: %(default)s]") docker_group = parser.add_mutually_exclusive_group() docker_group.add_argument( '--docker', help="Use docker to launch tests", action='store_true', default=True, dest='docker', ) docker_group.add_argument( '--no-docker', help="Do not use docker to launch tests", action='store_false', dest='docker', ) parser.add_argument( '-d', '--dbname', help="Database name [default: %(default)s]", default='%s_test' % project_name, ) parser.add_argument( '--db_user', help="Odoo database user [default: %(default)s]", default=None, ) parser.add_argument( '--db_password', help="Odoo database password [default: %(default)s]", default=None, ) odoo_log_levels = ['info', 'warn', 'debug'] # TODO there are more parser.add_argument( '--log-level', help="Override odoo log level (for tests and install)", default=None, choices=odoo_log_levels, ) parser.add_argument( '--install-log-level', help="Override odoo log level (for install)", default='warn', choices=odoo_log_levels, ) parser.add_argument( '--test-log-level', help="Override odoo log level (for test)", default=None, choices=odoo_log_levels, ) parser.add_argument( '--no-create-database', dest='createdb', action='store_false', ) parser.add_argument( '--test', help="Modules to test (override defaults from setup.cfg)", default=None, ) parser.add_argument( '-p', '--dbport', help="Database port [default: %(default)s]", default=None, ) # TODO options # - db host/uri (include socket) # - db user for creation/remove nmspc = parser.parse_args(argv) verbose = nmspc.verbose if not verbose: logging.basicConfig(level=logging.WARN) if verbose == 1: logging.basicConfig(level=logging.INFO) if verbose and verbose > 1: logging.basicConfig(level=logging.DEBUG) dbname = nmspc.dbname odoo_db_user = nmspc.db_user odoo_db_password = nmspc.db_password recreate_db = nmspc.createdb extensions = [] install_log_level = ( nmspc.log_level if nmspc.log_level else nmspc.install_log_level) test_log_level = ( nmspc.log_level if nmspc.log_level else nmspc.test_log_level) override_tested_module = nmspc.test dbport = nmspc.dbport # Get parameters from setup file c = ConfigParser.ConfigParser() if not os.path.exists(setup_path): logging.fatal('Missing %s', setup_path) return 12 c.read(setup_path) registry = ( c.has_section('odoo_scripts') and c.has_option('odoo_scripts', 'registry') and c.get('odoo_scripts', 'registry')) or 'dockerhub.xcg.io' project = ( c.has_section('odoo_scripts') and c.has_option('odoo_scripts', 'image') and c.get('odoo_scripts', 'image')) or os.path.basename(project_path) languages = ( c.has_section('odoo_scripts') and c.has_option('odoo_scripts', 'load-language') and c.get('odoo_scripts', 'load-language')) or None image = "%s/%s:latest" % (registry, project) logging.debug("Docker image: %s", image) # read from odoo.conf if it exists sample_conf = 'conf/dev/odoo.conf' if os.path.exists(sample_conf): logging.info('Reading from sample configuration %s', sample_conf) c.read(sample_conf) if not odoo_db_user: odoo_db_user = c.get('options', 'db_user') if ( c.has_option('options', 'unaccent') and c.getboolean('options', 'unaccent') ): extensions.append('unaccent') else: logging.debug('No sample configuration %s', sample_conf) extensions.append('unaccent') # Do stuff if nmspc.docker: # TODO detect that user is member of docker group args = [ '-d', dbname, '--stop-after-init', '--max-cron-threads', '0', '--no-flake8', '--no-dev', ] if odoo_db_user: args.append('--db_user') args.append(odoo_db_user) else: # TODO find from odoo version and conf file pass if odoo_db_password: args.append('--db_password') args.append(odoo_db_password) if dbport: args.append('--dbport') args.append(dbport) docker_dev_start.flake8() if recreate_db: # XXX use psycopg2 # drop database logging.info("Drop any existing database %s", dbname) dropdb = ['dropdb', dbname, '--if-exists', '--no-password'] if dbport: dropdb.append('-p') dropdb.append(dbport) result = call(dropdb) if result: return result # create database logging.info("Create database %s", dbname) if not odoo_db_user: logging.fatal( 'Owner of database is mandatory when creating database') return 14 create_db = ['createdb', dbname, '-O', odoo_db_user, '--no-password'] if dbport: create_db.append('-p') create_db.append(dbport) result = call(create_db) if result: return result # add unaccent if needed for extension in extensions: logging.info("Adding extension %s", extension) result = call([ 'psql', dbname, '-c', 'CREATE EXTENSION %s;' % extension]) if result: return result # TODO start odoo and detect if install fails if nmspc.docker: install_args = list(args) install_args.append('--install-default') if languages: install_args.append('--load-language') install_args.append(languages) if install_log_level: install_args.append('--log-level') install_args.append(install_log_level) docker_dev_start.main(install_args) if result: return result else: raise NotImplementedError # TODO start odoo and detect if test fails if nmspc.docker: test_args = list(args) if override_tested_module: test_args.append('--test') test_args.append(override_tested_module) else: test_args.append('--test-default') if test_log_level: test_args.append('--log-level') test_args.append(test_log_level) return docker_dev_start.main(test_args) else: raise NotImplementedError return 255 if __name__ == "__main__": return_code = main(sys.argv[1:]) if return_code: exit(return_code)