-
Notifications
You must be signed in to change notification settings - Fork 4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
CodeBuild: Allow DockerImageAssets to be built using buildx #28517
Comments
Yes it would be great to include |
You can try overriding the CDK_DOCKER variable like this. It could be a workaround for you. |
OK I have a full working sample now. Let's say if we need to build a DockerImage assets of a Golang application on AMD64 linux machine for ARM64 Fargate runtimePlatform. main.go package main
import (
"fmt"
"runtime"
"net/http"
)
func handleCDK(w http.ResponseWriter, r *http.Request) {
// Get the current CPU architecture
cpuArch := runtime.GOARCH
// Print the CPU architecture to the client
fmt.Fprintf(w, "Current CPU architecture: %s\n", cpuArch)
}
func main() {
http.HandleFunc("/", handleCDK)
fmt.Println("Starting server on port 8080")
http.ListenAndServe(":8080", nil)
} Dockerfile FROM golang:alpine AS builder
WORKDIR /app
COPY . .
RUN go build -o main .
FROM alpine
WORKDIR /app
COPY --from=builder /app/main /app
EXPOSE 8080
ENTRYPOINT ["/app/main"] If we build and run it locally, we should see this with
Now if we have a cdk app like this export class DummyStack extends Stack {
constructor(scope: Construct, id: string, props: StackProps) {
super(scope, id, props);
const vpc = getDefaultVpc(this);
new ecsPatterns.ApplicationLoadBalancedFargateService(this, 'Service', {
vpc,
taskImageOptions: {
image: ecs.ContainerImage.fromAsset(path.join(__dirname, '../webapp'), {
platform: Platform.LINUX_ARM64,
}),
containerPort: 8080,
},
runtimePlatform: {
cpuArchitecture: ecs.CpuArchitecture.ARM64,
operatingSystemFamily: ecs.OperatingSystemFamily.LINUX,
}
})
}
} And we have Let's write a custom wrapper for it at ~/bin/buildx.sh #!/bin/bash
# covert docker build to docker buildx build --load
if [[ "$1" == "build" ]]; then
docker buildx build --load "${@:2}"
else
docker "$@"
fi Now, deploy it like this:
On deployment completed, you should get the fargate service URL and if you cURL it:
It's actually running the golang app on arm64. I think it's a good workaround for you to allow you leverage the Please note cross-platform image building with Let me know if it works for you. |
As this is a working workadound, I am downgrading this issue to p2 but I'll leave it open until we have a better native support with buildx. |
@pahud Thanks for the quick response! I have been able to successfully implement the solution you provided above locally, however, in CodeBuild there still seems to be some issues relating to the cross architecture building. In order to incorporate the above shell script into the Docker build process I've included it in the root directory of the asset that needs to be built. As such the current root directory of the Java project contains the Dockerfile, pom, src directory, and associated buildx.sh. In order to have codebuild use the buildx.sh file I have included a number of commands to the pre-build phase of the default asset publishing build spec to determine whether a
With these pre-build commands, CodeBuild will correctly perform the Any insight you could offer into why this error continues to persist would be greatly appreciated. Dockerfile
CodePipeline Asset Publishing CodeBuild Defaults
CodeBuild Log Exerts
|
After some further investigation is seems that the CodeBuild standard:7.0 image only supports
With these two commands the application is able to be successfully built and run (with the addition of |
Awesome! Yes the I guess By the way, CodeBuild allows you to specify LinuxArmBuildImage for your build environment and you won't need |
Yeah I did see that you are able to specify a LinuxArmBuildImage for CodeBuild however when using a CodePipeline with stages I was only able to see methods to have the architecture be set at a project level and not for a specific asset to be built (we do not manually define the build stage using code pipeline actions). As within our pipeline we also build some assets for X86 it wouldn't be possible to change the default image as we would just experience the same issue for the X86 assets. It would be good if we were able to specify the environment on a per asset basis? This would allow for the assets to be built natively. |
@James-Coulson Makes sense. Thanks for sharing your use case. |
Hi @pahud, We are currently starting our migration to ARM compute. Our first step was to replicate our custom CodeBuild image we use to build our application. We want to create CodeBuild projects using both x86 and arm64 to create build checks for github until we have our code base ready for both platforms. Our CDK is deployed using CodePipeline construct and we've added the additional ARM image as follows:
Dockerfile
When this is built in the Docker Assets section of the pipeline it passes the correct
Could you let me know if the workaround can be applied to my use case or whether you would like me to submit a separate issue. |
I managed to get this working by changing the image type of the Assets pipeline step CodeBuild project. You can do that by changing new pipelines.CodePipeline(this, 'Pipeline', {
...
assetPublishingCodeBuildDefaults: {
buildEnvironment: {
buildImage: codebuild.LinuxBuildImage.AMAZON_LINUX_2_ARM_3,
},
},
...
} It would be useful to add to the docs that image: ecs.ContainerImage.fromAsset('./', {
platform: ecrAssets.Platform.LINUX_ARM64,
}), |
Describe the feature
We make use of a CDK
CodePipeline
construct to build and deploy our backend infrastructure to the development and production accounts. As part of our backend we require the ability to run Dockerised applications as a Service in ECS, specifically these services are built using Java (Corretto 21) and run on the ARM based t4g instances. This requires that the docker images be built using the ARM instructuction set, however, when we specify the docker images within the CDK pipeline including the desired 'linus/arm' platform CodeBuild fails to build the applications (using the existingplatform
property in theDockerImageAsset
construct). Specifically, when CodeBuild attempts to build the image aformat exec error
is thrown.Dockerfile
CDK Code
Error in CodeBuild
This docker image can be built successfully locally (Mac i7) as I believe that the
buildx
plugin is used by default for Docker Desktop. Upon reading through the documentation for the DockerImageAsset it can be seen that the use of theplatform
property is dependent on building using thebuildx
however I have not been able to locate how we can force the build stage to use this (the above error message shows that onlydocker build ...
is being used).As such this feature request is to add the ability to build a DockerImageAsset using
buildx
to allow for cross architecture building of Dockerised applications.If there is already a method for using
buildx
or this is simply a case of user error/RTFM please let me know.Note
It is my understanding that the Docker
buildx
package which allows for cross architecture compliation to be performed is included within the standard:7.0 codebuild image so ther should be no issue relating to having to install the application see here.Use Case
By introducing this feature it will allow for ARM based dockerised applications to be built using the
DockerImageAsset
construct within anCodePipeline
.Proposed Solution
DockerImageAsset
construct to allow for building the image using thebuildx
plugin.DockerImageAsset
to build the image natively on an ARM based instance.Other Information
No response
Acknowledgements
CDK version used
2.108.0
Environment details (OS name and version, etc.)
Mac i7, AWS CodeBuild
The text was updated successfully, but these errors were encountered: