Skill

detect-platform

detect-platform · current version v1

Download v1

Detect the host platform before troubleshooting anything else — OS and package family, init system, whether it is bare metal, a VM, a container, or a Kubernetes pod, the real CPU/RAM/disk and the cgroup memory limit, and the security module (SELinux/AppArmor). Produces a compact platform profile the service-specific skills rely on. Use this first when diagnosing any server, database, or service, so later steps use the right package manager, unit names, paths, and resource limits.

20 downloads · published 2026-09-02

What this grants

Skill Card

Security Audits

Version history

VersionPublishedStatus
v1 2026-09-02 published

Files

SKILL.md

raw | preview

---
name: detect-platform
description: Detect the host platform before troubleshooting anything else — OS and package family, init system, whether it is bare metal, a VM, a container, or a Kubernetes pod, the real CPU/RAM/disk and the cgroup memory limit, and the security module (SELinux/AppArmor). Produces a compact platform profile the service-specific skills rely on. Use this first when diagnosing any server, database, or service, so later steps use the right package manager, unit names, paths, and resource limits.
---

# Detect Platform

Run this first, before any service-specific troubleshooting. Most support mistakes are not about
the service — they are about assuming the environment: `apt` on a `dnf` box, a unit that has a
different name here, "8 GB of RAM" when the container is capped at 512 MB, a 403 that is really
SELinux. This skill establishes the ground truth once and hands the next skill a short profile.

Detection only. It reads; it changes nothing. Every command here is safe to run on a production
host. If a command is missing or returns nothing, record "unknown" and move on — an absent tool
is itself a signal (no `systemctl` usually means not systemd).

## Probe, top to bottom

**OS and package family** — decides package manager, unit names, config paths.
```bash
grep -E '^(PRETTY_NAME|ID|ID_LIKE|VERSION_ID)=' /etc/os-release
for p in apt dnf yum apk zypper pacman; do command -v "$p" >/dev/null && echo "pkg: $p"; done
```
`ID=ubuntu`/`ID_LIKE=debian` => `apt`, services often named `<svc>` or `<svc>-server`, config
under `/etc/<svc>/`. `ID=rhel`/`fedora`/`centos` (`ID_LIKE` includes `rhel`) => `dnf`, and
SELinux is in play (below).

**Init system** — decides how you inspect and signal services.
```bash
ps -p 1 -o comm=            # "systemd" => systemctl/journalctl; otherwise adapt (openrc, s6, runit, init)
```

**Substrate — bare metal, VM, container, or pod?** This decides whether host-level tuning even
applies (a container inherits it; bare metal owns it) and where logs go.
```bash
systemd-detect-virt         # "none" => bare metal; a hypervisor name (kvm/vmware/…) => VM;
                            # "docker"/"lxc"/"podman" => container
test -f /.dockerenv && echo "container: docker"
grep -qa 'kubepods' /proc/1/cgroup 2>/dev/null && echo "kubernetes: pod"
[ -n "$KUBERNETES_SERVICE_HOST" ] && echo "kubernetes: yes (service env present)"
```

**Resources — and the cgroup limit, which is the one that fools people.** The process sees the
cgroup limit, not the host's RAM; a service sized for the host gets OOM-killed inside a smaller
container.
```bash
nproc                                   # visible CPUs
free -h | awk '/Mem:/{print $2" total, "$7" available"}'
# cgroup v2 (most modern hosts):
cat /sys/fs/cgroup/memory.max           # a number = the hard cap in bytes; "max" = no limit
cat /sys/fs/cgroup/cpu.max              # "<quota> <period>"; "max <period>" = uncapped
# cgroup v1 fallback:
cat /sys/fs/cgroup/memory/memory.limit_in_bytes 2>/dev/null
```
If `memory.max` is a real number well below `free -h` total, **that number is the ceiling** —
quote it to the service skill, which will size caches/workers against it.

**Disk and filesystem** — for the data path the service actually uses.
```bash
df -h /                                 # and df -h <data-dir> for the service's dbPath/dir
findmnt -no FSTYPE,OPTIONS /            # ext4/xfs/btrfs; note "noatime", and overlay => container layer
```

**Security module** — the top cause of "permission denied / 403" that is not a file mode.
```bash
getenforce 2>/dev/null                  # Enforcing/Permissive/Disabled (RHEL family); absent elsewhere
command -v aa-status >/dev/null && aa-status --enabled && echo "apparmor: enabled"   # Debian/Ubuntu
```
`Enforcing` means a denial may be SELinux, not the service — the service skill will point at
`ausearch -m avc` and booleans/labels rather than at file modes.

## The profile to carry forward

Assemble what you found into a few lines and keep it in front of you for the rest of the
session. Example from a real run of the commands above:

```
os: Ubuntu 24.04 (debian family, apt)     init: systemd
substrate: bare metal                      k8s: no
cpu: 24                                     ram: 124Gi total
cgroup mem limit: none (bare metal)         rootfs: ext4 on LVM, 1.8T (46% used)
security: AppArmor enabled; SELinux n/a
```

Then hand these facts to the service skill: they tell it the package manager and unit names to
use, whether host tuning applies, the memory ceiling to size against, and whether a permission
failure is likely the security module. Do not re-detect them in the service skill — it assumes
this ran.

## Scope

- Detection and interpretation only — no installs, no config changes, no restarts.
- Unknown is a valid answer. Record it and continue; a later step can probe deeper if it matters.
- This is host/substrate detection, not service discovery. Which services run, and their
  versions, belong to each service's own skill.