diff --git a/module_build_service/builder.py b/module_build_service/builder.py index c6767413..1f894850 100644 --- a/module_build_service/builder.py +++ b/module_build_service/builder.py @@ -188,6 +188,8 @@ class GenericBuilder(six.with_metaclass(ABCMeta)): """ if backend == "koji": return KojiModuleBuilder.repo_from_tag(config, tag_name, arch) + if backend == "copr": + return CoprModuleBuilder.repo_from_tag(config, tag_name, arch) else: raise ValueError("Builder backend='%s' not recognized" % backend) @@ -1026,3 +1028,17 @@ class MockModuleBuilder(GenericBuilder): def get_disttag_srpm(disttag): # @FIXME return KojiModuleBuilder.get_disttag_srpm(disttag) + + @classmethod + def repo_from_tag(cls, config, tag_name, arch): + from copr.client import CoprClient + + # @TODO get the correct user + # Premise is that tag_name is in name-version-release format + owner, nvr = "@copr", tag_name + cl = CoprClient.create_from_file_config(config.copr_config) + response = cl.get_module_repo(owner, nvr).data + + if response["output"] == "notok": + raise ValueError(response["error"]) + return response["repo"] diff --git a/tests/test_copr.py b/tests/test_copr.py new file mode 100644 index 00000000..ac9627a7 --- /dev/null +++ b/tests/test_copr.py @@ -0,0 +1,65 @@ +# Copyright (c) 2016 Red Hat, Inc. +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in all +# copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +# SOFTWARE. +# +# Written by Jakub Kadlcik + + +import unittest +import mock +import module_build_service.builder +from copr.client import CoprClient + + +class TestCoprBuilder(unittest.TestCase): + + def setUp(self): + self.config = mock.Mock() + self.config.copr_config = "/etc/rida/copr.conf" + + @mock.patch.object(CoprClient, "get_module_repo") + def test_tag_to_repo(self, get_module_repo): + # Mock the CoprClient.get_module_repo to return something, without requesting a Copr instance + def get_module_repo_mock(owner, nvr): + return ResponseMock({ + "output": "ok", + "repo": "http://copr-be-instance/results/{}/{}/modules".format(owner, nvr) + }) + get_module_repo.side_effect = get_module_repo_mock + + repo = module_build_service.builder.GenericBuilder.tag_to_repo( + "copr", self.config, "foo-module-name-0.25-9", None) + self.assertEquals(repo, "http://copr-be-instance/results/@copr/foo-module-name-0.25-9/modules") + + @mock.patch.object(CoprClient, "get_module_repo") + def test_non_existing_tag_to_repo(self, get_module_repo): + # Let's pretend that CoprClient.get_module_repo couldn't find the project on Copr instance + get_module_repo.return_value = ResponseMock({"output": "notok", "error": "some error"}) + self.assertRaises(ValueError, + lambda: module_build_service.builder.GenericBuilder.tag_to_repo( + "copr", self.config, None, None)) + + +class ResponseMock(object): + def __init__(self, data): + self._data = data + + @property + def data(self): + return self._data