OpenShift & Containers
Complete Guide
All key concepts, bash commands, and architectures extracted from four official Red Hat student workbooks and organized into one progressive knowledge reference.
Container Fundamentals
A container is an encapsulated process that includes all required runtime dependencies. Unlike a virtual machine, a container shares the host kernel but isolates its filesystem, network, and process tree using Linux kernel primitives.
Namespaces
Kernel feature that isolates processes — each container gets its own PID, network, mount, UTS, IPC, and user namespaces, providing the illusion of a dedicated machine.
Control Groups (cgroups)
Kernel mechanism for resource management. Limits and tracks CPU time, memory, disk I/O, and network bandwidth allocated to containers.
Container Image
An immutable, layered archive defining an application and its libraries. Read-only layers are stacked via a union filesystem; a writable layer is added at runtime.
Container Instance
A running process created from a container image. Analogous to an object instantiated from a class. Many instances can run from a single image simultaneously.
OCI Standard
The Open Container Initiative defines image-spec and runtime-spec so any compliant engine (Podman, Docker, CRI-O) can run the same images interchangeably.
Ephemeral by Default
Container engines remove the writable layer when a container is deleted. Any data written inside a container is lost unless explicitly persisted via a volume or bind mount.
Containers vs. Virtual Machines
| Attribute | Virtual Machine | Container |
|---|---|---|
| Machine-level component | Hypervisor (KVM, VMware, Hyper-V) | Container engine (Podman, CRI-O) |
| Virtualization level | Fully virtualized environment + own kernel | Shared host kernel; isolated user-space only |
| Typical size | Gigabytes | Megabytes |
| Startup time | Minutes | Milliseconds to seconds |
| Portability | Usually tied to same hypervisor | Any OCI-compliant engine |
| Best for | Full OS isolation, non-Linux workloads | Microservices, scale-out applications |
Podman — Container Engine
Podman (Pod Manager) is a daemonless, rootless-capable OCI container engine from Red Hat. Unlike Docker, it does not require a background daemon — each podman invocation runs as a regular process, reducing attack surface.
Checking the Installation
Running Your First Container
Managing Container Lifecycle
| Command | Description |
|---|---|
podman ps | List running containers |
podman ps --all | List all containers including stopped ones |
podman ps --all --format=json | Output container list as JSON |
podman stop <name|id> | Send SIGTERM, then SIGKILL after timeout (default 10 s) |
podman stop -t 30 <name> | Graceful stop with custom timeout |
podman kill <name> | Send SIGKILL immediately |
podman start <name> | Restart a stopped container |
podman restart <name> | Stop then start a container |
podman rm <name|id> | Remove a stopped container |
podman rm -f <name> | Force-remove a running container |
podman pause / unpause <name> | Freeze / resume all processes in a container using cgroup freezer |
Inspecting and Interacting with Containers
Rootless Containers
Rootless Podman runs containers without root privileges. The user namespace maps the container's internal root (UID 0) to the current unprivileged host user. This limits the blast radius of container escapes.
Container Images & Registries
A container image is a read-only, layered archive (OCI image-spec). Each layer is a diff of filesystem changes. Layers are cached and shared between images to save disk space.
Image Naming Convention
Pulling, Listing, Tagging, Removing Images
Registry Authentication
Skopeo — Registry Manipulation Without Pulling
Skopeo works with container images at the registry level, without needing a running container engine. It inspects, copies, and deletes images across registries efficiently.
Building Custom Images — Containerfile
A Containerfile (compatible with Dockerfile syntax) is a text recipe for building a container image. Each instruction creates a new immutable layer.
Essential Containerfile Instructions
| Instruction | Purpose | Example |
|---|---|---|
FROM | Base image to build upon. Every Containerfile starts here. | FROM ubi8/ubi-minimal:8.8 |
RUN | Execute a shell command during build (creates a layer). | RUN dnf install -y python3 && dnf clean all |
COPY | Copy files from build context into the image. | COPY app.py /app/app.py |
ADD | Like COPY but also handles URLs and auto-extracts tar archives. | ADD app.tar.gz /app/ |
WORKDIR | Set working directory for subsequent instructions. | WORKDIR /app |
ENV | Set environment variables available at build and runtime. | ENV PORT=8080 DEBUG=false |
ARG | Build-time variable (not available at runtime unless set in ENV too). | ARG VERSION=1.0 |
EXPOSE | Documents which port the container listens on (informational only). | EXPOSE 8080 |
USER | Switch to a non-root user for all subsequent instructions and the final container. | USER 1001 |
ENTRYPOINT | Main command that always runs (use exec form JSON array). | ENTRYPOINT ["python3", "-m", "http.server"] |
CMD | Default arguments for ENTRYPOINT, or the default command if no ENTRYPOINT. | CMD ["8080"] |
LABEL | Attach key-value metadata to the image. | LABEL version="1.0" maintainer="team@example.com" |
VOLUME | Declare a mount point for persistent storage. | VOLUME /data |
HEALTHCHECK | Define a command to probe container health. | HEALTHCHECK CMD curl -f http://localhost:8080/health || exit 1 |
Multi-Stage Build Example
Multi-stage builds produce small production images by separating the build environment from the runtime environment.
Building Images with Podman
OpenShift requires containers to run as non-root. Always add USER 1001 (or any UID above 1000) as the last USER instruction. OpenShift will reject pods whose containers run as UID 0 unless a special SCC is granted.
Persisting Data — Volumes & Bind Mounts
Containers are ephemeral; data written inside is lost on removal. There are two main mechanisms to persist data outside the container lifecycle.
Podman Named Volumes
Named volumes are managed by Podman, stored under ~/.local/share/containers/storage/volumes/ (rootless) or /var/lib/containers/storage/volumes/ (root). They survive container removal.
Bind Mounts
Bind mounts map a host directory into the container. Useful during development to share source code.
Running a Database Container with Persistent Storage
Container Networking
Podman uses a software-defined network layer (CNI or Netavark) to connect containers. By default, each container gets a private IP address on the podman bridge network. DNS-based name resolution works between containers on the same user-defined network.
Podman Network Commands
Containers on the same user-defined network can reach each other by container name. For example, a web app on app-net can reach a database named db at db:5432. The default podman network does not provide DNS.
Troubleshooting Containers
Log Access and Debugging
Multi-Container Applications with Podman Compose
Podman Compose reads a docker-compose.yml / compose.yaml file and translates each service into Podman containers, networks, and volumes. It is ideal for local development environments.
Sample Compose File
Podman Compose Commands
Kubernetes Architecture
Kubernetes is an open-source container orchestration system. It groups containers into Pods, ensures desired state, scales workloads, and manages networking and storage across a cluster of nodes.
Control Plane
Runs the API server (kube-apiserver), scheduler, controller manager, and etcd. Manages cluster state and makes scheduling decisions.
Worker Nodes
Run the kubelet (node agent), kube-proxy, and a container runtime (CRI-O). Execute the actual workloads.
Pod
The smallest deployable unit — a group of one or more tightly coupled containers sharing a network namespace (same IP) and storage volumes.
ReplicaSet
Ensures a specified number of Pod replicas are always running. Replaces failed pods automatically.
Deployment
Manages ReplicaSets declaratively. Enables rolling updates, rollbacks, and scaling. The standard way to deploy stateless apps.
Service
A stable virtual IP and DNS name that load-balances traffic to a set of matching Pods. Types: ClusterIP, NodePort, LoadBalancer.
etcd
Distributed key-value store that holds all cluster state (resource definitions, secrets, configuration). The single source of truth.
Namespace
Virtual cluster within Kubernetes for multi-tenancy. Resources in different namespaces are isolated, and resource quotas can be applied per namespace.
kubectl — Kubernetes CLI
Red Hat OpenShift Container Platform
Red Hat OpenShift (RHOCP) is an enterprise Kubernetes distribution that adds developer tools, security hardening, integrated CI/CD (Tekton/Pipelines), a web console, and enterprise support on top of upstream Kubernetes.
Logging In and Basic Navigation
Key OpenShift-Specific Concepts
Project
OpenShift's enhanced Namespace. Adds access control, network policies, and resource quota isolation per team or application.
Route
OpenShift extension to expose services to external traffic via a hostname. Backed by HAProxy; supports TLS termination (edge, passthrough, re-encrypt).
Security Context Constraint (SCC)
Cluster-level policy controlling what a pod can do (run as root, mount host paths, use host network, etc.). Default SCC prevents privileged operations.
ImageStream
A pointer to container images that triggers automatic redeployments when the referenced image changes. Decouples image location from deployment config.
BuildConfig
Defines how to build a container image from source — supports Docker, Source-to-Image (S2I), and custom build strategies.
Operator
A Kubernetes controller that encodes operational knowledge for managing a complex application (e.g., database clusters). Extends the Kubernetes API with CRDs.
Managing Workloads in OpenShift
Deploying Applications with oc new-app
Viewing and Managing Resources
Exposing Services via Routes
StatefulSets — Stateful Workloads
For stateful applications (databases, message queues), use a StatefulSet. Pods get stable network identifiers (mydb-0, mydb-1) and each gets its own PersistentVolumeClaim.
Builds — Source-to-Image (S2I)
Source-to-Image (S2I) is an OpenShift build strategy that takes application source code and a builder image, injects the source, runs the build scripts, and produces a ready-to-run container image — without writing a Containerfile.
S2I Build Commands
BuildConfig YAML Example
ImageStreams
Injecting Configuration — ConfigMaps & Secrets
Applications should not bake configuration into images. ConfigMaps hold non-sensitive configuration; Secrets hold sensitive data (passwords, tokens, keys) as base64-encoded values.
ConfigMaps
Secrets
Persistent Storage in OpenShift
Kubernetes storage model decouples how storage is provisioned (PersistentVolume) from how it is requested (PersistentVolumeClaim).
Storage Object Hierarchy
Access Modes
| Mode | Short Form | Meaning |
|---|---|---|
ReadWriteOnce | RWO | One node can read and write. Suitable for block storage (AWS EBS, iSCSI). |
ReadOnlyMany | ROX | Many nodes can read. Suitable for shared read-only configuration. |
ReadWriteMany | RWX | Many nodes can read and write. Requires distributed storage (NFS, CephFS, GlusterFS). |
ReadWriteOncePod | RWOP | Only a single Pod can access at a time (K8s 1.22+). Strongest isolation. |
Working with PVCs
Application Reliability — Health Probes & Autoscaling
Health Probe Types
Liveness Probe
Checks if the application is still running. If it fails, Kubernetes restarts the container. Detects deadlocks and infinite loops.
Readiness Probe
Checks if the application is ready to serve traffic. A failing readiness probe removes the pod from Service endpoints, preventing traffic to a still-starting app.
Startup Probe
Gates the liveness and readiness probes until the application has started. Critical for slow-starting applications to prevent premature restarts.
Horizontal Pod Autoscaler (HPA)
Resource Quotas & LimitRanges
Authentication, Authorization & RBAC
OpenShift supports multiple identity providers. The most common lab/on-premises choice is HTPasswd. Role-Based Access Control (RBAC) governs what authenticated users can do.
HTPasswd Identity Provider
RBAC — Roles and RoleBindings
| Resource | Scope | Purpose |
|---|---|---|
Role | Namespace | Defines a set of allowed API verbs (get, list, watch, create, update, delete) on specific resources within a namespace. |
RoleBinding | Namespace | Binds a Role (or ClusterRole) to users/groups/service accounts within a namespace. |
ClusterRole | Cluster-wide | Like Role but applies across all namespaces. Also used for non-namespaced resources (nodes, PVs). |
ClusterRoleBinding | Cluster-wide | Binds a ClusterRole to subjects for cluster-wide access. |
Groups
Declarative Resource Management & Kustomize
The declarative workflow describes desired state in YAML manifests and uses kubectl apply to reconcile the cluster to that state. This is reproducible, auditable (Git-based), and supports GitOps workflows.
Imperative vs. Declarative
| Imperative | Declarative | |
|---|---|---|
| How | kubectl create / delete commands | YAML files + kubectl apply |
| Reproducibility | Difficult — depends on command history | High — files define the exact desired state |
| GitOps compatible | No | Yes |
| Best for | Quick one-off tasks, debugging | Production deployments, CI/CD pipelines |
Kustomize — Configuration Overlays
Kustomize generates Kubernetes manifests from a base and environment-specific overlays without duplicating YAML. It is natively integrated into kubectl and oc.
OpenShift Templates
Templates are OpenShift-native packaged resource sets with parameters. They are stored in the openshift namespace and deployable via the web console or CLI.
Operators & Helm Charts
Kubernetes Operators
An Operator is a Kubernetes controller that manages a specific application using domain knowledge encoded in software. It watches Custom Resources (CRs) and reconciles the cluster to match the desired state defined in those CRs.
Custom Resource Definition (CRD)
Extends the Kubernetes API with new resource types. An Operator registers CRDs and watches for instances to reconcile.
Operator Lifecycle Manager (OLM)
OpenShift's system for installing, updating, and managing Operators cluster-wide. Provides the OperatorHub web UI.
ClusterServiceVersion (CSV)
Operator metadata file describing capabilities, required CRDs, install strategy, and lifecycle details. OLM uses the CSV to install an Operator.
Subscription
Tells OLM which Operator to install, from which catalog, and update channel. OLM keeps the Operator updated as new versions are published.
Helm — Package Management for Kubernetes
Helm packages Kubernetes manifests into charts (versioned, shareable archives). It uses Go templates to parameterize manifests, and tracks installed releases.
Network Policies & TLS
NetworkPolicy resources enforce firewall-like rules between pods and namespaces. By default in OpenShift, all pods in a project can communicate with each other. NetworkPolicies restrict this.
Default Deny + Allow Pattern
Egress Controls
Cluster & Operator Updates
OpenShift uses the Cluster Version Operator (CVO) to manage cluster updates. Updates follow a graph of supported upgrade paths and can be performed with minimal downtime using rolling node replacements.
Update Channels
| Channel | Purpose |
|---|---|
stable-4.x | Fully tested, production-recommended updates for minor version 4.x |
fast-4.x | Updates released faster than stable; less bake time but still tested |
candidate-4.x | Release candidates; not for production |
eus-4.x | Extended Update Support — for customers on a fixed minor version |
Updating Operators via OLM
OpenShift supports updates only between adjacent minor versions (e.g., 4.12 → 4.13 → 4.14). Skipping minor versions requires following the official upgrade graph from Red Hat's upgrade graph tool. Always update the cluster before updating Operators that depend on it.
Quick Reference — Most-Used Commands
Podman Cheat Sheet
| Goal | Command |
|---|---|
| Run a container | podman run -d -p 8080:8080 --name myapp image:tag |
| List running | podman ps |
| List all (including stopped) | podman ps -a |
| Shell into running container | podman exec -it myapp /bin/sh |
| View logs | podman logs -f myapp |
| Stop / remove container | podman stop myapp && podman rm myapp |
| Build image | podman build -t myapp:latest . |
| Push image | podman push quay.io/myorg/myapp:latest |
| List local images | podman images |
| Remove image | podman rmi myapp:latest |
| Multi-container app up | podman-compose up -d |
| Multi-container app down | podman-compose down |
OpenShift / oc Cheat Sheet
| Goal | Command |
|---|---|
| Log in | oc login -u user -p pass https://api.cluster:6443 |
| Switch project | oc project myproject |
| Create project | oc new-project myapp |
| Deploy from image | oc new-app --image registry.io/img:tag |
| List everything | oc get all |
| Watch pods | watch oc get pods |
| Shell into pod | oc rsh pod-name |
| Pod logs | oc logs -f pod-name |
| Scale deployment | oc scale deployment myapp --replicas 3 |
| Expose service as route | oc expose service myapp |
| Apply manifest | oc apply -f manifest.yaml |
| Apply kustomize overlay | oc apply -k overlays/production |
| Grant edit role | oc adm policy add-role-to-user edit user1 |
| Check cluster version | oc get clusterversion |
| Start cluster upgrade | oc adm upgrade --to 4.14.15 |
No comments:
Post a Comment