Skip to main content
In this guide, you’ll learn how to configure Docker Content Trust (DCT) to allow only cryptographically signed images in your environment. We cover:
  • Pulling unsigned images without Content Trust
  • Enabling Content Trust on an individual host
  • Enforcing Content Trust across a UCP cluster
  • Pushing unsigned images to Docker Trusted Registry (DTR)
  • Managing Notary keys and signing images
  • Verifying and pulling signed images

Step 1: Pulling an Unsigned Image (without Content Trust)

On a UCP worker node, list existing images and pull the unsigned image yogeshraheja/tomcatone:v1 from Docker Hub:
[root@ucpworker ~]# docker image ls
REPOSITORY                  TAG       IMAGE ID       CREATED        SIZE
docker/ucp-pause            3.2.6     feb0e469f6ac   2 months ago   683kB
docker/ucp-agent            3.2.6     b9763a5e7df8   2 months ago   62.1MB
docker/ucp-hyperkube        3.2.6     56c3b92d2b4f   2 months ago   441MB
docker/ucp-calico-node      3.2.6     40091fdbb1b4   2 months ago   189MB
docker/ucp-calico-cni       3.2.6     dd89cabc02dd   2 months ago   162MB

[root@ucpworker ~]# docker image pull yogeshraheja/tomcatone:v1
v1: Pulling from yogeshraheja/tomcatone
[...]
Status: Downloaded newer image for docker.io/yogeshraheja/tomcatone:v1

[root@ucpworker ~]# docker image ls
REPOSITORY                  TAG       IMAGE ID       CREATED        SIZE
yogeshraheja/tomcatone      v1        bd808d1...     5 days ago     497MB
By default, Docker allows pulling unsigned images from public registries.

Step 2: Enabling Docker Content Trust on a Single Host

To require signed images, set the DOCKER_CONTENT_TRUST environment variable:
[root@ucpworker ~]# export DOCKER_CONTENT_TRUST=1
Remove the previously pulled image and attempt to pull it again:
[root@ucpworker ~]# docker image rm yogeshraheja/tomcatone:v1
[root@ucpworker ~]# docker image pull yogeshraheja/tomcatone:v1
Error: remote trust data does not exist for docker.io/yogeshraheja/tomcatone: notary.docker.io does not have trust data
Docker refuses to pull the unsigned image when Content Trust is enabled.

Step 3: Enforcing Content Trust Cluster-Wide via UCP

Manually exporting an environment variable on each node is tedious. Instead, enforce Content Trust across your Docker Universal Control Plane (UCP) cluster:
  1. Log in to UCP as an administrator.
  2. Navigate to Admin SettingsAccount Settings.
  3. Enable Docker Content Trust (Only Signed Images).
  4. Save your changes.
This setting propagates DOCKER_CONTENT_TRUST=1 to all cluster nodes.
The image shows the "Admin Settings" page of Docker Enterprise, specifically focusing on "Docker Content Trust" settings, with an option to run only signed images.

Step 4: Pulling an Unsigned Image from a Client with Content Trust Enabled

On your local workstation using the UCP client bundle, Content Trust is now enforced:
[root@yogeshclientbundle ~]# ./docker image pull yogeshraheja/tomcatone:v1
Error response from daemon: image or trust data does not exist for docker.io/yogeshraheja/tomcatone:v1
Disabling Content Trust exposes your environment to unsigned and potentially unverified images. Only unset if absolutely necessary.
To continue working with unsigned images temporarily:
[root@yogeshclientbundle ~]# unset DOCKER_CONTENT_TRUST
[root@yogeshclientbundle ~]# ./docker image pull yogeshraheja/tomcatone:v1

Step 5: Pushing the Unsigned Image to Docker Trusted Registry (DTR)

  1. In DTR, create a repository named yogeshraheja/testimagesigning.
  2. Tag and push the image from your local host:
[root@yogeshclientbundle ~]# ./docker image tag \
    yogeshraheja/tomcatone:v1 \
    54.145.234.153/yogeshraheja/testimagesigning:v1

[root@yogeshclientbundle ~]# ./docker login 54.145.234.153
Username: yogeshraheja
Password: 
Login Succeeded

[root@yogeshclientbundle ~]# ./docker image push \
    54.145.234.153/yogeshraheja/testimagesigning:v1
The repository now contains the unsigned image.

Step 6: Signing the Image with Docker Content Trust

Docker Content Trust uses Notary to manage trust metadata. Below are the steps to import your keys, initialize trust for a repository, and sign an image.

6.1 Import Your Notary Private Key

Copy the private key into Docker’s trust directory and load it:
[root@yogeshclientbundle ~]# mkdir -p ~/.docker/trust
[root@yogeshclientbundle ~]# cp key.pem ~/.docker/trust/
[root@yogeshclientbundle ~]# ./docker trust key load --name yogeshraheja key.pem
Loading key from "key.pem"...
Enter passphrase for new yogeshraheja key with ID 97dd9b8:
Repeat passphrase for new yogeshraheja key with ID 97dd9b8:
Successfully imported key from key.pem

6.2 Initialize Trust Metadata and Add a Signer

Authorize your user as a signer and initialize the repository’s trust data:
[root@yogeshclientbundle ~]# ./docker trust signer add --key cert.pub \
    yogeshraheja \
    54.145.234.153/yogeshraheja/testimagesigning
Adding signer "yogeshraheja" to 54.145.234.153/yogeshraheja/testimagesigning...
Initializing signed repository for 54.145.234.153/yogeshraheja/testimagesigning...
Enter passphrase for root key with ID 47caaa5:
Enter passphrase for new repository key with ID faf8bd5:
Repeat passphrase for new key with ID faf8bd5:
Successfully initialized and added signer "yogeshraheja".

6.3 Sign the Image Tag

Sign the v1 tag:
[root@yogeshclientbundle ~]# ./docker trust sign \
    54.145.234.153/yogeshraheja/testimagesigning:v1
Enter passphrase for "yogeshraheja" key with ID 97dd9b8:
Signed 1 tag for 54.145.234.153/yogeshraheja/testimagesigning:v1
(Optional) Verify trust metadata:
[root@yogeshclientbundle ~]# ./docker trust inspect \
    --pretty 54.145.234.153/yogeshraheja/testimagesigning

Step 7: Pushing Signed Images and New Tags

After signing, push your v1 image and optionally tag and sign a new version v2:
[root@yogeshclientbundle ~]# ./docker push \
    54.145.234.153/yogeshraheja/testimagesigning:v1

# Tag a new version
[root@yogeshclientbundle ~]# ./docker image tag \
    54.145.234.153/yogeshraheja/testimagesigning:v1 \
    54.145.234.153/yogeshraheja/testimagesigning:v2

# Sign the new tag
[root@yogeshclientbundle ~]# ./docker trust sign \
    54.145.234.153/yogeshraheja/testimagesigning:v2

# Push the v2 tag
[root@yogeshclientbundle ~]# ./docker push \
    54.145.234.153/yogeshraheja/testimagesigning:v2
The image shows a Docker Enterprise Trusted Registry interface displaying details of a repository named "testimagesigning," including a signed image tagged "v2" with its type, ID, size, and vulnerability scan options.

Summary Table of Content Trust Configuration

ActionMethodCommand / UI Path
Enable Content Trust on hostEnvironment variableexport DOCKER_CONTENT_TRUST=1
Enforce Content Trust clusterUCP Admin SettingsAdmin SettingsAccount SettingsDocker Content Trust
Import Notary keyCLIdocker trust key load --name <user> key.pem
Initialize repository signingCLIdocker trust signer add --key cert.pub <user> <repo>
Sign an image tagCLIdocker trust sign <repo>:<tag>