b047a20135
Buildah and Podman will replace Docker. This patch will be used by tripleoclient when running: $ openstack overcloud container image build --use-buildah When using Buildah, the kolla_builder will, in that order: 1) Generate container templates but not actually build the images. The directories are generated by kolla-build and containers files like Dockerfiles and such. 2) Generate container dependencies and build a dictionary, later used by the new BuildahBuilder. In this patch, we introduce a Class for builders. For now, we only have BuildahBuilder but later we will refactor kolla_builder. The BuildahBuilder has in charge of: 1) Build containers using "buildah bud". This command is used because Kolla uses Dockerfiles to build images. Each image build is logged in the directory that contains the Dockerfile. During the build, logging displays the container that is being built and also the buildah command that is used. The image layers that don't have childs are multi-threaded to accelerate the build. We don't go over 8 builds at the same time otherwise Buildah struggles with the locks too hard. We also setup a timeout of 30 minutes for the workers to report back. For example: base └─openstack-base ├─nova-base │ ├─nova-api │ └─nova-conductor └─neutron-base └─neutron-dhcp └─multipathd └─crond The builder will first build "base" then: - build openstack-base, multipathd and crond in same time. - build nova-base and neutron-base in same time - build nova-api, nova-conductor in same time - etc 2) Push containers to a Docker registry. We'll support more than Docker registries, but later. Note: All commands are executed using processutils from oslo_concurrency which is pretty and rock solid. Note2: kolla_builder will be refactored to use the new Builder class. This patch is an initial support for Buildah, improvements will come later. Co-Authored-By: Alex Schultz <aschultz@redhat.com> Co-Authored-By: Christophe Fontaine <cfontain@redhat.com> blueprint podman-support Change-Id: Ieff41a5f84456530b4621218b01f3b546cd867bf
82 lines
3.3 KiB
Python
82 lines
3.3 KiB
Python
# Copyright (c) 2019 Red Hat, Inc.
|
|
#
|
|
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
# you may not use this file except in compliance with the License.
|
|
# You may obtain a copy of the License at
|
|
#
|
|
# http://www.apache.org/licenses/LICENSE-2.0
|
|
#
|
|
# Unless required by applicable law or agreed to in writing, software
|
|
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
|
# implied.
|
|
# See the License for the specific language governing permissions and
|
|
# limitations under the License.
|
|
|
|
"""Unit tests for utils.process."""
|
|
|
|
|
|
import os
|
|
|
|
import mock
|
|
from oslo_concurrency import processutils
|
|
|
|
from tripleo_common.tests import base
|
|
from tripleo_common.utils import process
|
|
|
|
|
|
class ExecuteTestCase(base.TestCase):
|
|
# Allow calls to process.execute() and related functions
|
|
block_execute = False
|
|
|
|
@mock.patch.object(processutils, 'execute', autospec=True)
|
|
@mock.patch.object(os.environ, 'copy', return_value={}, autospec=True)
|
|
def test_execute_use_standard_locale_no_env_variables(self, env_mock,
|
|
execute_mock):
|
|
process.execute('foo', use_standard_locale=True)
|
|
execute_mock.assert_called_once_with('foo',
|
|
env_variables={'LC_ALL': 'C'})
|
|
|
|
@mock.patch.object(processutils, 'execute', autospec=True)
|
|
def test_execute_use_standard_locale_with_env_variables(self,
|
|
execute_mock):
|
|
process.execute('foo', use_standard_locale=True,
|
|
env_variables={'foo': 'bar'})
|
|
execute_mock.assert_called_once_with('foo',
|
|
env_variables={'LC_ALL': 'C',
|
|
'foo': 'bar'})
|
|
|
|
@mock.patch.object(processutils, 'execute', autospec=True)
|
|
def test_execute_not_use_standard_locale(self, execute_mock):
|
|
process.execute('foo', use_standard_locale=False,
|
|
env_variables={'foo': 'bar'})
|
|
execute_mock.assert_called_once_with('foo',
|
|
env_variables={'foo': 'bar'})
|
|
|
|
@mock.patch.object(process, 'LOG', autospec=True)
|
|
def _test_execute_with_log_stdout(self, log_mock, log_stdout=None):
|
|
with mock.patch.object(
|
|
processutils, 'execute', autospec=True) as execute_mock:
|
|
execute_mock.return_value = ('stdout', 'stderr')
|
|
if log_stdout is not None:
|
|
process.execute('foo', log_stdout=log_stdout)
|
|
else:
|
|
process.execute('foo')
|
|
execute_mock.assert_called_once_with('foo')
|
|
name, args, kwargs = log_mock.debug.mock_calls[1]
|
|
if log_stdout is False:
|
|
self.assertEqual(2, log_mock.debug.call_count)
|
|
self.assertNotIn('stdout', args[0])
|
|
else:
|
|
self.assertEqual(3, log_mock.debug.call_count)
|
|
self.assertIn('stdout', args[0])
|
|
|
|
def test_execute_with_log_stdout_default(self):
|
|
self._test_execute_with_log_stdout()
|
|
|
|
def test_execute_with_log_stdout_true(self):
|
|
self._test_execute_with_log_stdout(log_stdout=True)
|
|
|
|
def test_execute_with_log_stdout_false(self):
|
|
self._test_execute_with_log_stdout(log_stdout=False)
|