Skip to content

Instantly share code, notes, and snippets.

@evanscottgray
Last active June 21, 2018 07:09
Show Gist options
  • Star 3 You must be signed in to star a gist
  • Fork 2 You must be signed in to fork a gist
  • Save evanscottgray/6ebd9b45551d52145c39 to your computer and use it in GitHub Desktop.
Save evanscottgray/6ebd9b45551d52145c39 to your computer and use it in GitHub Desktop.
creating base images with docker.

Docker Container/Image Basics

This is a basic step by step intro to working with Docker containers and Images. You should be able to follow along with your installation of docker, but be sure to change IDs/naming schemes according to your use case.

The goal of this exercise is to create a base image from the ubuntu base image that has both the jre and htop installed.

Start up an ubuntu container to modify, install htop, then exit.

docker run -t -i ubuntu /bin/bash

Get the ID of the container you just modified.

docker ps -a

Check out the cool changes you made to the filesystem when you added htop!

docker diff e22ac97a0748

Start up that container just to make sure the changes are there.

This syntax allows you to attach to an already created container.

docker start -i -a e22ac97a0748

Commit the container as a new image that you can start containers from.

docker commit --author='evan' --message='wow added htop' e22ac97a0748 evancoolrepo/htop

Start up a new copy of your fresh image, wow your changes are there, htop starts!

docker run -t -i evancoolrepo/htop htop

Take a look at the image history so you can visualize what actually went down.

docker images --tree | grep -C 5 evancoolrepo/htop

We can even look at what happened to generate each layer.

docker history evancoolrepo/htop

Now we want to install the openjdk-7-jre package to our image, let's pop into it and make some changes, this time we'll name it for simplicity of working with it later.

docker run -t -i --name='added_the_jre' evancoolrepo/htop /bin/bash

Once you're out let's go ahead and commit this container to a new image that you can spawn more containers from.

docker commit --author='evan' --message='wow added the jre' added_the_jre evancoolrepo/htopjre

Cool, we can see that we have created the evancoolrepo/htopjre image.

docker images | sed -e '1p' -e '/evancoolrepo\/htopjre/!d'

That's fancy, but let's look at the tree again.

docker images --tree | grep -C 8  evancoolrepo/htopjre

Output:

├─d497ad3926c8 Virtual Size: 192.5 MB
│ └─c5fcd5669fa5 Virtual Size: 192.7 MB
│   └─49bb1c57a82c Virtual Size: 192.7 MB
│     └─67983a9b1599 Virtual Size: 192.7 MB
│       └─88fba6f3d2d8 Virtual Size: 192.7 MB
│         └─eca7633ed783 Virtual Size: 192.7 MB Tags: ubuntu:trusty, ubuntu:latest, ubuntu:14.04, ubuntu:14.04.1
│           └─83ba41572d75 Virtual Size: 214.5 MB Tags: evancoolrepo/htop:latest
│             └─5bff31176519 Virtual Size: 579.9 MB Tags: evancoolrepo/htopjre:latest

Hmm. We've got excess layers. These add to the size of the evancoolrepo/htopjre container and are unnecessary.

Flatten the new evancoolrepo/htopjre with some docker magic.

Start by creating a dummy container to export as a flat container. Without the -t -i flags, the container will start and then immediately exit, thereby creating the dummy container we're after.

docker run --name='dummy_to_flatten' evancoolrepo/htopjre /bin/bash

Verify the dummy container exists.

docker ps -a | sed -e '1p' -e '/dummy_to_flatten/!d'

DO DOCKER MAGIC!

docker export is an amazing command that takes the filesystem of a container and exports it to a tar file over stdout.
docker import is an amazing command that takes a tar file from stdin and creates an image from it.
When you combine these commands, docker is forced to composite the filesystem of a container to a single layer, and then pop that directly into an image, thus eliminating space wasting intermediary layers as seen a few steps ago.

docker export dummy_to_flatten | docker import - evancoolrepo/htopjre-flat

Verify the new evancoolrepo/htopjre-flat image was created

docker images | sed -e '1p' -e'/evancoolrepo\/htopjre-flat/!d'

Make sure it still has java and htop installed!

docker run evancoolrepo/htopjre-flat which java && which htop

Should output something like this:

/usr/bin/java
/usr/bin/htop

Take a look at the new evancoolrepo/htopjre-flat's structure.

docker images --tree | grep -C 8 evancoolrepo/htopjre-flat

Only one layer, same great ubuntu base image, htop and java installed, and 52.9 MB smaller to boot!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment