Docker Policy Examples
Apcera provides a Docker-specific policy claim for whitelisting Docker images that can be used to create jobs and packages. You can write policy that restricts Docker image availability by registry location (Docker Hub or a private Quay registry, for example), image repository ("apcerademos", e.g.), and image name and version tag ("nats:latest" or "mysql:5.7.14", e.g.).
Note that Docker policy is always written against the job::
realm, regardless of whether you are creating an application from a Docker image (with apc docker run
) or just creating a package from an image (with apc docker pull
), as explained below.
Docker image whitelisting
To create an application or package from a Docker image you must define a docker.allow
claim on the job::
realm of the target app or package resource. Without docker.allow
policy, you cannot deploy Docker jobs or create Docker packages in the system.
Whitelisting for app creation
To create an application from a Docker image using apc docker run <app-name>
(or equivalent Web Console menu) policy must be defined that allows access to the specified Docker image in the target namespace or at the target FQN. For example, in the following example the authenticated user does not have the necessary policy permissions to create an app in the current namespace from the latest NATS Docker image:
apc docker run nats1 --image nats:latest --restart always
Error: Docker image "https://registry-1.docker.io/library/nats:latest" not allowed by policy:
missing claim "docker.allow \"https://registry-1.docker.io/library/nats:latest\""
on "job::/sandbox/user::nats1"
As the error message indicates, you must add policy that allows job::/sandbox/user::nats1
to pull the latest NATS image from Docker Hub, as shown below:
job::/sandbox/user::nats1 {
{ docker.allow "https://registry-1.docker.io/nats:latest" }
}
Also see Global and fine-grained whitelisting.
Whitelisting for package creation
The apc docker pull <package-name>
command creates a new package from a Docker image. When you run this command Apcera checks if the specified Docker image would be allowed to run as a "hypothetical" job in the same namespace. For example, if the package being created is package::/namespace/pkg::mypackage
then the cluster checks job::/namespace/pkg
for the necessary docker.allow
policy. Note that only the namespace is checked for policy compliance, not including the resource's local name.
For example, consider the following apc docker pull
command that fails because the proper policy is not in place:
apc docker pull /mypackages/docker::nats-pkg --image nats:0.9.4
[nats-pkg] -- Pulling Docker image -- checking policy
[error] -- Docker image "https://registry-1.docker.io/library/nats:0.9.4" not allowed by policy:
missing claim "docker.allow \"https://registry-1.docker.io/library/nats:0.9.4\""
on "job::/mypackages/docker::nats-pkg"
The following policy on the job::
realm fixes this error by allowing the authenticated user to pull any tagged version of the NATS image:
job::/mypackages/docker {
{ docker.allow "https://registry-1.docker.io/library/nats" }
}
Note: Despite the wording of the "missing claim" error message shown previously, it's recommended that Docker policy for creating packages be written against the "hypothetical" job's namespace (
job::/mypackages/docker
) as shown above, rather than it's fully-qualified name (job::/mypackages/docker::nats-pkg
) (as the error states).
Global and fine-grained whitelisting
The following policy grants Docker job deployment and package creation globally across the cluster:
job::/ {
{ docker.allow "*" }
}
However, you can also use docker.allow
for more fine-grained control over what Docker images can be pulled and deployed to the system. For example, the following policy explicitly allows the mybin/redis
Docker image:
job::/sandbox/user {
{ docker.allow "https://registry-1.docker.io/mybin/redis" }
}
The following policy explicitly allows the mybin/redis
Docker image (any tagged version) and the nats
image, the latter only with the latest
tag:
job::/sandbox/user {
{ docker.allow "https://registry-1.docker.io/mybin/redis", "https://registry-1.docker.io/nats:latest" }
}
Note that the policy is permissive from left to right. For example, the following policy would allow any image from Docker Hub:
job::/sandbox/user {
{ docker.allow "https://registry-1.docker.io" }
}
In comparison, the following policy would only allow images from Docker Hub in the /mybin repository.
job::/sandbox/user {
{ docker.allow "https://registry-1.docker.io/mybin" }
}
See also Docker whitelisting.