Dec 02, 2025
Marta P. & Ariffud M.
6min Read
Docker build secrets are a Docker BuildKit feature that securely passes sensitive data, such as API keys and passwords, during image builds without baking them into the final image.
Keep reading as we walk you through everything you need to know about using build secrets, such as:
By the end, you’ll be able to protect sensitive data at build time using ephemeral secret management techniques that are secure, temporary, and designed for modern container workflows.
Download free docker cheat sheet
Docker build secrets provide a secure way to use sensitive files during a Docker build without leaving them in the final image.
When you use a secret, Docker temporarily mounts it into the build container. Once the build step using the secret finishes, Docker unmounts the file. The secret is not stored in any image layers or its history.
The main advantage over older methods like ARG and ENV is security. Data passed with ARG or ENV can be inspected using the docker history command, which could expose your secrets.
With build secrets, the data is ephemeral and never becomes part of the image, preventing accidental leaks.
Docker supports two types of mounts for handling sensitive data during builds:
The detailed steps to create and pass your first build secret are below.
First, install Docker on your system. The steps will vary depending on your operating system. For this example, we’ll use Docker on Ubuntu.
Next, enable Docker BuildKit, as it powers the build secrets feature. You can enable it for a single build or permanently.
If you want to enable BuildKit for a single build, run the build command with the DOCKER_BUILDKIT=1 environment variable:
DOCKER_BUILDKIT=1 docker build .
To enable BuildKit permanently, edit the Docker daemon configuration file at ~/.docker/config.json and add the following feature flag:
{
"features": {
"buildkit": true
}
}A secret file is a plain text file that contains the sensitive data you want to protect. For this example, create a file to store a database password.
In your terminal, create the secret file:
echo "mydb_password" > mydb-password.txt
If you have multiple secrets, store each one in a separate file. This lets you manage their permissions and mount them individually into the container. For instance:
echo "my_api_key" > api-key.txt echo "my_ssh_key" > ssh-key.txt
To pass the secret file into the build process, use the –secret flag in your docker build command like this:
--secret id=mydb_password,src=mydb-password.txt
Here’s a breakdown of the flag’s syntax:
You’ll use this flag later after referencing the secret in your Dockerfile.
Once you pass a secret to the build command, you can make it available inside your Dockerfile.
To use a secret, mount it within a RUN instruction using the –mount flag. The mount type for secrets is type=secret.
Here’s an example Dockerfile that mounts your database password secret:
# Use Ubuntu base image FROM ubuntu:24.04 # Mount a secret and check if it’s there, but don’t print the secret value RUN --mount=type=secret,id=mydb_password ls -l /run/secrets/ && echo "Secret is available and correctly mounted!" || echo "No secret found"
In this example, id=mydb_password corresponds to the ID you specified in the –secret flag. By default, Docker mounts the secret at /run/secrets/, and the filename inside the container is the secret’s ID.
Now, build the image using the complete command, including the –secret flag. Add –no-cache and –progress=plain to view the output clearly.
docker build --no-cache --progress=plain --secret id=mydb_password,src=mydb-password.txt -t my-image .
If successful, the output will show that the secret mounted correctly inside the /run/secrets/ directory during that RUN step.

Once the step finishes, the secret disappears and is not saved in the final image.
You can access the content of the secret file like any other file. For example, use the cat command to view its contents during the build for debugging.
Update your Dockerfile as follows:
# Mount a secret and access its content RUN --mount=type=secret,id=mydb_password cat /run/secrets/mydb_password || echo "No secret found"
Then, run the build again:
docker build --no-cache --progress=plain --secret id=mydb_password,src=mydb-password.txt -t my-image .
This will print the secret’s content to the console. While this is useful for testing, be careful not to leave this in your production Dockerfiles, as it can expose secrets in your build logs.

If you’re building multi-service apps, the next step is integrating secrets into Docker Compose.
Docker Compose is a tool for defining and running multi-container Docker apps. You can also manage build secrets directly within your docker-compose.yml file, simplifying the management of configurations for complex services.
This approach is ideal for managing apps like a Kafka cluster on Docker, where multiple components need secure configurations.
To use build secrets with Docker Compose, define them in the top-level secrets section of your docker-compose.yml file and then assign them to the relevant services.
Here’s an example using a PostgreSQL database service:
version: "3.8"
services:
db:
image: postgres
environment:
POSTGRES_PASSWORD_FILE: /run/secrets/mydb_password
secrets:
- mydb_password
secrets:
mydb_password:
file: ./mydb-password.txtIn this file:
To start your app, run docker-compose up. Compose will read the secret file from your host and securely mount it into the running container without exposing it in the service definition.
Please note that while Docker Compose works well for managing app secrets like passwords, you’ll often need to handle authentication secrets. That’s where SSH mounts can help.
SSH mounts are a specialized type of build secret that forward SSH keys. They are useful when you need to clone a private Git repository or access other SSH-protected resources during a build.
Like regular secrets, the SSH key is only available temporarily during the RUN step and never gets baked into the final image.
In automated CI/CD pipelines, where you might use tools like Ansible to install and configure Docker, SSH mounts provide a secure channel for these build steps.
To use an SSH mount, load your SSH key into your local SSH agent.
First, start the SSH agent if it isn’t already running:
eval $(ssh-agent)
Then, add your private key to the agent:
ssh-add ~/.ssh/id_rsa
Verify that the key is loaded:
ssh-add -l
Next, reference the SSH mount in your Dockerfile. The mount type for SSH is type=ssh.
Below is an example that clones a private Git repository:
FROM ubuntu:24.04
# Install Git and SSH dependencies
RUN apt update && apt install -y git ssh-client
# Add GitHub's SSH key to known_hosts to avoid host verification prompts
RUN mkdir -p -m 0700 ~/.ssh &&
ssh-keyscan github.com >> ~/.ssh/known_hosts
# Clone a private Git repository using the mounted SSH key
RUN --mount=type=ssh git clone git@github.com:your-org/your-private-repo.git /myprojectFinally, build the image using the –ssh flag. This flag tells Docker to forward the SSH agent socket to the build:
docker build --ssh default -t my-image .
Now that you know how to handle both file-based secrets with Docker Compose and SSH keys with SSH mounts, let’s look at best practices to keep your builds secure.
Following best practices helps protect sensitive data in Docker containers throughout the development lifecycle. Some universal guidelines are listed below:

Using Docker build secrets is an essential practice for securing containerized applications. It prevents sensitive data like API keys, tokens, and credentials from being accidentally exposed in your final Docker images.
Here are the main points to remember:
Next, strengthen your Docker security by setting up a private Docker registry to control image access and protect sensitive workloads.
This approach safeguards images, reduces the risk of unauthorized access, and gives you full control over your deployment pipeline.