def test_linux_gcc(self): generator = JobGeneratorEnviron( conanfile_wrapper=self.conanfile_wrapper, settings=self.settings, osys="Linux") with context_env(CONAN_OPTIONS=self.options): self.assertEqual(len(list(generator.enumerate_jobs())), 68 * self.options_multiplier) with context_env(CONAN_GCC_VERSIONS="7", CONAN_OPTIONS=self.options): jobs = list(generator.enumerate_jobs()) self.assertEqual(len(jobs), 8 * self.options_multiplier) with context_env(CONAN_GCC_VERSIONS="6,7", CONAN_OPTIONS=self.options): jobs = list(generator.enumerate_jobs()) self.assertEqual(len(jobs), 16 * self.options_multiplier) with context_env(CONAN_GCC_VERSIONS="0", CONAN_OPTIONS=self.options): # Invalid version jobs = list(generator.enumerate_jobs()) self.assertEqual(len(jobs), 0 * self.options_multiplier) with context_env( CONAN_GCC_VERSIONS="0,7", CONAN_OPTIONS=self.options): # Invalid version (fail-safe) jobs = list(generator.enumerate_jobs()) self.assertEqual(len(jobs), 8 * self.options_multiplier)
def test_upload(self): runner = AppveyorRunner(conanfile=self.conanfile, settings=self.settings, osys="Windows") with mock.patch('conan_sword_and_sorcery.ci.runners.base_runner.upload', return_value=0) as mocked_upload: with context_env(CONAN_UPLOAD_ONLY_WHEN_STABLE="True", APPVEYOR_REPO_BRANCH='non-stable-branch'): runner.upload(username='******', channel='testing') with context_env(CONAN_UPLOAD_ONLY_WHEN_STABLE="False", APPVEYOR_REPO_BRANCH='non-stable-branch'): runner.upload(username='******', channel='testing') args, kwargs = mocked_upload.call_args self.assertEqual(kwargs['username'], 'test')
def test_is_stable_branch(self): with self.assertRaises(TypeError): self.runner.is_stable_branch() # Travis always inform about branch name with context_env(TRAVIS_BRANCH='master'): self.assertFalse(self.runner.is_stable_branch()) with context_env(TRAVIS_BRANCH='stable/v1.2.3'): self.assertTrue(self.runner.is_stable_branch())
def test_is_stable_branch(self): with self.assertRaises(TypeError): self.runner.is_stable_branch() # Appveyor always inform about branch name with context_env(APPVEYOR_REPO_BRANCH='master'): self.assertFalse(self.runner.is_stable_branch()) with context_env(APPVEYOR_REPO_BRANCH='stable/v1.2.3'): self.assertTrue(self.runner.is_stable_branch())
def test_is_pull_request(self): with self.assertRaises(AssertionError): self.assertFalse(self.runner.is_pull_request()) # Travis always populates this variable with context_env(TRAVIS_PULL_REQUEST='23'): self.assertTrue(self.runner.is_pull_request()) with context_env(TRAVIS_PULL_REQUEST='false'): self.assertFalse(self.runner.is_pull_request())
def test_one_compiler(self): with context_env(CONAN_VISUAL_VERSIONS='10'): self.assertDictEqual(self.registry.environment_filters(), {'version': { ('Visual Studio', '10'), }}) with context_env(CONAN_VISUAL_VERSIONS='10,12'): self.assertDictEqual(self.registry.environment_filters(), { 'version': {('Visual Studio', '10'), ('Visual Studio', '12')} })
def test_total_macos(self): generator = JobGeneratorEnviron(conanfile_wrapper=self.wrapper, settings=self.settings, osys="Macos") self.assertEqual(len(list(generator.enumerate_jobs())), 32) with context_env(CONAN_APPLE_CLANG_VERSIONS="7.3"): self.assertEqual(len(list(generator.enumerate_jobs())), 8) with context_env(CONAN_APPLE_CLANG_VERSIONS="7.3", CONAN_BUILD_TYPES="Release", CONAN_ARCHS="x86_64"): self.assertEqual(len(list(generator.enumerate_jobs())), 2)
def test_macos(self): generator = JobGeneratorEnviron( conanfile_wrapper=self.conanfile_wrapper, settings=self.settings, osys="Macos") with context_env(CONAN_OPTIONS=self.options): self.assertEqual(len(list(generator.enumerate_jobs())), 32 * self.options_multiplier) with context_env(CONAN_APPLE_CLANG_VERSIONS="8.1", CONAN_OPTIONS=self.options): jobs = list(generator.enumerate_jobs()) self.assertEqual(len(jobs), 8 * self.options_multiplier)
def test_linux_gcc_and_clang(self): generator = JobGeneratorEnviron( conanfile_wrapper=self.conanfile_wrapper, settings=self.settings, osys="Linux") with context_env(CONAN_OPTIONS=self.options): self.assertEqual(len(list(generator.enumerate_jobs())), 68 * self.options_multiplier) with context_env(CONAN_GCC_VERSIONS="7", CONAN_CLANG_VERSIONS="5.0", CONAN_OPTIONS=self.options): jobs = list(generator.enumerate_jobs()) self.assertEqual(len(jobs), 20 * self.options_multiplier)
def test_several_filters(self): with context_env(CONAN_VISUAL_VERSIONS='10', CONAN_VISUAL_RUNTIMES='MT,MTd'): self.assertDictEqual(self.registry.environment_filters(), { 'version': {('Visual Studio', '10')}, 'runtime': {"MT", "MTd"}, })
def test_run_pages_invalid(self, runner_mocked): with context_env( CONAN_TOTAL_PAGES="2", CONAN_CURRENT_PAGE="1", ): with self.assertRaises(AssertionError): self.assertEqual(run(conanfile=self.conanfile, dry_run=False), 0)
def test_total_linux(self): generator = JobGeneratorEnviron(conanfile_wrapper=self.wrapper, settings=self.settings, osys="Linux") self.assertEqual(len(list(generator.enumerate_jobs())), 1) with context_env(CONAN_OPTIONS='shared'): all_jobs = list(generator.enumerate_jobs()) self.assertEqual(len(all_jobs), 2) self.assertTrue(isinstance(all_jobs[0][0], NoCompiler)) self.assertTrue(isinstance(all_jobs[1][0], NoCompiler)) with context_env(CONAN_BUILD_TYPES='Debug'): self.assertEqual(len(list(generator.enumerate_jobs())), 1) with context_env(CONAN_BUILD_TYPES='Debug', CONAN_GCC_VERSIONS='4.7'): self.assertEqual(len(list(generator.enumerate_jobs())), 1)
def test_upload(self, remote_auth_mocked, cmd_mocked): with context_env(CONAN_UPLOAD='http://my.remote.com', CONAN_USERNAME="******", CONAN_PASSWORD="******"): upload(recipe=self.recipe, username="******", channel="testing", dry_run=False)
def test_macos(self): generator = JobGeneratorEnviron( conanfile_wrapper=self.conanfile_wrapper, settings=self.settings, osys="Macos") with context_env(CONAN_OPTIONS='shared'): self.assertEqual(len(list(generator.enumerate_jobs())), 1 * self.options_multiplier)
def test_dry_run(self): runner = AppveyorRunner(conanfile=self.conanfile, settings=self.settings, osys="Windows", dry_run=True) with context_env(CONAN_GCC_VERSIONS="6", CONAN_ARCHS='x86', CONAN_BUILD_PACKAGES='pckg1'): compiler, options = list(runner.enumerate_jobs())[0] with profile_for(compiler=compiler) as profile_file: runner.set_compiler(compiler) runner.set_profile(profile_file) r = runner.run(options={'shared': True}, username='******', channel='testing') self.assertEqual(r, DRY_RUN)
def test_is_upload_requested(self): runner = AppveyorRunner(conanfile=self.conanfile, settings=self.settings, osys="Windows") with context_env(CONAN_UPLOAD_ONLY_WHEN_STABLE="True", APPVEYOR_REPO_BRANCH='non-stable-branch'): self.assertFalse(runner.is_stable_branch()) self.assertFalse(runner.is_upload_requested()) with context_env(CONAN_UPLOAD_ONLY_WHEN_STABLE="False", APPVEYOR_REPO_BRANCH='non-stable-branch'): self.assertFalse(runner.is_stable_branch()) self.assertTrue(runner.is_upload_requested()) with context_env(CONAN_UPLOAD_ONLY_WHEN_STABLE="False", APPVEYOR_REPO_BRANCH='stable/v1.2.3'): self.assertTrue(runner.is_stable_branch()) self.assertTrue(runner.is_upload_requested()) with context_env(CONAN_UPLOAD_ONLY_WHEN_STABLE="True", APPVEYOR_REPO_BRANCH='stable/v1.2.3'): self.assertTrue(runner.is_stable_branch()) self.assertTrue(runner.is_upload_requested())
def test_existing_variable(self): key1 = list(os.environ.keys())[0] value1 = os.environ[key1] value_for_testing = "new-value-for-testing" self.assertNotEqual(value1, value_for_testing) with context_env(**{key1: value_for_testing}): print(os.environ[key1]) self.assertIn(key1, os.environ) self.assertEqual(os.environ[key1], value_for_testing) self.assertEqual(os.environ[key1], value1)
def test_multi_pattern(self): with context_env(CONAN_VAR1="value", APPVEYOR_VAR2="value2", APPVEYOR_VAR="other"): pattern = r'^(CONAN_.*)|(^APPVEYOR_[A-Z]+)$' self.assertFalse(re.match(pattern, "APPVEYOR_VAR2")) with clean_context_env(pattern=pattern): self.assertNotIn("CONAN_VAR1", os.environ.keys()) self.assertNotIn("APPVEYOR_VAR", os.environ.keys()) self.assertIn("APPVEYOR_VAR2", os.environ.keys())
def test_linux(self): generator = JobGeneratorEnviron( conanfile_wrapper=self.conanfile_wrapper, settings=self.settings, osys="Linux") self.assertEqual(len(list(generator.enumerate_jobs())), 68) with context_env(CONAN_OPTIONS='opt1'): self.assertEqual( len(list(generator.enumerate_jobs())), 68 ) # Same number, because opt1 has two values and all recipes with opt1=False are discarded.
def test_conan_pattern(self): with context_env(CONAN_VAR1="value", CONAN_VAR2="value2"): self.assertIn("CONAN_VAR1", os.environ.keys()) self.assertIn("CONAN_VAR2", os.environ.keys()) with clean_context_env(pattern=r'CONAN_.*'): self.assertNotIn("CONAN_VAR1", os.environ.keys()) self.assertNotIn("CONAN_VAR2", os.environ.keys()) self.assertIn("CONAN_VAR1", os.environ.keys()) self.assertEqual(os.environ["CONAN_VAR1"], "value") self.assertIn("CONAN_VAR2", os.environ.keys()) self.assertEqual(os.environ["CONAN_VAR2"], "value2")
def test_run_fail(self): runner = AppveyorRunner(conanfile=self.conanfile, settings=self.settings, osys="Windows") with context_env(CONAN_GCC_VERSIONS="6", CONAN_ARCHS='x86', CONAN_BUILD_PACKAGES='pckg1'): compiler, options = list(runner.enumerate_jobs())[0] with profile_for(compiler=compiler) as profile_file: runner.set_compiler(compiler) runner.set_profile(profile_file) with mock.patch('conan_sword_and_sorcery.ci.runners.base_runner.cmd', return_value=1) as mocked_cmd: r = runner.run(options={'shared': True}, username='******', channel='testing') self.assertEqual(r, FAIL)
def test_total_windows(self): generator = JobGeneratorEnviron(conanfile_wrapper=self.wrapper, settings=self.settings, osys="Windows") self.assertEqual(len(list(generator.enumerate_jobs())), 64) # Visual Studio + MinGW # Just Visual Studio with context_env(CONAN_VISUAL_VERSIONS='12'): self.assertEqual(len(list(generator.enumerate_jobs())), 8) with context_env(CONAN_VISUAL_VERSIONS='12', CONAN_BUILD_TYPES='Debug'): self.assertEqual(len(list(generator.enumerate_jobs())), 4) with context_env(CONAN_VISUAL_VERSIONS='12', CONAN_BUILD_TYPES='Debug', CONAN_OPTIONS='build_gmock,shared'): self.assertEqual(len(list(generator.enumerate_jobs())), 32) with context_env(CONAN_VISUAL_VERSIONS='12', CONAN_BUILD_TYPES='Debug', CONAN_VISUAL_RUNTIMES="MT"): self.assertEqual(len(list(generator.enumerate_jobs())), 0) with context_env(CONAN_VISUAL_VERSIONS='12', CONAN_BUILD_TYPES='Debug', CONAN_VISUAL_RUNTIMES="MTd"): self.assertEqual(len(list(generator.enumerate_jobs())), 2) with context_env(CONAN_BUILD_TYPES='Debug', CONAN_GCC_VERSIONS='4.7'): self.assertEqual(len(list(generator.enumerate_jobs())), 0) # Just MinGW with context_env(CONAN_MINGW_VERSIONS='4.9'): self.assertEqual(len(list(generator.enumerate_jobs())), 8) with context_env(CONAN_MINGW_VERSIONS='4.9', CONAN_MINGW_EXCEPTIONS="seh"): self.assertEqual(len(list(generator.enumerate_jobs())), 8) with context_env(CONAN_MINGW_VERSIONS='4.9', CONAN_MINGW_EXCEPTIONS="seh", CONAN_MINGW_THREADS="posix"): self.assertEqual(len(list(generator.enumerate_jobs())), 4)
def test_total_linux(self): generator = JobGeneratorEnviron(conanfile_wrapper=self.wrapper, settings=self.settings, osys="Linux") self.assertEqual(len(list(generator.enumerate_jobs())), 68) # Just GCC with context_env(CONAN_GCC_VERSIONS="7"): self.assertEqual(len(list(generator.enumerate_jobs())), 8) with context_env(CONAN_GCC_VERSIONS="7", CONAN_BUILD_TYPES='Debug'): self.assertEqual(len(list(generator.enumerate_jobs())), 4) with context_env(CONAN_GCC_VERSIONS="7", CONAN_BUILD_TYPES='Debug', CONAN_OPTIONS='build_gmock,shared'): self.assertEqual(len(list(generator.enumerate_jobs())), 32) # Just CLANG with context_env(CONAN_CLANG_VERSIONS="5.0"): self.assertEqual(len(list(generator.enumerate_jobs())), 12) with context_env(CONAN_CLANG_VERSIONS="5.0", CONAN_BUILD_TYPES='Debug'): self.assertEqual(len(list(generator.enumerate_jobs())), 6) with context_env(CONAN_CLANG_VERSIONS="5.0", CONAN_BUILD_TYPES='Debug', CONAN_OPTIONS='build_gmock,shared'): self.assertEqual(len(list(generator.enumerate_jobs())), 48)
def test_upload(self, DockerHelperMocked): runner = TravisRunner(conanfile=self.conanfile, settings=self.settings, osys="Linux") with context_env(CONAN_GCC_VERSIONS="6", CONAN_ARCHS='x86', CONAN_BUILD_PACKAGES='pckg1'): compiler, options = list(runner.enumerate_jobs())[0] with profile_for(compiler=compiler) as profile_file: runner.set_compiler(compiler) with mock.patch( 'conan_sword_and_sorcery.ci.runners.base_runner.upload', return_value=0) as mocked_upload: with context_env(CONAN_UPLOAD_ONLY_WHEN_STABLE="True", TRAVIS_BRANCH='non-stable-branch'): runner.upload(username='******', channel='testing') with context_env(CONAN_UPLOAD_ONLY_WHEN_STABLE="False", TRAVIS_BRANCH='non-stable-branch'): runner.upload(username='******', channel='testing') args, kwargs = mocked_upload.call_args self.assertEqual(kwargs['username'], 'test')
def test_default_profile_list(self): tmp_dir = tempfile.mkdtemp() try: # Generate a couple of random profiles profiles_dir = os.path.join(tmp_dir, '.conan', 'profiles') os.makedirs(profiles_dir) with profile_for(CompilerClangApple(arch='x86', build_type='Release', version='7.3', libcxx='libc++'), basepath=profiles_dir) as _1: with profile_for(CompilerClangLinux(arch='x86', build_type='Release', version='4.0', libcxx='libstdc++'), basepath=profiles_dir) as _2: with context_env(CONAN_USER_HOME=tmp_dir): generator = JobGeneratorProfiles(conanfile_wrapper=self.conanfile_wrapper, settings=self.settings, osys=platform_system()) self.assertEqual(len(list(generator.enumerate_jobs())), 2) finally: shutil.rmtree(tmp_dir, ignore_errors=True)
def main(): sys.stdout.write("=== Conan - Sword & Sorcery ===\n") parser = argparse.ArgumentParser(description='Run CI for given conanfile') parser.add_argument('conanfile', help='Path to conanfile.py') parser.add_argument("-v", "--verbose", dest="verbose_count", action="count", default=0, help="increases log verbosity for each occurence.") parser.add_argument("--dry-run", dest="dry_run", action='store_true', default=False, help="do not create package (won't compile recipes)") parser.add_argument("--options", dest="conan_options", help="comma separated list of options from de conanfile.py to conjugate") parser.add_argument("--username", dest="conan_username", help="Username for package reference xxx/x.y.z@<username>/xxxx") parser.add_argument("--channel", dest="conan_channel", help="Channel for package reference xxx/x.y.z@xxxxxx/<channel>") args = parser.parse_args() # Configure logging my_formatter = CLIFormatter('[%(levelname)-8s] %(name)-36s (%(lineno)d): %(message)s') handler = logging.StreamHandler() handler.setFormatter(my_formatter) # logging.basicConfig(stream=sys.stderr, level=logging.INFO, # format='[%(levelname)-8s] %(name)s (%(lineno)d): %(message)s') log.setLevel(max(3 - args.verbose_count, 0) * 10) log.addHandler(handler) # Check that the file exists conanfile = os.path.abspath(args.conanfile) if not os.path.exists(conanfile): sys.stderr.write("Conanfile '{}' does not exists or it is inaccessible\n".format(conanfile)) exit(-1) # May override environament (options) from command line env_vars = {} if args.conan_options: log.info("Override 'CONAN_OPTIONS' env variable with '{}'".format(args.conan_options)) env_vars["CONAN_OPTIONS"] = args.conan_options if args.conan_username: log.info("Override 'CONAN_USERNAME' env variable with '{}'".format(args.conan_username)) env_vars["CONAN_USERNAME"] = args.conan_username if args.conan_channel: log.info("Override 'CONAN_CHANNEL' env variable with '{}'".format(args.conan_channel)) env_vars["CONAN_CHANNEL"] = args.conan_channel with context_env(**env_vars): r = run(conanfile=conanfile, dry_run=args.dry_run) sys.stdout.write("=====\n") return r
def test_run_remotes_and_upload(self, runner_mocked): initial_remotes = set([it[1] for it in parse_remote_list()]) class Runner4TestingEnvCheck(Runner4Testing): def run(_, options, username, channel): remotes = set([it[1] for it in parse_remote_list()]) self.assertEqual(len(initial_remotes) + 2 + 1, len(remotes)) return SUCCESS runner_mocked.return_value = Runner4TestingEnvCheck(run_return=SUCCESS) with context_env(CONAN_REMOTES="http://remote1.com,http://remote2.com", CONAN_UPLOAD="http://remote3.com"): self.assertEqual(run(conanfile=self.conanfile, dry_run=False), 0)
def test_run_fail(self, DockerHelperMocked): runner = TravisRunner(conanfile=self.conanfile, settings=self.settings, osys="Linux") with context_env(CONAN_GCC_VERSIONS="6", CONAN_ARCHS='x86', CONAN_BUILD_PACKAGES='pckg1'): compiler, options = list(runner.enumerate_jobs())[0] with profile_for(compiler=compiler) as profile_file: runner.set_compiler(compiler) runner.set_profile(profile_file) r = runner.run(options={'shared': True}, username='******', channel='testing') self.assertEqual(r, FAIL)
def test_temporary_env_file(self): with context_env(CONAN_VAR="conan_var", TRAVIS_VAR="travis_var", APPVEYOR_VAR="appveyor_var"): with temporary_env_file() as tmp_file: vars = dict([ line.strip().split('=') for line in open(tmp_file, 'r').readlines() ]) self.assertIn('CONAN_VAR', vars) self.assertEqual(vars['CONAN_VAR'], 'conan_var') self.assertIn('TRAVIS_VAR', vars) self.assertEqual(vars['TRAVIS_VAR'], 'travis_var') self.assertNotIn('APPVEYOR_VAR', vars) # Docker is available only for TRAVIS
def test_pagination(self): generator = JobGeneratorEnviron(conanfile_wrapper=self.wrapper, settings=self.settings, osys="Windows") with context_env(CONAN_VISUAL_VERSIONS='12'): all_jobs = list(generator.enumerate_jobs()) self.assertEqual(len(all_jobs), 8) page_list = JobGeneratorEnviron.paginate(all_jobs, page=1, page_size=5) self.assertEqual(len(page_list), 3) page_list = JobGeneratorEnviron.paginate(all_jobs, page=6, page_size=5) self.assertEqual(len(page_list), 0)