Skip to content

Commit

Permalink
Merge pull request #92 from bluesliverx/main
Browse files Browse the repository at this point in the history
Fix references to docker registry image and fix docs
  • Loading branch information
bluesliverx authored Nov 8, 2023
2 parents 290337c + 12fe87c commit 6a8b409
Showing 4 changed files with 35 additions and 26 deletions.
9 changes: 6 additions & 3 deletions buildrunner/__init__.py
Original file line number Diff line number Diff line change
@@ -582,9 +582,12 @@ def run(self): # pylint: disable=too-many-statements,too-many-branches,too-many

exit_explanation = None
try: # pylint: disable=too-many-nested-blocks
with MultiplatformImageBuilder(keep_images=not self.cleanup_images,
temp_dir=self.global_config.get_temp_dir(),
disable_multi_platform=self.disable_multi_platform) as multi_platform:
with MultiplatformImageBuilder(
docker_registry=self.global_config.get_docker_registry(),
keep_images=not self.cleanup_images,
temp_dir=self.global_config.get_temp_dir(),
disable_multi_platform=self.disable_multi_platform,
) as multi_platform:
if not os.path.exists(self.build_results_dir):
# create a new results dir
os.mkdir(self.build_results_dir)
37 changes: 21 additions & 16 deletions buildrunner/docker/multiplatform_image_builder.py
Original file line number Diff line number Diff line change
@@ -11,7 +11,7 @@
from platform import machine, system
import shutil
import tempfile
from typing import List
from typing import List, Optional

import python_on_whales
from python_on_whales import docker
@@ -117,13 +117,17 @@ def __repr__(self):
class MultiplatformImageBuilder: # pylint: disable=too-many-instance-attributes
"""Multiple platform image builder"""

# pylint: disable=too-many-arguments
def __init__(
self,
docker_registry: Optional[str] = None,
use_local_registry: bool = True,
keep_images: bool = False,
temp_dir: str = os.getcwd(),
disable_multi_platform: bool = False,):
self._registry_info = None
disable_multi_platform: bool = False,
):
self._docker_registry = docker_registry
self._mp_registry_info = None
self._use_local_registry = use_local_registry
self._keep_images = keep_images
self._temp_dir = temp_dir
@@ -164,12 +168,12 @@ def disable_multi_platform(self) -> int:
@property
def registry_ip(self) -> int:
"""Returns the ip address of the local registry"""
return self._registry_info.ip_addr
return self._mp_registry_info.ip_addr

@property
def registry_port(self) -> int:
"""Returns the port of the local registry"""
return self._registry_info.port
return self._mp_registry_info.port

@property
def tagged_images_names(self) -> List[str]:
@@ -182,7 +186,7 @@ def is_multiplatform(self, name: str) -> bool:

def registry_address(self) -> str:
"""Returns the address of the local registry"""
return f"{self._registry_info.ip_addr}:{self._registry_info.port}"
return f"{self._mp_registry_info.ip_addr}:{self._mp_registry_info.port}"

def _start_local_registry(self):
"""
@@ -193,7 +197,10 @@ def _start_local_registry(self):
"""
if not self._local_registry_is_running:
logger.debug("Starting local docker registry")
container = docker.run("registry", detach=True, publish_all=True)
image = 'registry'
if self._docker_registry:
image = f'{self._docker_registry}/{image}'
container = docker.run(image, detach=True, publish_all=True)
ports = container.network_settings.ports

# If any assert fails something changed in the registry image and we need to update this code
@@ -204,9 +211,9 @@ def _start_local_registry(self):
assert ports.get("5000/tcp")[0].get('HostIp') == "0.0.0.0", \
f"Expected HostIp to be 0.0.0.0 but got {ports.get('5000/tcp')[0].get('HostIp')}"

self._registry_info = RegistryInfo(container.name, "localhost", ports.get("5000/tcp")[0].get("HostPort"))
self._mp_registry_info = RegistryInfo(container.name, "localhost", ports.get("5000/tcp")[0].get("HostPort"))
self._local_registry_is_running = True
logger.debug(f"Started local registry {self._registry_info}")
logger.debug(f"Started local registry {self._mp_registry_info}")
else:
logger.warning("Local registry is already running")

@@ -215,11 +222,11 @@ def _stop_local_registry(self):
Stops and removes the local registry along with any images
"""
if self._local_registry_is_running:
logger.debug(f"Stopping and removing local registry {self._registry_info}")
logger.debug(f"Stopping and removing local registry {self._mp_registry_info}")
try:
docker.remove(self._registry_info.name, volumes=True, force=True)
docker.remove(self._mp_registry_info.name, volumes=True, force=True)
except python_on_whales.exceptions.NoSuchContainer as err:
logger.error(f"Failed to stop and remove local registry {self._registry_info.name}: {err}")
logger.error(f"Failed to stop and remove local registry {self._mp_registry_info.name}: {err}")
self._local_registry_is_running = False
else:
logger.warning("Local registry is not running when attempting to stop it")
@@ -379,7 +386,6 @@ def build_multiple_images(
tags: List[str] = None,
push=True,
do_multiprocessing: bool = True,
docker_registry: str = None,
build_args: dict = None,
inject: dict = None,
) -> List[ImageInfo]:
@@ -394,7 +400,6 @@ def build_multiple_images(
tags (List[str], optional): The tags to apply to the image. Defaults to None.
push (bool, optional): Whether to push the image to the registry. Defaults to True.
do_multiprocessing (bool, optional): Whether to use multiprocessing to build the images. Defaults to True.
docker_registry (str, optional): The docker registry to push the image to. Defaults to None.
build_args (dict, optional): The build args to pass to docker. Defaults to None.
inject (dict, optional): The files to inject into the build context. Defaults to None.
@@ -409,7 +414,7 @@ def get_path(file):

if build_args is None:
build_args = {}
build_args['DOCKER_REGISTRY'] = docker_registry
build_args['DOCKER_REGISTRY'] = self._docker_registry

# It is not valid to pass None for the path when building multi-platform images
if not path:
@@ -429,7 +434,7 @@ def get_path(file):
# Updates name to be compatible with docker
image_prefix = "buildrunner-mp"
santized_name = f"{image_prefix}-{mp_image_name.replace('/', '-').replace(':', '-')}"
base_image_name = f"{self._registry_info.ip_addr}:{self._registry_info.port}/{santized_name}"
base_image_name = f"{self._mp_registry_info.ip_addr}:{self._mp_registry_info.port}/{santized_name}"

# Keeps track of the built images {name: [ImageInfo(image_names)]]}
manager = Manager()
7 changes: 4 additions & 3 deletions buildrunner/steprunner/tasks/build.py
Original file line number Diff line number Diff line change
@@ -91,6 +91,8 @@ def __init__(
)

for src_glob, dest_path in self.config.get('inject', {}).items():
if not dest_path:
dest_path = ''
_src_glob = self.step_runner.build_runner.global_config.to_abs_path(src_glob)
xsglob = glob.glob(_src_glob)
if not xsglob:
@@ -102,7 +104,7 @@ def __init__(
# Only one source - destination may be directory or filename - check for a trailing
# '/' and treat it accordingly.
source_file = xsglob[0]
if dest_path[-1] == '/' or os.path.split(dest_path)[-1] in ('.', '..'):
if dest_path and (dest_path[-1] == '/' or os.path.split(dest_path)[-1] in ('.', '..')):
self.to_inject[source_file] = os.path.normpath(
os.path.join(
'.',
@@ -219,10 +221,9 @@ def run(self, context):
path=self.path,
file=self.dockerfile,
mp_image_name=self.get_unique_build_name(),
docker_registry=docker_registry,
build_args=self.buildargs,
inject=self.to_inject,
)
)

number_of_images = len(self.platforms)

8 changes: 4 additions & 4 deletions tests/test_multiplatform.py
Original file line number Diff line number Diff line change
@@ -33,7 +33,7 @@ def test_start_local_registry():

with MultiplatformImageBuilder() as mp:
mp._start_local_registry()
registry_name = mp._registry_info.name
registry_name = mp._mp_registry_info.name

# Check that the registry is running and only one is found with that name
registry_container = docker.ps(filters={"name": registry_name})
@@ -64,7 +64,7 @@ def test_start_local_registry_on_build():

with MultiplatformImageBuilder() as mp:
# Check that the registry is NOT running
assert mp._registry_info is None
assert mp._mp_registry_info is None
assert mp._local_registry_is_running is False

# Building should start the registry
@@ -77,7 +77,7 @@ def test_start_local_registry_on_build():


# Check that the registry is running and only one is found with that name
registry_name = mp._registry_info.name
registry_name = mp._mp_registry_info.name
first_registry_name = registry_name
registry_container = docker.ps(filters={"name": registry_name})
assert len(registry_container) == 1
@@ -102,7 +102,7 @@ def test_start_local_registry_on_build():
file=f'{test_path}/Dockerfile',
do_multiprocessing=True)

registry_name = mp._registry_info.name
registry_name = mp._mp_registry_info.name
assert first_registry_name == registry_name

# Check that the registry is stopped and cleaned up

0 comments on commit 6a8b409

Please sign in to comment.