.dockerignore: Keep Unwanted Files Out of Builds

Practical advice from AriZone

Training scenario: a local configuration file is absent from Git’s output, but you run a build containing COPY . and are unsure whether the builder can access it. Git rules do not automatically determine the contents of a local Docker context. A .dockerignore file lets you restrict that set separately. We will test the rule in a small directory containing fictional data, without transmitting real passwords or building a production application.

The goal is to see which files COPY can access after exclusions are applied. A small filesystem export is more useful than assumptions based on build size. It will show that a required public file remains, an example local configuration is excluded, and a safe template is retained. This checks the learning example; it does not guarantee that every image in your company is free of secrets.

Separate the Docker context from the repository

The final argument of a local build command specifies its context: a dot means the current directory. This boundary determines which files COPY can access. Do not run the exercise from your home directory or the root of a large working tree. With .dockerignore, the rule must not merely exist: the file must be at the root of the context actually selected. The Docker build context documentation describes this mechanism.

The example is intended for macOS or Linux with Docker Engine and Buildx already configured, and access to an approved local builder. The command docker buildx version checks Buildx availability but does not confirm that the builder itself works. If the environment is not ready, follow the installation instructions for your system; do not change a shared server’s settings for this exercise. Editing the learning files does not require administrator privileges.

Using an editor, create a new empty directory named dockerignore-demo. Add public/index.html containing any learning text, .env.training containing DEMO_NOT_SECRET=1, and .env.example containing an obvious placeholder, SETTING=replace_me. These are not real credentials. Do not copy a live website’s configuration into this directory: we are checking a rule first, not testing protection with actual secrets.

Create .dockerignore at the root of this directory with the following lines. Agree on the list separately for a real project: a log might be a required test fixture, and the local configuration filename might differ. Do not mechanically apply the list to every repository.

.git
.env
.env.*
!.env.example
*.log

The initial rules exclude the Git directory, environment files and logs. The line beginning with an exclamation mark restores .env.example after the broader .env.* rule. Order matters. The template must contain only parameter names and safe placeholders; the example suffix does not make its contents safe. Before the first build, open every learning file and ensure that none contains a real value.

Make the result visible without running an application

Create a Dockerfile in the same directory. This recipe is only for inspecting files: it does not install dependencies, run a website or provide a container execution command. It uses scratch as an empty base, and COPY transfers the allowed context into a snapshot directory. Do not replace your application’s Dockerfile with this recipe.

FROM scratch AS context-check
COPY . /snapshot/

Enter dockerignore-demo and check that the neighbouring dockerignore-result-01 directory does not already exist. If it does, choose another new name and change it consistently in every command below. The next command runs a build, may create cache entries and writes its result to disk outside the context. Do not choose a directory containing working files as the destination: the export must not be mixed with them.

docker buildx build \
  --output type=local,dest=../dockerignore-result-01 \
  .

The output option with type local exports the result’s filesystem into the selected directory. This does not publish an image to a registry or start a web server. The local exporter documentation explains the behaviour and supported settings. If the command fails, record the cause first; do not treat files left by an earlier export as a new successful result.

From the same learning directory, run each check separately. Each is expected to exit with code 0: the public page and template exist, while .env.training is absent. The test command normally prints nothing on success; a lack of text does not replace checking its exit code in your terminal or script.

test -f ../dockerignore-result-01/snapshot/public/index.html
test ! -e ../dockerignore-result-01/snapshot/.env.training
test -f ../dockerignore-result-01/snapshot/.env.example

If the configuration file is present, stop and check the context path, the .dockerignore filename and rule order. Also check whether a separate ignore file exists for the selected Dockerfile: it can take precedence over the root file. This exercise uses only the ordinary Dockerfile. Do not disable all exclusions at once: that conceals the cause and increases the files accessible to the builder.

Move the rule into the project as a separate change

For a real website, first preserve the current rules and agree on which directories the build actually needs. Add exclusions in small groups and check that templates, static assets and dependency files remain available. A failed build after excluding a file does not mean that the entire home directory should be returned to the context. Identify the specific dependency and narrow down the required path.

Checking this export does not cover additional contexts, previous images, external downloads or other stages of your actual recipe. Do not use fictional passwords as a substitute for correctly supplying secrets. If a real secret has already entered someone else’s build or a published image, adding a rule is insufficient: stop using the compromised access and agree on a separate response. Do not include sensitive values in investigation logs.

After the exercise, you can remove the learning directories manually after verifying their exact names; clearing every Docker image or the entire cache is unnecessary. Keep a short context-content check in the project and review staged changes before committing. If the new rules break the build, restore the previous rules from version control in the test environment without erasing other work.

Conclusion: check .dockerignore against the actual set of accessible files, not a clean Git status. A separate directory containing placeholders lets you test rules without risking real configuration. If you need help organising a web project’s Docker build, contact AriZone with a description of the context and an anonymised error, not an archive containing passwords and private keys.

Discussion

Leave a comment

Add a comment

Your email will not be published. Required fields are marked *.

Cloudflare Turnstile spam protection