From b39a050f464a35a33fbadc4e0b79b9d77b5a2ed6 Mon Sep 17 00:00:00 2001 From: Reed Hamilton Date: Fri, 10 Apr 2026 16:59:51 -0700 Subject: [PATCH] feat: add ability to pass docker build params in template --- samcli/lib/build/app_builder.py | 3 +++ samcli/lib/samlib/resource_metadata_normalizer.py | 3 +++ samcli/local/docker/image_build_client.py | 14 ++++++++++++++ 3 files changed, 20 insertions(+) diff --git a/samcli/lib/build/app_builder.py b/samcli/lib/build/app_builder.py index ab49a8bb77..25ee223b87 100644 --- a/samcli/lib/build/app_builder.py +++ b/samcli/lib/build/app_builder.py @@ -434,6 +434,7 @@ def _build_lambda_image(self, function_name: str, metadata: Dict, architecture: docker_tag = f"{image_name.lower()}:{tag}" docker_build_target = metadata.get("DockerBuildTarget", None) docker_build_args = metadata.get("DockerBuildArgs", {}) + docker_build_extra_params = metadata.get("DockerBuildExtraParams", None) if not dockerfile or not docker_context: raise DockerBuildFailed("Docker file or Docker context metadata are missed.") @@ -460,6 +461,8 @@ def _build_lambda_image(self, function_name: str, metadata: Dict, architecture: } if docker_build_target: build_args["target"] = cast(str, docker_build_target) + if docker_build_extra_params: + build_args["extra_params"] = docker_build_extra_params try: if not self._image_build_client: diff --git a/samcli/lib/samlib/resource_metadata_normalizer.py b/samcli/lib/samlib/resource_metadata_normalizer.py index f1bb101888..b2a471c68a 100644 --- a/samcli/lib/samlib/resource_metadata_normalizer.py +++ b/samcli/lib/samlib/resource_metadata_normalizer.py @@ -25,12 +25,14 @@ IMAGE_ASSET_PROPERTY = "Code.ImageUri" ASSET_DOCKERFILE_PATH_KEY = "aws:asset:dockerfile-path" ASSET_DOCKERFILE_BUILD_ARGS_KEY = "aws:asset:docker-build-args" +ASSET_DOCKER_BUILD_EXTRA_PARAMS_KEY = "aws:asset:docker-build-extra-params" SAM_RESOURCE_ID_KEY = "SamResourceId" SAM_IS_NORMALIZED = "SamNormalized" SAM_METADATA_DOCKERFILE_KEY = "Dockerfile" SAM_METADATA_DOCKER_CONTEXT_KEY = "DockerContext" SAM_METADATA_DOCKER_BUILD_ARGS_KEY = "DockerBuildArgs" +SAM_METADATA_DOCKER_BUILD_EXTRA_PARAMS_KEY = "DockerBuildExtraParams" ASSET_BUNDLED_METADATA_KEY = "aws:asset:is-bundled" SAM_METADATA_SKIP_BUILD_KEY = "SkipBuild" @@ -189,6 +191,7 @@ def _extract_image_asset_metadata(metadata): SAM_METADATA_DOCKERFILE_KEY: str(dockerfile_path.as_posix()), SAM_METADATA_DOCKER_CONTEXT_KEY: str(asset_path), SAM_METADATA_DOCKER_BUILD_ARGS_KEY: metadata.get(ASSET_DOCKERFILE_BUILD_ARGS_KEY, {}), + SAM_METADATA_DOCKER_BUILD_EXTRA_PARAMS_KEY: metadata.get(ASSET_DOCKER_BUILD_EXTRA_PARAMS_KEY, None), } @staticmethod diff --git a/samcli/local/docker/image_build_client.py b/samcli/local/docker/image_build_client.py index 7d3aa2f3c5..675a1266c5 100644 --- a/samcli/local/docker/image_build_client.py +++ b/samcli/local/docker/image_build_client.py @@ -39,6 +39,7 @@ def build_image( platform: Optional[str] = None, target: Optional[str] = None, rm: bool = True, + extra_params: Optional[list[str]] = None, ) -> Generator[Dict[str, Any], None, None]: """ Build a container image from a Dockerfile. @@ -59,6 +60,8 @@ def build_image( Build target stage in multi-stage Dockerfile rm : bool Remove intermediate containers after build (default: True) + extra_params : list of str, optional + Extra CLI flags (e.g., ["--ssh", "default"]). Only supported by CLIBuildClient Yields ------ @@ -119,6 +122,7 @@ def build_image( platform: Optional[str] = None, target: Optional[str] = None, rm: bool = True, + extra_params: Optional[list[str]] = None, ) -> Generator[Dict[str, Any], None, None]: """Build image using docker-py SDK""" build_kwargs = { @@ -135,6 +139,12 @@ def build_image( if target is not None: build_kwargs["target"] = target + if extra_params: + LOG.warning( + "DockerBuildExtraParams are not supported with the SDK build client and will be ignored. " + "Use --use-buildkit to enable CLI-based builds." + ) + _, build_logs = self.container_client.images.build(**build_kwargs) return build_logs # type: ignore[no-any-return] @@ -159,6 +169,7 @@ def build_image( platform: Optional[str] = None, target: Optional[str] = None, rm: bool = True, + extra_params: Optional[list[str]] = None, ) -> Generator[Dict[str, Any], None, None]: # Make dockerfile path relative to context if not absolute if not os.path.isabs(dockerfile): @@ -187,6 +198,9 @@ def build_image( if rm: cmd.append("--rm") + if extra_params: + cmd.extend(extra_params) + cmd.append(path) LOG.debug(f"Executing build command: {' '.join(cmd)}")