docs: add Kubernetes CKS study notes
This commit is contained in:
144
kubernetes/level 1/task-10.md
Normal file
144
kubernetes/level 1/task-10.md
Normal file
@@ -0,0 +1,144 @@
|
||||
# Assignment
|
||||
|
||||
The Nautilus DevOps team needs a time check pod created in a specific Kubernetes namespace for logging purposes. Initially, it's for testing, but it may be integrated into an existing cluster later. Here's what's required:
|
||||
|
||||
|
||||
Create a pod called time-check in the nautilus namespace. The pod should contain a container named time-check, utilizing the busybox image with the latest tag (specify as busybox:latest).
|
||||
|
||||
Create a config map named time-config with the data TIME_FREQ=7 in the same namespace.
|
||||
|
||||
Configure the time-check container to execute the command: while true; do date; sleep $TIME_FREQ;done. Ensure the result is written /opt/finance/time/time-check.log. Also, add an environmental variable TIME_FREQ in the container, fetching its value from the config map TIME_FREQ key.
|
||||
|
||||
Create a volume log-volume and mount it at /opt/finance/time within the container.
|
||||
|
||||
Note: The kubectl utility on the jump-host has been configured to work with the Kubernetes cluster.
|
||||
|
||||
# Solution
|
||||
|
||||
# Kubernetes Pod + ConfigMap — `time-check` in `nautilus`
|
||||
|
||||
A `time-check` pod that loops `date` into a log file on a mounted volume, reading its
|
||||
sleep interval from a ConfigMap-backed env var. Applied inline via a multi-document
|
||||
heredoc — no manifest file on disk.
|
||||
|
||||
## Apply (heredoc → kubectl)
|
||||
|
||||
```bash
|
||||
kubectl apply -f - <<'EOF'
|
||||
apiVersion: v1
|
||||
kind: Namespace
|
||||
metadata:
|
||||
name: nautilus
|
||||
---
|
||||
apiVersion: v1
|
||||
kind: ConfigMap
|
||||
metadata:
|
||||
name: time-config
|
||||
namespace: nautilus
|
||||
data:
|
||||
TIME_FREQ: "7"
|
||||
---
|
||||
apiVersion: v1
|
||||
kind: Pod
|
||||
metadata:
|
||||
name: time-check
|
||||
namespace: nautilus
|
||||
spec:
|
||||
containers:
|
||||
- name: time-check
|
||||
image: busybox:latest
|
||||
command:
|
||||
- /bin/sh
|
||||
- -c
|
||||
- "while true; do date; sleep $TIME_FREQ; done >> /opt/finance/time/time-check.log"
|
||||
env:
|
||||
- name: TIME_FREQ
|
||||
valueFrom:
|
||||
configMapKeyRef:
|
||||
name: time-config
|
||||
key: TIME_FREQ
|
||||
volumeMounts:
|
||||
- name: log-volume
|
||||
mountPath: /opt/finance/time
|
||||
volumes:
|
||||
- name: log-volume
|
||||
emptyDir: {}
|
||||
EOF
|
||||
```
|
||||
|
||||
## How it works
|
||||
|
||||
### The heredoc apply pattern
|
||||
|
||||
- **`kubectl apply -f -`** reads from **stdin**; `---` separates the three documents,
|
||||
processed in order so the **Namespace → ConfigMap → Pod** dependency chain is satisfied.
|
||||
- **`<<'EOF'` (delimiter quoted)** is critical here: it stops the jump-host's shell from
|
||||
expanding `$TIME_FREQ` when you paste the command. The literal `$TIME_FREQ` must reach the
|
||||
manifest untouched so the **container's** shell expands it at runtime from the env var.
|
||||
An unquoted heredoc would blank it out before it ever got to Kubernetes.
|
||||
|
||||
### The Namespace
|
||||
|
||||
- **`kind: Namespace` / `name: nautilus`** — created first so the ConfigMap and Pod have
|
||||
somewhere to live. If `nautilus` already exists, `apply` is idempotent and simply no-ops.
|
||||
|
||||
### The ConfigMap
|
||||
|
||||
- **`name: time-config`, `namespace: nautilus`** — as required.
|
||||
- **`data.TIME_FREQ: "7"`** — the key/value the pod reads. The value is **quoted** because
|
||||
ConfigMap values must be strings; an unquoted `7` would be a YAML integer and rejected.
|
||||
|
||||
### The Pod
|
||||
|
||||
- **`name: time-check`, `namespace: nautilus`**, container **`name: time-check`**,
|
||||
**`image: busybox:latest`** — all exactly as required.
|
||||
|
||||
- **`command`** — run via `/bin/sh -c` so the shell interprets the loop and, crucially,
|
||||
expands `$TIME_FREQ`. The loop prints `date` every `$TIME_FREQ` seconds; the
|
||||
`>> /opt/finance/time/time-check.log` redirect on the **whole loop** opens the log file
|
||||
once and appends each timestamp to it continuously. That satisfies "the result is written
|
||||
to /opt/finance/time/time-check.log."
|
||||
|
||||
- **`env` with `valueFrom.configMapKeyRef`** — injects an env var named `TIME_FREQ` whose
|
||||
value is pulled from the `TIME_FREQ` key of the `time-config` ConfigMap. This is the link
|
||||
between requirement 2 and the `$TIME_FREQ` in the command — the container gets `7` at
|
||||
runtime without hardcoding it.
|
||||
|
||||
- **`volumeMounts` + `volumes`** — the two halves of attaching storage:
|
||||
- **`volumes: - name: log-volume / emptyDir: {}`** declares a volume named `log-volume`.
|
||||
`emptyDir` is an ephemeral, pod-lifetime scratch volume — the simplest choice for a log
|
||||
location the task doesn't require to persist.
|
||||
- **`volumeMounts: - name: log-volume / mountPath: /opt/finance/time`** mounts that volume
|
||||
into the container at `/opt/finance/time`, which is where the log file is written. The
|
||||
`name` on both sides must match, or Kubernetes can't wire them together.
|
||||
|
||||
### Why the mount path and log path line up
|
||||
|
||||
The command writes to `/opt/finance/time/time-check.log`, and the volume is mounted at
|
||||
`/opt/finance/time`. So the log file lands **inside** the mounted volume — meaning the
|
||||
directory exists (the mount creates it) and the write succeeds. If the mount path and the
|
||||
log directory didn't match, the write could fail or land on the container's ephemeral
|
||||
root filesystem instead.
|
||||
|
||||
## Verify
|
||||
|
||||
```bash
|
||||
# ConfigMap present with the value
|
||||
kubectl get configmap time-config -n nautilus -o jsonpath='{.data.TIME_FREQ}{"\n"}'
|
||||
|
||||
# Pod running
|
||||
kubectl get pod time-check -n nautilus -o wide
|
||||
|
||||
# Env var resolved from the ConfigMap
|
||||
kubectl exec time-check -n nautilus -- printenv TIME_FREQ
|
||||
|
||||
# Log file is being written inside the mounted volume
|
||||
kubectl exec time-check -n nautilus -- cat /opt/finance/time/time-check.log
|
||||
```
|
||||
|
||||
Expected — ConfigMap value `7`, pod `Running`, `printenv` showing `TIME_FREQ=7`, and the
|
||||
log file accumulating timestamps roughly every 7 seconds.
|
||||
|
||||
> Remember `-n nautilus` on every command — nothing here is in `default`. If the pod is
|
||||
> `Error`/`CrashLoopBackOff`, check `kubectl logs time-check -n nautilus` (though output goes
|
||||
> to the log file, so the pod's stdout may be quiet).
|
||||
Reference in New Issue
Block a user