DEV Community

Celso Nery
Celso Nery

Posted on

Part 5: Managing Images

🇧🇷 Artigo em português aqui

Using Docker — Part 5: Managing Images

In Part 4 of this series, we covered how containers communicate through networks. Now let's tackle the lifecycle of Docker images: how to build your own, list the ones already available locally, version them correctly, and publish them to a registry — whether Docker Hub or a private registry.

Building an image

To build an image from a Dockerfile:

$ docker build -t <image_name>:<version> -f dockerfile .
Enter fullscreen mode Exit fullscreen mode

Where:

  • -t <image_name>:<version>: sets the name and tag (version) of the resulting image; if the version is released, a 'latest' version will be created;
  • -f dockerfile: specifies which Dockerfile to use (useful when you have multiple Dockerfiles in the same directory, or a non-default filename); if there is only one Dockerfile at the project root, this argument can be omitted;
  • .: sets the build context — the directory whose contents become available to instructions like COPY and ADD inside the Dockerfile.

Dockerfile example:

FROM nginx:alpine
RUN apk update && apk upgrade --no-cache
WORKDIR /usr/share/nginx/html
COPY ./index.html ./
EXPOSE 80
CMD [ "nginx", "-g", "daemon off;" ]
Enter fullscreen mode Exit fullscreen mode
  • FROM: Specifies the base image to be used.
  • RUN: Commands to execute in order to build the application before building the image.
  • WORKDIR: Specifies the internal location within the image where operations are currently taking place.
  • COPY: Command to copy files from the local application into the Docker image.
  • EXPOSE: Specifies the port the container will listen on.
  • CMD: Command for the final execution of the application. (In this case, I am running Nginx).

Listing images

To see all images already downloaded or built locally:

$ docker image ls
Enter fullscreen mode Exit fullscreen mode

Versioning images (tag)

Before publishing an image to a registry, you generally need to "tag" it with the full destination address:

$ docker tag <local_image_name>:<version> <remote_registry>/<remote_image_name>:<version>
Enter fullscreen mode Exit fullscreen mode

For example, tagging a local myapp:1.0.0 image for Docker Hub, under the user celsonery:

$ docker tag myapp:1.0.0 celsonery/myapp:1.0.0
Enter fullscreen mode Exit fullscreen mode

Or for a private registry:

$ docker tag myapp:1.0.0 registry.yourcompany.com/myapp:1.0.0
Enter fullscreen mode Exit fullscreen mode

It's considered good practice to use semantic versioning in your tags (1.0.0, 1.0.1, 1.1.0) instead of relying solely on the latest tag, since latest doesn't indicate exactly which version is running in production.

Removing images

To remove a specific image:

$ docker image rm <image_name>:<version>
Enter fullscreen mode Exit fullscreen mode

Cleaning up unused images

Intermediate images and images no longer referenced by any container tend to pile up over time, taking up disk space. To clean up:

$ docker image prune
Enter fullscreen mode Exit fullscreen mode

Publishing an image (push)

To publish an image, you must first authenticate with a registry.

  • Docker Hub (default)
$ docker login
Enter fullscreen mode Exit fullscreen mode
  • Private registry

When the destination isn't Docker Hub, you need to provide the server address:

$ docker login registry.yourcompany.com
Enter fullscreen mode Exit fullscreen mode
  • Push to Docker Hub
$ docker push <image_name>:<version>
Enter fullscreen mode Exit fullscreen mode
  • Push to a private registry
$ docker push <registry>/<image_name>:<version>
Enter fullscreen mode Exit fullscreen mode

Remember: the image needs to have been tagged (previous step) with the full destination registry address before the push — otherwise, Docker will try to send it to Docker Hub by default.

Next steps

With the complete image lifecycle covered — build, tag, push —, you can now distribute your own applications as versioned images. In Part 6, the last of this series, we'll bring everything we've covered together (volumes, networks, multiple containers) using Docker Compose, making it much simpler and more organized to manage applications with multiple services.

Continued in Part 6.

Top comments (0)