---
tags: [VPS-IA, disque, audit, OpenCode, Infra]
date: 2026-11-02
description: "Droits 700 expliquaient l'écart df/du : disque ramené de 81 à 63 %, ~18 Go libérés."
nature: documentation
projects:
  - [[03_PROJETS/VPS-IA]]
type: note
---

# Audit disque VPS — 02/11/2026

**Résultat : 81 % → 63 % de disque, soit ~18 Go libérés** (68 Go → 59 Go alloués), hors 6,6 Go supprimés par GRK dans Nextcloud.

## Contexte et méthode

L'alerte de départ : `df` annonçait 76 Go alloués alors que `du` (en utilisateur `opencode`) n'en montrait que 32 → **~44 Go « invisibles »**.

| Hypothèse testée | Résultat |
|---|---|
| Sous-mount caché (`/proc/mounts`) | non — une seule partition `/dev/sda1` |
| Liens physiques comptés une fois (`du --count-links`) | non — 32 Go dans les deux cas |
| Fichiers supprimés mais ouverts (`lsof +L1`) | non (impossible à vérifier sans root, écart résolu ensuite) |
| **Arborescences en 700/750 illisibles pour `opencode`** | **cause réelle** |

Le diagnostic définitif est venu d'un `du` exécuté **en root** : 68 Go visibles pour 69 Go alloués → écart d'~1 Go = journal ext4. **Aucune donnée perdue, aucun espace fantôme.**

### Outils installés pendant l'audit

- `/etc/cron.d/vps-disk-top` → `/usr/local/sbin/vps-disk-top.sh` : top des gros dossiers quotidien (profondeur 1, 03:15 UTC) + détaillé le dimanche (profondeur 2), écrit dans `/var/log/vps-check.log` (rotation déjà gérée par `/etc/logrotate.d/vps-check`, lu par `opencode` via le groupe `adm`).
- L'agent `opencode` n'a **aucun accès sudo** au-delà d'une liste restreinte (`df`, `ss`, `yunohost diagnosis`…) et le coffre `pass` ne contient pas de secret root pour cette machine (`shogun-sudo` = 2e VPS) → tout travail disque root passe par une commande collée par GRK.

## Ce qui a été libéré

| Cible | Gain | Détail |
|---|---|---|
| Suppression Nextcloud (GRK) | 6,64 Gio | visible immédiatement dans `df` (pas de corbeille en route) |
| Reranker QMD | 610 Mo | `.cache/qmd/models` 2,2 → 1,6 Go ; `qmd query` sans `--no-rerank` le re-télécharge seul |
| `qmd cleanup` | 6 Mo | index 33,6 → 28 Mo ; 2207 chunks orphelins, FTS compacté, VACUUM |
| Worktree `misty-nebula` | ~0 | purge via `cron-hebdo-purge-worktrees.sh` |
| Batch 1 (caches root, grist, node-red) | ~3,4 Go | ``/root/.npm` + `/root/.cache` (2,4 Go), caches grist/nodered (1 Go) |
| Anciens binaires OpenCode | ~594 Mo | `.opencode-backups` : gardé `2.1.4` uniquement |
| `/tmp/restore/shizendo` | 171 Mo | doublon de `backups/shizendo-pre-migration-univers_20261030.tar.gz` |
| Ancien install ollama | **4,34 Go** | `/usr/local/lib/ollama` + `/usr/local/bin/ollama` (install manuel fév. 2026) |
| Profils Chromium obsolètes | 791 Mo | 7 `runtime-*` sur 8 ; seul `runtime-Rqaiea` actif conservé |
| `/tmp/opencode` | 349 Mo | 2 clones git propres + backup DB du 18/10 (sous-ensemble vérifié : 0 donnée unique) |

## Détail des gros postes restants (état fin : 59 Go / 63 %)

| Poste | Taille | Statut |
|---|---|---|
| `/home/yunohost.backup/archives` | **11 Go** | **conservé par choix de GRK** — snapshots `*-pre-upgrade` créés à chaque upgrade d'app (36 fichiers, janv. 2026 → oct. 2026), YNH ne les purge jamais. Rétention à revoir si le disque redevient tendu (`onlyoffice` 2,1 Go = 5 mois, `ollama` 2,4 Go = 2 j). |
| `/home/yunohost.app` | 12 Go | `nextcloud/data` 8,7 Go (données) · `ollama/models` 1,4 Go · `silverbullet` 497 Mo · sauvegardes SB < 150 Mo |
| `/var/www` | 11 Go | ollama 2,4 Go · onlyoffice 2,3 Go · grist 1,7 Go · nextcloud 1,2 Go · silverbullet 1,1 Go (dont chrome-data désormais 124 Mo) |
| `/usr` | 18 Go | `usr/share` 8,8 Go (système) · `usr/local` 5,4 Go (dont `lib/ollama` actif 4,3 Go ?) |
| `/var` | 19 Go | `var/lib` 5,5 Go · `var/log` 1,3 Go (journal 586 Mo) |
| `/root` | 2,5 Go | resté après nettoyage ? à re-vérifier (avant : `.npm` 1,7 Go + `.cache` 675 Mo purgés) |
| `/swapfile` | 4,1 Go | non récupérable |

> À noter : `/usr/local/lib/ollama` (4,3 Go, CUDA) est **distinct** de l'install actif `/var/www/ollama` (2,4 Go) — le service utilise bien ce dernier (processus pid, `ExecStart`, `override.conf` sans `LD_LIBRARY_PATH`).

## Automations en place en fin de session

| Fréquence | Tâche |
|---|---|
| dim. 04:00 UTC | `cron-hebdo-purge-worktrees.sh` — purge des worktrees de sessions closes (5 garde-fous, alerte si commits hors branche) |
| dim. 04:30 UTC | `chrome-data-clean.sh` — purge des profils Chromium de +7 j (garde actifs + profil récent) |
| quotid. 03:15 UTC | `vps-disk-top.sh` (profondeur 1) ; dimanche profondeur 2 |
| 03/11 07:00 UTC | one-shot contrôle des 3 crons OpenCode (auto-destruit) |
| 08/11 07:00 UTC | one-shot contrôle de la purge de `swift-engine` (auto-destruit) |

## Leçons

- **Les droits d'accès faussent tout `du`** : un audit disque en utilisateur non-root est systématiquement sous-estimé. Vérifier `du` **et** `df` avant de conclure à une perte.
- **`ps -eo cmd` tronque en tty** et une classe de caractères sans `.` (`[a-zA-Z0-9/_-]`) casse la détection de `--user-data-dir=...` → motif `[^ ]*` + `ps -ww`.
- **`systemd-tmpfiles-clean` est inactif** et `D /tmp 1777 root root -` ne précise aucun âge → **`/tmp` n'est jamais purgé automatiquement** sur cette machine.
- **Garde-fou efficace** : une purge qui ne détecte pas l'état actif s'arrête sans rien supprimer (`set -e` + test vide) — s'est déclenché à tort puis corrigé, sans aucun dégât.
- **Une commande root = une commande collée** : pas de secret root dans le coffre, pas d'extension de sudoers (choix assumé : zéro modification des droits).
