feat(veille): extension du suivi versions au VPS Contabo et mise a jour DSH/FileBrowser
This commit is contained in:
@@ -0,0 +1,85 @@
|
|||||||
|
# DeepSeek Harness (DSH) VPS & FileBrowser — Guide d'Exploitation et MAJ
|
||||||
|
|
||||||
|
Ce document décrit la structure, la configuration et la procédure de mise à jour de la stack **DeepSeek Harness (`dsh-vps`)** et de son compagnon **FileBrowser (`dsh-vps-filebrowser`)** hébergés sur le VPS Contabo (`100.94.90.119`).
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 1. Architecture et Composants
|
||||||
|
|
||||||
|
```
|
||||||
|
/home/dsh-agent/dsh-vps/
|
||||||
|
├── Dockerfile # node:20-bookworm-slim + @deepseek-ai/dsh pinné + inkstone + patch 0.0.0.0
|
||||||
|
├── docker-compose.yml # Services: dsh-proxy, dsh-vps, dsh-filebrowser
|
||||||
|
├── entrypoint.sh # Script de démarrage dsh-web-app
|
||||||
|
├── nginx.conf # Proxy inverse TLS + Basic Auth (ports 8900 et 8901)
|
||||||
|
├── auth/ # .htpasswd, credentials.txt
|
||||||
|
├── certs/ # Certificats auto-signés TLS
|
||||||
|
└── backups/ # Sauvegardes dsh_vps_home
|
||||||
|
```
|
||||||
|
|
||||||
|
### Services et Ports
|
||||||
|
| Service | Conteneur | Port Interne | Port Public / Tailscale | Auth | Description |
|
||||||
|
|---|---|---|---|---|---|
|
||||||
|
| `dsh-proxy` | `dsh-vps-proxy` | 8900 / 8901 | `100.94.90.119:8900` / `8901` | Basic Auth | Proxy TLS Nginx unifié |
|
||||||
|
| `dsh-vps` | `dsh-vps` | 3080 | Réseau Docker `dsh_vps_net` | Proxy 8900 | Instance DSH Web UI & Agent |
|
||||||
|
| `dsh-filebrowser` | `dsh-vps-filebrowser` | 8080 | Réseau Docker `dsh_vps_net` | Proxy 8901 | Explorateur de fichiers workspace |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 2. Points d'Attention & Pièges Techniques
|
||||||
|
|
||||||
|
1. **Version DSH dans Dockerfile** :
|
||||||
|
- La version est explicitement fixée dans le `Dockerfile` à la ligne `RUN npm install -g @deepseek-ai/dsh@<version> @banlan/inkstone`.
|
||||||
|
- Ne jamais utiliser `@latest` sans vérifier les breaking changes.
|
||||||
|
|
||||||
|
2. **Patch de binding `0.0.0.0` dans `startup.js`** :
|
||||||
|
- Par défaut, `@deepseek-ai/dsh-web-app` interdit l'écoute sur `0.0.0.0` (erreur de sécurité native).
|
||||||
|
- Dans le conteneur, l'écoute sur `0.0.0.0` est indispensable pour que le proxy Nginx (`dsh-vps-proxy`) puisse lui transférer les requêtes.
|
||||||
|
- Le `Dockerfile` applique un patch obligatoire :
|
||||||
|
```dockerfile
|
||||||
|
RUN find /usr/local/lib/node_modules -name "startup.js" -path "*/@deepseek-ai/dsh-web-app/*" -exec sed -i 's/if (options.host === "0.0.0.0")/if (false \&\& options.host === "0.0.0.0")/' {} +
|
||||||
|
```
|
||||||
|
- **Vérification post-build impérative** :
|
||||||
|
```bash
|
||||||
|
docker exec dsh-vps sh -c 'grep -n "options.host" $(find /usr/local/lib/node_modules -name startup.js -path "*/@deepseek-ai/dsh-web-app/*")'
|
||||||
|
```
|
||||||
|
|
||||||
|
3. **FileBrowser Entrypoint (`v2.63.23+`)** :
|
||||||
|
- Depuis les versions récentes de l'image `filebrowser/filebrowser`, le binaire est localisé dans `/bin/filebrowser` (et non `/filebrowser`).
|
||||||
|
- L'entrypoint officiel utilise `tini` et `/init.sh` qui tente d'écrire dans `/config` appartenant à `root`.
|
||||||
|
- L'exécution avec `user: "1001:1001"` requiert de surcharger l'entrypoint :
|
||||||
|
```yaml
|
||||||
|
entrypoint: ["/bin/filebrowser"]
|
||||||
|
command: ["--noauth", "-a", "0.0.0.0", "-p", "8080", "-r", "/srv", "-d", "/srv/.filebrowser.db"]
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 3. Procédure de Mise à Jour DSH
|
||||||
|
|
||||||
|
1. **Sauvegarde préalable de `dsh_vps_home`** :
|
||||||
|
```bash
|
||||||
|
ssh -i ~/.ssh/vps_dsh_agent dsh-agent@100.94.90.119 \
|
||||||
|
"docker run --rm -v dsh_vps_home:/source:ro -v /home/dsh-agent/dsh-vps/backups:/backup alpine \
|
||||||
|
tar -czf /backup/dsh_vps_home-$(date +%Y%m%d-%H%M%S).tar.gz -C /source ."
|
||||||
|
```
|
||||||
|
|
||||||
|
2. **Mise à jour du Dockerfile** :
|
||||||
|
Modifier le tag de version dans `/home/dsh-agent/dsh-vps/Dockerfile`.
|
||||||
|
|
||||||
|
3. **Rebuild sans cache** :
|
||||||
|
```bash
|
||||||
|
cd /home/dsh-agent/dsh-vps && docker compose build --no-cache dsh-vps
|
||||||
|
```
|
||||||
|
|
||||||
|
4. **Recréation du conteneur** :
|
||||||
|
```bash
|
||||||
|
docker compose up -d --force-recreate dsh-vps
|
||||||
|
```
|
||||||
|
|
||||||
|
5. **Contrôles de conformité** :
|
||||||
|
- Version binaire : `docker exec dsh-vps dsh --version`
|
||||||
|
- Patch actif : `docker exec dsh-vps sh -c 'grep -n "options.host" $(find /usr/local/lib/node_modules -name startup.js -path "*/@deepseek-ai/dsh-web-app/*")'`
|
||||||
|
- Écoute interne : `docker exec dsh-vps curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:3080`
|
||||||
|
- Proxy HTTPS : `curl -sk -u "dsh-admin:..." https://100.94.90.119:8900`
|
||||||
|
- Vérification Bifrost : `docker exec dsh-vps curl -s -H "Authorization: Bearer sk-bf-..." http://100.86.197.88:3086/v1/models`
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
# Veille Versions Stack NAS & Référentiel Baserow
|
# Veille Versions Stack NAS & VPS — Référentiel Baserow
|
||||||
|
|
||||||
Ce document décrit le fonctionnement du dispositif de suivi et de veille automatisée des versions des conteneurs du NAS Synology.
|
Ce document décrit le fonctionnement du dispositif de suivi et de veille automatisée des versions des conteneurs du NAS Synology et du VPS Contabo.
|
||||||
|
|
||||||
> **Doctrine stricte** : Ce workflow ne fait **que détecter et notifier**. Aucune mise à jour n'est exécutée automatiquement. Toute opération de mise à jour fait l'objet d'un brief de cadrage, d'une exécution contrôlée avec sauvegardes et d'une validation par commandes réelles.
|
> **Doctrine stricte** : Ce workflow ne fait **que détecter et notifier**. Aucune mise à jour n'est exécutée automatiquement. Toute opération de mise à jour fait l'objet d'un brief de cadrage, d'une exécution contrôlée avec sauvegardes et d'une validation par commandes réelles.
|
||||||
|
|
||||||
@@ -11,10 +11,11 @@ Ce document décrit le fonctionnement du dispositif de suivi et de veille automa
|
|||||||
```mermaid
|
```mermaid
|
||||||
graph TD
|
graph TD
|
||||||
Trigger["Schedule Trigger (Lundi 08h00 Africa/Tunis)"] --> ReadBR["Lire Table Baserow (Table 1097 / Infra Stack)"]
|
Trigger["Schedule Trigger (Lundi 08h00 Africa/Tunis)"] --> ReadBR["Lire Table Baserow (Table 1097 / Infra Stack)"]
|
||||||
ReadBR --> SSHCheck["SSH Restreint NAS (n8n-versions-ro)"]
|
ReadBR --> SSHNAS["SSH Restreint NAS (n8n-versions-ro @ 192.168.100.33:22222)"]
|
||||||
SSHCheck --> MapItems["Préparer Mapping & Éléments"]
|
SSHNAS --> SSHVPS["SSH Restreint VPS (n8n-versions-ro @ tailscale-nyora-bridge:22223)"]
|
||||||
MapItems --> DHub["API Docker Hub (Tags stables)"]
|
SSHVPS --> MapItems["Préparer Mapping & Éléments (Fusion NAS & VPS)"]
|
||||||
DHub --> Analyze["Analyser Écarts & Versions"]
|
MapItems --> Registries["API Registres (Docker Hub & npm registry)"]
|
||||||
|
Registries --> Analyze["Analyser Écarts & Versions (Boucle 11 items)"]
|
||||||
Analyze --> UpdateBR["Mettre à jour Baserow (PATCH Table 1097)"]
|
Analyze --> UpdateBR["Mettre à jour Baserow (PATCH Table 1097)"]
|
||||||
UpdateBR --> Filter["Filtrer Alertes (Si nouvel écart détecté)"]
|
UpdateBR --> Filter["Filtrer Alertes (Si nouvel écart détecté)"]
|
||||||
Filter -->|Nouvel écart| Telegram["Notification Telegram (ND_Telegram)"]
|
Filter -->|Nouvel écart| Telegram["Notification Telegram (ND_Telegram)"]
|
||||||
@@ -26,16 +27,17 @@ graph TD
|
|||||||
## 2. Composants Techniques
|
## 2. Composants Techniques
|
||||||
|
|
||||||
### A. Référentiel Baserow (`infra_versions`)
|
### A. Référentiel Baserow (`infra_versions`)
|
||||||
- **Workspace** : `187 (Perso)` *(déplacé depuis le 148 le 21/08/2026)*
|
- **Workspace** : `187 (Perso)`
|
||||||
- **Database** : `Infra Stack` (ID `317`)
|
- **Database** : `Infra Stack` (ID `317`)
|
||||||
- **Table** : `infra_versions` (ID `1097`)
|
- **Table** : `infra_versions` (ID `1097`)
|
||||||
- **URL** : `https://baserow.bolbol.tn/database/317/table/1097`
|
- **URL** : `https://baserow.bolbol.tn/database/317/table/1097`
|
||||||
- **Token API dédié** : `n8n-infra-versions` (Token ID `32`, scopé Workspace 187 Perso)
|
- **Token API dédié** : `n8n-infra-versions` (Token ID `32`, scopé Workspace 187 Perso)
|
||||||
- **Champs suivis** :
|
- **Champs suivis** :
|
||||||
- `conteneur` (Texte, clé primaire) : Nom du conteneur
|
- `conteneur` (Texte, clé primaire) : Nom du conteneur
|
||||||
- `image_repo` (Texte) : Repository Docker Hub (ex: `n8nio/n8n`, `maximhq/bifrost`)
|
- `image_repo` (Texte) : Repository Docker Hub ou nom de package npm (ex: `@deepseek-ai/dsh`)
|
||||||
- `methode_verif` (Single select) : `image_tag` ou `exec_version`
|
- `methode_verif` (Single select) : `image_tag`, `exec_version` ou `npm_registry`
|
||||||
- `version_installee` (Texte) : Version réelle active sur le NAS
|
- `emplacement` (Single select) : `NAS` ou `VPS`
|
||||||
|
- `version_installee` (Texte) : Version réelle active sur l'hôte
|
||||||
- `derniere_version_disponible` (Texte) : Dernière version stable publiée
|
- `derniere_version_disponible` (Texte) : Dernière version stable publiée
|
||||||
- `ecart` (Texte) : Statut de l'écart (`0`, `Installée: ... ➔ Dispo: ...`)
|
- `ecart` (Texte) : Statut de l'écart (`0`, `Installée: ... ➔ Dispo: ...`)
|
||||||
- `criticite` (Single select) : `Critique`, `Important`, `Mineur`
|
- `criticite` (Single select) : `Critique`, `Important`, `Mineur`
|
||||||
@@ -48,20 +50,34 @@ graph TD
|
|||||||
---
|
---
|
||||||
|
|
||||||
### B. Accès SSH Restreint NAS (`n8n-versions-ro`)
|
### B. Accès SSH Restreint NAS (`n8n-versions-ro`)
|
||||||
Pour respecter le principe de moindre privilège et interdire tout shell interactif ou injection de commande :
|
|
||||||
- **Compte DSM** : `n8n-versions-ro` (UID `1041`, membre du groupe `docker` `65538`).
|
- **Compte DSM** : `n8n-versions-ro` (UID `1041`, membre du groupe `docker` `65538`).
|
||||||
- **Clé SSH** : Clé Ed25519 dédiée (`/volume1/docker/scripts/id_ed25519_n8n_versions`).
|
- **Clé SSH** : Clé Ed25519 dédiée (`/volume1/docker/scripts/id_ed25519_n8n_versions`).
|
||||||
- **Restriction `authorized_keys`** :
|
- **Restriction `authorized_keys`** :
|
||||||
```text
|
```text
|
||||||
command="/volume1/docker/scripts/versions-check.sh",no-port-forwarding,no-X11-forwarding,no-agent-forwarding,no-pty ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIIn3e1VvE3Z/q1W5o6Q+30w7U57u3aK8JqC8Z57Z8z/c n8n-versions-ro
|
command="/volume1/docker/scripts/versions-check.sh",no-port-forwarding,no-X11-forwarding,no-agent-forwarding,no-pty ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIKDwuAwKnKiKskL+Vr4WYhn/uySlk5jyOHPh1R/P/9K0 n8n-versions-ro
|
||||||
```
|
```
|
||||||
- **Script exécutable** : `/volume1/docker/scripts/versions-check.sh`
|
- **Script exécutable** : `/volume1/docker/scripts/versions-check.sh` (mode 755)
|
||||||
- Filtre `$SSH_ORIGINAL_COMMAND` contre une whitelist stricte des 9 conteneurs.
|
|
||||||
- Toute commande arbitraire (`rm -rf /`, `sh`, etc.) est rejetée avec un code d'erreur `1`.
|
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
### C. Workflow n8n (`veille-versions-stack`)
|
### C. Accès SSH Restreint VPS (`n8n-versions-ro`)
|
||||||
|
- **Compte VPS** : `n8n-versions-ro` (UID `1002`, GID `1002`, membre du groupe `docker`).
|
||||||
|
- **Clé SSH dédiée** : `/volume1/docker/scripts/id_ed25519_n8n_versions_vps`
|
||||||
|
- **Fingerprint réel** : `256 SHA256:fTDnqFouAhwApAsnQjuLoGjvZCNoHAwYC4gpGqRvygY n8n-versions-ro@vps (ED25519)`
|
||||||
|
- **Clé publique** : `ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFdwCzUBTsBKNSRxhjwU82o9T2VbQn4HKbp+3mFyIQTq n8n-versions-ro@vps`
|
||||||
|
- **Restriction `authorized_keys` VPS** (`/home/n8n-versions-ro/.ssh/authorized_keys`) :
|
||||||
|
```text
|
||||||
|
command="/home/n8n-versions-ro/versions-check-vps.sh",no-port-forwarding,no-X11-forwarding,no-agent-forwarding,no-pty ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFdwCzUBTsBKNSRxhjwU82o9T2VbQn4HKbp+3mFyIQTq n8n-versions-ro@vps
|
||||||
|
```
|
||||||
|
- **Script exécutable VPS** : `/home/n8n-versions-ro/versions-check-vps.sh` (mode 755)
|
||||||
|
- **Relais Réseau n8n ➔ VPS** :
|
||||||
|
- OpenSSH standard écoute sur le port `22222` sur l'interface `tailscale0` du VPS (`100.94.90.119:22222`).
|
||||||
|
- Sur le NAS, le conteneur `tailscale-vps-ssh-relay` (partageant l'espace réseau de `tailscale-nyora-bridge`) relaie le port `22223` vers `100.94.90.119:22222`.
|
||||||
|
- Le conteneur `n8n` interroge directement `tailscale-nyora-bridge:22223`.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
### D. Workflow n8n (`veille-versions-stack`)
|
||||||
- **ID Workflow** : `zUWN5K4Q1A2JKFIS`
|
- **ID Workflow** : `zUWN5K4Q1A2JKFIS`
|
||||||
- **Déclenchement** : Hebdomadaire (Lundi à 08h00 Africa/Tunis) + Webhook de test manuel `/webhook/test-veille-versions`.
|
- **Déclenchement** : Hebdomadaire (Lundi à 08h00 Africa/Tunis) + Webhook de test manuel `/webhook/test-veille-versions`.
|
||||||
- **Canal Telegram** : Credential `ND_Telegram` (`OyOHh6jAzCDsiBux`), Chat ID `2084513684`.
|
- **Canal Telegram** : Credential `ND_Telegram` (`OyOHh6jAzCDsiBux`), Chat ID `2084513684`.
|
||||||
@@ -69,32 +85,38 @@ Pour respecter le principe de moindre privilège et interdire tout shell interac
|
|||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
## 3. Table des 9 Conteneurs Suivis
|
## 3. Table des 11 Conteneurs Suivis
|
||||||
|
|
||||||
| Conteneur | Image Repo | Méthode | Criticité | Particularités |
|
| Conteneur | Emplacement | Image Repo / Package | Méthode | Criticité | Particularités |
|
||||||
|---|---|---|---|---|
|
|---|---|---|---|---|---|
|
||||||
| `n8n` | `n8nio/n8n` | `exec_version` | Important | Image custom (docx, exceljs) |
|
| `n8n` | NAS | `n8nio/n8n` | `exec_version` | Important | Image custom (docx, exceljs) |
|
||||||
| `bifrost` | `maximhq/bifrost` | `image_tag` | Critique | Pin image, backup config.db/config.json |
|
| `bifrost` | NAS | `maximhq/bifrost` | `image_tag` | Critique | Pin image, backup config.db/config.json |
|
||||||
| `gitea` | `gitea/gitea` | `image_tag` | Important | Pin rootless, backup natif `gitea dump` |
|
| `gitea` | NAS | `gitea/gitea` | `image_tag` | Important | Pin rootless, backup natif `gitea dump` |
|
||||||
| `portainer` | `portainer/portainer-ce` | `image_tag` | Mineur | Pilote stacks, MAJ en priorité |
|
| `portainer` | NAS | `portainer/portainer-ce` | `image_tag` | Mineur | Pilote stacks, MAJ en priorité |
|
||||||
| `vaultwarden` | `vaultwarden/server` | `image_tag` | Mineur | Pin alpine, backup db.sqlite3 |
|
| `vaultwarden` | NAS | `vaultwarden/server` | `image_tag` | Mineur | Pin alpine, backup db.sqlite3 |
|
||||||
| `baserow` | `baserow/baserow` | `exec_version` | Important | Mode minimal, DNS dynamique Nginx |
|
| `baserow` | NAS | `baserow/baserow` | `exec_version` | Important | Mode minimal, DNS dynamique Nginx |
|
||||||
| `crowdsec` | `crowdsecurity/crowdsec` | `exec_version` | Important | Sécurité IDS/IPS DSM |
|
| `crowdsec` | NAS | `crowdsecurity/crowdsec` | `exec_version` | Important | Sécurité IDS/IPS DSM |
|
||||||
| `tailscale-nyora-bridge` | `tailscale/tailscale` | `image_tag` | Mineur | Bridge HTTP/SOCKS5 |
|
| `tailscale-nyora-bridge` | NAS | `tailscale/tailscale` | `image_tag` | Mineur | Bridge HTTP/SOCKS5 |
|
||||||
| `trilium` | `triliumnext/trilium` | `image_tag` | Mineur | `En pause` (exclu des alertes actives) |
|
| `trilium` | NAS | `triliumnext/trilium` | `image_tag` | Mineur | `En pause` (exclu des alertes actives) |
|
||||||
|
| `dsh-vps` | VPS | `@deepseek-ai/dsh` | `npm_registry` | Important | Build custom, version npm pinnée, patch binding `startup.js` |
|
||||||
|
| `dsh-vps-filebrowser` | VPS | `filebrowser/filebrowser` | `image_tag` | Mineur | Compagnon Web UI, entrypoint `/bin/filebrowser` |
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
## 4. Procédure de Test et Validation
|
## 4. Procédure de Test et Validation
|
||||||
|
|
||||||
1. **Test d'exécution manuelle sans alerte (tout à jour)** :
|
1. **Test d'exécution manuelle globale via webhook** :
|
||||||
```bash
|
```bash
|
||||||
curl -s http://192.168.100.33:5678/webhook/test-veille-versions
|
curl -s http://192.168.100.33:5678/webhook/test-veille-versions -H "Host: n8n.bolbol.tn"
|
||||||
# Réponse attendue : {"no_alert": true, "message": "Aucun nouvel ecart"}
|
# Réponse attendue si tout est à jour : {"no_alert": true, "message": "Aucun nouvel ecart"}
|
||||||
```
|
```
|
||||||
|
|
||||||
2. **Test d'interrogation SSH unitaire** :
|
2. **Test d'interrogation SSH unitaire NAS** :
|
||||||
```bash
|
```bash
|
||||||
ssh -p 22222 -i /volume1/docker/scripts/id_ed25519_n8n_versions -o BatchMode=yes n8n-versions-ro@127.0.0.1 "n8n"
|
ssh -p 22222 -i /volume1/docker/scripts/id_ed25519_n8n_versions -o BatchMode=yes n8n-versions-ro@127.0.0.1 "all"
|
||||||
# Réponse attendue : version exacte (ex: 2.36.5)
|
```
|
||||||
|
|
||||||
|
3. **Test d'interrogation SSH unitaire VPS** (depuis le conteneur `n8n`) :
|
||||||
|
```bash
|
||||||
|
docker exec n8n ssh -p 22223 -i /tmp/id_vps_n8n -o BatchMode=yes n8n-versions-ro@tailscale-nyora-bridge "all"
|
||||||
```
|
```
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user