3 Working With Images, Containers, and Pods
Podman can be used to run containers and to obtain the images that are used to create a container in the same way that you would use Oracle Container Runtime for Docker. The following information describes how you can pull container images from registries into the local image storage; how you can manage container images on local storage; how you can run containers based on these images; and how you can manage the containers that you have created on the host system.
In many ways, Podman can be used as a drop-in replacement for Oracle Container Runtime for Docker. Podman can use images that comply with the Open Container Initiative (OCI) specification and can run containers based on these images. Most Podman commands map directly to the command equivalents that are available in the Docker CLI.
A key difference between Podman and Docker is that while the Docker Engine runs as a service on the host and all actions are performed by the service, Podman runs as a standalone runtime so that each operation is independent. This difference is important, as it changes the security model around working with images and containers.
Because Podman operations aren't dependent on a service daemon running as a particular user on the system, Podman provides more isolation than Docker. This means that you can either run Podman as a standard user or as the root user.
Podman respects user namespaces. This means that several users on a single host can all run their own containers and local image stores without any concern that there could be a conflict. Because containers running within a user's namespace are limited to the permissions available to the user on the host system, Podman is considered to provide more security than Docker.
Some key differences exist when you run Podman as a standard user, instead of running Podman as the root user. These differences are based on the permissions available to these different user types. For example, networking functionality is more limited when running Podman as a standard user and most networking is achieved solely using port mapping and port forwarding, when in this mode. This doesn't suggest that running Podman as the root user is preferred, but some limitations might apply when working as a standard user. To some degree, many issues that arise for a standard user can be mitigated by running groups of containers within a pod. For more information about networking and Podman, see Configuring Networking for Podman. For more information about pods, see Managing Pods.
In general, the instructions provided here apply similarly regardless of whether Podman runs as a standard user or as the root user.
Running Commands With Podman
You can review a list of the commands available for the installed version of Podman by using
the podman -h
command. For example, that list might contain the following
commands:
- attach
-
Attach to the shell of a running container
- auto-update
-
Automatically update containers with automatic updating enabled
- build
-
Build an image from a Containerfile
- commit
-
Create an image based on an edited container
- container
-
Manager existing containers
- cp
-
Copy files and folders between the container and host file system
- create
-
Create a container without starting it
- diff
-
View changes on the container's file system
- events
-
Show Podman event logs for the running container
- exec
-
Run a process in a specified container that's already running
- export
-
Export a container's file system and contents to a compressed archive
- generate
-
Generate systemd unit files and pod YAML files
- healthcheck
-
Run a healthcheck on an existing container
- history
-
Review the history of a specified image
- image
-
Manages existing images
- images
-
Lists images present on the host system
- import
-
Import a compressed archive to create a container file system
- info
-
Show system information for Podman
- init
-
Initialize one or more containers
- inspect
-
Display the existing configuration values for a container or image
- kill
-
Stop running containers with a predefined signal
- load
-
Load an image from a container archive file
- login
-
Log in to a container registry
- logout
-
Log out of a container registry
- logs
-
Review logs for a container
- manifest
-
Create and edit manifest lists and image indexes
- mount
-
Mount a running container's root file system
- network
-
Manage networks that are accessible to containers
- pause
-
Suspend all the processes in one or more containers
- play
-
Start a Pod
- pod
-
Create and manage pods
- port
-
List network port mappings for a container
- ps
-
List containers
- pull
-
Pull an image from a container registry
- push
-
Push an image to a container registry
- restart
-
Restart one or more containers
- rm
-
Remove one or more containers
- rmi
-
Remove one or more images from local storage on the host system
- run
-
Run a single command in a new container
- save
-
Save an image to a compressed archive
- search
-
Search a container registry for an image
- start
-
Start one or more containers
- stats
-
Display a real time stream of container resource usage statistics
- stop
-
Stop one or more containers
- system
-
Manage Podman configuration settings
- tag
-
Add another name to an image in local storage on the host system
- top
-
Display the running processes for a container
- unmount
-
Unmount a running container's root file system
- unpause
-
Resume all processes for one or more containers
- unshare
-
Run a command as a specified user
- untag
-
Remove a secondary name from an image in local storage on the host system
- version
-
Show version information for Podman
- volume
-
Manage container storage volumes
- wait
-
Block processes on one or more containers until a specified condition is fulfilled
Each of the listed commands is linked to a manual page that
follows the
podman-command(1)
pattern. For example, to retrieve information about the
attach
command, see the
podman-attach(1)
manual page. For a full list
of all the documentation available for Podman, see the
podman(1)
manual page.
Working With Container Images
A container image is a read-only template that's used to generate a container. The image contains all the requirements for a service or application to run. Images can be limited in scope, for example, to host a single service such as a web server application. Or, images can be extensive enough to include a basic OS environment, such as a minimal Oracle Linux release.
Images can be tagged to enable you to identify different versions of the same image. Often
an image might include a default tag of latest
so that Podman users can
easily identify the most recent version of the image. Note that Oracle Linux images don't use
the latest
tag. See Oracle Linux Container Image Tagging Conventions
for more information.
Images are often hosted on container registries that can be accessed over HTTP/S by Podman instances to obtain particular image versions. Registries are described in more detail in Using Container Registries.
Sometimes, you might want to change an existing image or create custom images, which can be done by using the Buildah utility. See Building Images With Buildah for more information.
Searching for Images in Available Registries
You can search the configured registries for an image by using the podman search command:
podman search oraclelinux
For more information about how to configure container registries for use with Podman, see Using Container Registries
Pulling Images From a Registry
When you have found an image, download a copy of it by using the podman pull command. When pulling an image, specify the image reference as follows:
podman pull registry.host/repository/imagename:tag
-
The registry.host is the resolvable hostname of the registry where the image is hosted. Although the registry host is often required, if the registry is already listed within the podman configuration you don't need to specify this value.
-
The repository is optional and depends on how images are stored and on the registry.
-
The imagename is required to specify which image to download.
-
The tag represents a version of the image and should always be specified. Many tools default to using the
latest
tag if no tag is specified but this can lead to errors and is now considered bad practice. See Oracle Linux Container Image Tagging Conventions for more information on tags and why thelatest
tag is unreliable.
The following example shows how to pull a slim Oracle Linux 8 image from the Oracle Container Registry:
podman pull container-registry.oracle.com/os/oraclelinux:8-slim
Trying to pull container-registry.oracle.com/os/oraclelinux:8-slim...
Getting image source signatures
Copying blob ea539e45e250 done |
Copying config 4acc8010c4 done |
Writing manifest to image destination
4acc8010c44238ca15b2faab0828cde14bee7899e19c244d042a662ccdc1b419
Because the Oracle Container Registry is configured for Podman by default, this command could equally be specified as follows:
podman pull os/oraclelinux:8-slim
Shortcuts to registries and repositories for some commonly used image names are stored in
/etc/containers/registries.conf.d/000-shortnames.conf
. These shortcuts
enable you to easily pull an image without needing to know the registry or repository to
search, for example:
podman pull oraclelinux:8-slim
The image is downloaded into the local container image store. This storage is described in more detail in Configuring Storage for Podman.
Inspecting an Image
After the download has completed, you can check the default configuration settings and metadata for a container image by running the following command:
podman inspect container-registry.oracle.com/os/oraclelinux:8-slim
The command provides similar JSON output to the following example:
[
{
"Id": "4acc8010c44238ca15b2faab0828cde14bee7899e19c244d042a662ccdc1b419",
"Digest": "sha256:9db31544a3391749411dc684fefd9d4193f9b553d8d76e8ffa626b1341df3850",
"RepoTags": [
"container-registry.oracle.com/os/oraclelinux:8-slim"
],
"RepoDigests": [
"container-registry.oracle.com/os/oraclelinux@sha256:0877d739d9f8..d90c",
"container-registry.oracle.com/os/oraclelinux@sha256:9db31544a339..3850"
],
"Parent": "",
"Comment": "",
"Created": "2024-08-20T16:21:05.373298261Z",
"Config": {
"Env": [
"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
],
"Cmd": [
"/bin/bash"
],
"Labels": {
"io.buildah.version": "1.24.1"
}
},
"Version": "",
"Author": "",
"Architecture": "amd64",
"Os": "linux",
"Size": 117976202,
"VirtualSize": 117976202,
"GraphDriver": {
"Name": "overlay",
"Data": {
"UpperDir": "/home/opc/.local/share/containers/storage/overlay/213d..5d4/diff",
"WorkDir": "/home/opc/.local/share/containers/storage/overlay/213d..5d4/work"
}
},
"RootFS": {
"Type": "layers",
"Layers": [
"sha256:213d49d043c850ae9bbbdf6cd2c7af7f34b597fa120f0a5e37a5a3299d0e45d4"
]
},
"Labels": {
"io.buildah.version": "1.24.1"
},
"Annotations": {},
"ManifestType": "application/vnd.docker.distribution.manifest.v2+json",
"User": "",
"History": [
{
"created": "2024-08-20T16:21:03.543613694Z",
"created_by": "/bin/sh -c #(nop) ADD file:16087ba6cc0b151..7208 in / "
},
{
"created": "2024-08-20T16:21:05.373437656Z",
"created_by": "/bin/sh -c #(nop) CMD [\"/bin/bash\"]",
"empty_layer": true
}
],
"NamesHistory": [
"container-registry.oracle.com/os/oraclelinux:8-slim"
]
}
]
Listing Available Images
To list all the locally stored container images that have already been downloaded, run the following command:
podman images
The command provides similar output to the following example:
REPOSITORY TAG IMAGE ID CREATED SIZE
container-registry.oracle.com/os/oraclelinux 9-slim 104b24e77bed 40 hours ago 115 MB
container-registry.oracle.com/os/oraclelinux 8-slim 4acc8010c442 47 hours ago 118 MB
Deleting an Image
To delete a locally stored container image that have already been downloaded, use the podman rmi command:
podman rmi oraclelinux:8-slim
The command provides similar output to the following example:
Untagged: container-registry.oracle.com/os/oraclelinux:8-slim
Deleted: 4acc8010c44238ca15b2faab0828cde14bee..1b419
Note:
You can't delete an image if it's in use by a container, even if the container isn't running. You must remove all the containers that depend on the image before you can remove the image itself.
Managing Containers
Containers are running instances of images. Each container uses an image as its starting point and then loads into run time by using the parameters that are provided when it's created or run.
Containers share namespaces and can access shared port mappings to communicate with each other and with the host system. Podman introduces the concept of pods to the runtime environment. You can use pods to further isolate a group of containers, thereby making it easier to manage a set of services that work together to provision a logical application. See Managing Pods for more information.
Creating Containers
You can create a container from an existing image using the podman create command.
podman create --name oracle oraclelinux:8-slim
If the image doesn't already exist on the local system, Podman searches the remote registries for a matching image and pulls the image automatically.
You can specify other options when creating a container, such as whether it belongs to a particular pod or whether it uses a particular network or port mapping. Run podman help create to see more information. Options are extensive and can be used to apply a wide range of runtime functionality to any container.
Running Containers
You run a single command in a container that's provisioned and destroy in a single step by using the podman run command with the --rm flag, for example:
podman run --rm oraclelinux:8-slim cat /etc/oracle-release
Oracle Linux Server release 8.10
You can also create a container and connect to it in a single step by using the -it flag. The -i flag makes the container interactive and -t connects the local terminal to the container. This flag combination is commonly used in conjunction when running a specified shell as part of the podman run command.
podman run --name=oracleshell -it oraclelinux:8-slim /bin/bash
bash-4.4#
The container stops as soon as you disconnect by typing exit. To restart the container and connect to it again, run the podmand start command:
podman start -ai oracleshell
You can also create Podman containers that continue to run as a background daemon by including the -d flag in the command, for example:
podman run -d --name=oracledaemon oraclelinux:8-slim /bin/bash -c 'sleep 1000'
If you run a container that doesn't already exist, it's created automatically. If the image that the container uses isn't available locally, Podman searches the remote registries for a matching image and pulls the image automatically.
Note:
If a container runs a shell as the primary process (PID 1) and you intend to detach it, run
it with the --stop-signal=SIGHUP
command option so that the shell is
stopped cleanly when you stop the container. For example:
podman run --stop-signal SIGHUP --name=myol8 oraclelinux:8-slim
Many shells ignore the default SIGTERM signal when stopping a container. If the correct stop-signal isn't used, the container might return the following error when the container is stopped:
WARN[0010] StopSignal SIGTERM failed to stop container myol8 in 10 seconds, resorting to SIGKILL
Enabling FIPS Mode in Containers
To run containers in FIPS mode, you must first enable FIPS mode on the Oracle Linux host system.
For more information about enabling FIPS mode on Oracle Linux 8 hosts, see Oracle Linux 8: Enhancing System Security.
For more information about enabling FIPS mode on Oracle Linux 9 hosts, see Oracle Linux 9: Enhancing System Security.
After you have enabled FIPS mode on an Oracle Linux 8 or Oracle Linux 9 host, Podman runs Oracle Linux 8 and Oracle Linux 9 containers in FIPS mode automatically.
Note:
Oracle provides FIPS compliant container images by using the slim-fips
tag. Container images tagged as FIPS compliant include compliant cryptographic package
versions and initial image setup required for container FIPS mode. If you use these images
you don't need to perform any extra steps to configure a container for FIPS mode. See The slim tag for more information.
For Oracle Linux 7 Containers:
To enable FIPS mode in an Oracle Linux 7 container, install the dracut-fips
package or mount /etc/system-fips
from the host. For more information about
mounting host files and directories inside a Podman container, see Setting Up Container Mounts.
Listing and Monitoring Containers
You can list all the running Podman containers by using the podman ps command. Use the -a flag to also display the stopped and paused containers:
podman ps -a
The command provides similar output to the following example:
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
3a430d30612d container-registry.oracle.com/os/oraclelinux:8-slim /bin/bash -c sle... 20 seconds ago Up 19 seconds ago oracledaemon
dcbe94cd0301 container-registry.oracle.com/os/oraclelinux:8-slim /bin/bash 58 seconds ago Exited (0) 29 seconds ago oracleshell
726d97e9bfbd container-registry.oracle.com/os/oraclelinux:8-slim top 3 days ago Created oracle
To review the logs generated by a container that has already performed actions, use the podman logs command.
podman logs oracledaemon
In the sample command, oracledaemon can be either the container's ID or name.
To review the hardware resource usage statistics for any running container, use the podman stats command.
podman stats oracledaemon
The command provides similar output to the following example:
ID NAME CPU % MEM USAGE / LIMIT MEM % NET IO BLOCK IO PIDS
c4e296d0c78e oracledaemon 4.25% 33.33MB / 29.22GB 0.11% 2.412kB / 1.536kB -- / -- 3
To review statistics for containers without root permissions, you need to enable cgroups
v2
on the host system. For more information about enabling cgroups
v2, see Oracle Linux 8: Managing Core System Configuration or Oracle Linux 9: Managing Core System
Configuration.
Pausing and Resuming Containers
If you need to temporarily halt the operation of a container without destroying its workload, you can use the podman pause command and specify the container name or ID.
podman pause oracledaemon
Running the previous command freezes all the running processes inside a container, in their current state:
When you're ready for the container to resume where it was halted, you can instruct the container to continue with its previous operation from that point by using the podman unpause command, for example:
podman unpause oracledaemon
Stopping and Removing Containers
To stop containers by specifying the name or container ID with the podman stop command:
podman stop oracledaemon
If you need to temporarily take the server down for maintenance, you can stop every running container that hasn't already been paused by appending the -a flag to the podman stop command:
podman stop -a
Specify the container name or ID with the podman rm command to delete a specified container:
podman rm oracleshell
Managing Pods
Podman introduces the concept of the pod within the context of a container runtime. This concept is borrowed from Kubernetes and isn't available in Oracle Container Runtime for Docker.
A pod is a collection of containers that are grouped together into a single namespace so that they can share resources, such as local networking to communicate with each other and interact. A pod can be used to group a set of services that you need to deploy a complete application.
In many ways a pod behaves similar to a virtual host on which the services within each container are run. This means that each container can access the services on each other container as if they were running on the same host. Running containers in this way can remove a lot of complexity around networking and can make it easier to limit public exposure of ports that are only intended for use by services within the application itself.
Finally, by running containers within pods, it's easier to set up and tear down entire application environments using atomic operations. By using pods, you can create service wrappers to automatically start a set of containers for an application at boot. See Working With Podman Services for more information.
Creating and Managing Pods
The concept of pods is derived from Kubernetes pods. Podman pods are the smallest compute units that you can create and deploy in a Kubernetes environment. These pods include an infra container so that Podman can connect with all the containers within the pod. Podman can manage the containers in the pod, such as stopping containers, without interfering with the operation of the pod itself.
Create a pod with the podman pod create command. Add the --name parameter to give the pod a human-readable identifier.
podman pod create --name oraclepod
You can also set the --hostname option if services within the pod need to use a particular hostname when connecting to each other.
Pods can also be created automatically when a container is run for the first time. See Using Containers Within a Pod for more information.
List all the available and running pods by using the podman pod ps or podman pod list command.
podman pod list
Remove the pod by using the rm command.
podman pod rm oraclepod
Note that you can only remove a pod when all the containers within the pod have been removed, except for the infrastructure container. By default, an infrastructure container is created for each pod, so a pod normally contains at least one container which can only be removed by removing the pod itself. You can see which containers are within the pod by using the podman pod inspect command.
Using Containers Within a Pod
To attach containers to a pod, use the --pod flag when you run the container.
podman run -d --pod oraclepod nginx:alpine
podman run --pod oraclepod -it --rm oraclelinux:8-slim curl http://localhost:80
In the previous example, a container using the nginx
image is run and
connected to the pod named oraclepod. A second container, using the
oraclelinux
image is started and connected to the same pod. The
curl command is run in the second container to access the web service
running on localhost
on port 80. The containers are both running as standard
user but can use a reserved port within the pod without any port mapping required.
Furthermore, the containers can both use the localhost
network namespace and
can access each other as if they were running on the same host. This example provides an
illustration of how pods can make it easier for services running within different containers
to access each other and work together without any requirement for complex networking.
If a pod doesn't already exist, you can create it directly by using the podman run command with the --pod option and prepending the new: option to the human-readable name that you have chosen as the pod name:
podman run -d --pod new:oraclepod nginx:alpine
Review all the containers on a host with the pod to which the containers are attached by including the --pod or -p flag with the podman ps -a command.
podman ps -ap
You can start and stop containers as usual without affecting the entire pod; however, you can also use the podman pod start and podman pod stop commands to start and stop every container that exists within the same pod simultaneously, for example:
podman pod stop oraclepod
podman pod start oraclepod
To check the current status of a pod, use the podman pod ps command:
podman pod ps