18 Commits
Author SHA1 Message Date
Djeex b6ffef5a8f Merge pull request 'Add BTRFS snapshots guide, TinyAuth/Pocket ID diagrams, and Backrest restore docs' (#3) from wip into main
Trigger container build / trigger (push) Successful in 6s
Reviewed-on: #3
2026-09-09 14:26:08 +02:00
Djeex 0f9b039e11 Document Backrest restore and fix the Paths field autocomplete claim 2026-09-09 14:23:25 +02:00
Djeex 12242579a0 Turn the Backrest bind mount explanation into plain paragraphs 2026-09-09 14:07:18 +02:00
Djeex 2d1865f0e0 Add /etc and /home bind mounts to Backrest and explain Paths selection 2026-09-09 14:03:23 +02:00
Djeex 7c89513b5b Strip embedded font and metadata from architecture diagram SVGs 2026-09-09 13:59:01 +02:00
Djeex 62d4fe4ec2 Explain and let readers tune the Snapper timeline snapshot frequency 2026-09-09 13:41:47 +02:00
Djeex c90cd781d3 Use Snapper instead of a custom script for BTRFS snapshots 2026-09-09 13:18:59 +02:00
Djeex a59966006b Add a BTRFS snapshots guide and mention it as an advanced install option 2026-09-09 12:58:36 +02:00
Djeex 1a1e4418bb Add network diagrams to TinyAuth and Pocket ID articles 2026-09-09 12:49:36 +02:00
Djeex 154cd0c66b Rename recycled section title to Recyclage 2026-09-07 22:57:17 +02:00
Djeex 66f7b78efd Merge pull request 'Djeex' audit' (#2) from Djeex-audit into main
Trigger container build / trigger (push) Successful in 2s
Reviewed-on: #2
2026-09-07 21:40:59 +02:00
Djeex 28c26dc488 Clean up remaining writing-quality issues from the audit 2026-09-07 21:30:03 +02:00
Djeex 18abf487a7 Rename Stockeex intro page title to avoid duplicate page title (F1) 2026-09-07 21:28:32 +02:00
Djeex 064d8f1576 Normalize formatting conventions across guides (chapter D) 2026-09-07 21:28:08 +02:00
Djeex db30198450 Fix spelling and grammar mistakes across EN and FR content (chapter C) 2026-09-07 21:25:08 +02:00
Djeex de3498fa65 Reconcile EN/FR content drift flagged in the audit (B9-B18) 2026-09-07 21:15:51 +02:00
Djeex f49f1409b9 Fix remaining minor audit findings in Serveex guides (A8-A14) 2026-09-07 21:12:29 +02:00
Djeex 9c4b8a756e Fix content audit findings across Serveex, Nonsense and recycled guides 2026-09-07 20:54:58 +02:00
91 changed files with 1157 additions and 349 deletions
+1
View File
@@ -42,3 +42,4 @@ __pycache__
# Scratch/demo files (not part of the site)
scratch
.screenshot
+1 -1
View File
@@ -102,7 +102,7 @@ Use RAID 5 when you want reliable storage with 3 to 5 disks and minimal space lo
- Total capacity is the sum of all disks minus two (e.g., 4×10TB = 20TB).
- Minimum of 4 disks (6 recommended to minimize space loss).
Use RAID 6 in similar situations as RAID 5, especially with 6 or more disks. More disks mean higher failure risk. RAID 6 offers peace of mind by tolerating two simultaneous failures.
Use RAID 6 in similar situations as RAID 5, especially with 6 or more disks. More disks mean higher failure risk. RAID 6 offers peace of mind by tolerating two simultaneous failures. There's nothing more frustrating than losing a second disk while the array is still rebuilding from replacing the first.
## Software RAID
(coming soon)
+4 -2
View File
@@ -49,7 +49,9 @@ When the target is a place on the disk, you write it as a path, and there are a
| `/var/log` | an **absolute** path, same result from anywhere |
| `logs/today` | a **relative** path, understood from where you currently stand |
Which folder holds what is a subject of its own, covered in [folders and partitions](/general/linux/filesystem).
::note{to="/general/linux/filesystem"}
Which folder holds what is a subject of its own, covered in **folders and partitions**.
::
The prompt itself tells you where you are: in `username@serveex:~/docker$`, you're logged in as `username` on the machine named `serveex`, inside the `docker` folder of your home. That final `$` means a normal user. If it ever shows `#`, you're root and every typo counts double.
@@ -241,7 +243,7 @@ The ones worth keeping at hand, and where their names come from.
| `chmod` | change mode | Changes a file's permissions |
| `chown` | change owner | Changes who owns a file |
| `sudo` | substitute user do | Runs one command as administrator |
| `apt` | Advanced Packaging Tool | Installs, updates and removes packages |
| `apt` | Advanced Package Tool | Installs, updates and removes packages |
| `systemctl` | control systemd | Starts, stops and enables services |
| `ssh` | secure shell | Opens a session on a remote machine |
| `scp` | secure copy | Copies files over SSH |
@@ -203,7 +203,7 @@ Being outside `apt` also means it won't be updated by `apt full-upgrade`. Repeat
## `ufw`, a firewall you can actually read
Debian's firewall (`iptables`/`nftables` under the hood) is powerful and unreadable directly. `ufw`, *uncomplicated firewall*, is a thin layer on top that turns it into short, plain-English rules, block everything by default and open only what you actually expose.
Debian's firewall (`iptables`/`nftables` under the hood) is powerful and unreadable directly. `ufw`, *uncomplicated firewall*, is a thin layer on top that turns it into short, plain-English rules: block everything by default and open only what you actually expose.
::steps{level="4"}
#### Install it
+10
View File
@@ -296,6 +296,8 @@ ui:
icon: text-[#175DDC]
---
Install and deploy Vaultwarden
::
::
::
@@ -313,6 +315,14 @@ Install and deploy Authentik
::card{icon="i-noto-crystal-ball" title="Multi-host Docker manager" to="/serveex/advanced/arcane"}
Install and deploy Arcane
::
::card{icon="i-lucide-database-backup" title="3-2-1 Backups" to="/serveex/advanced/backrest"}
Install and deploy Backrest
::
::card{icon="i-lucide-rotate-ccw" title="Instant Rollback" to="/serveex/advanced/btrfs-snapshots"}
Set up BTRFS snapshots
::
::
## Coming Soon
@@ -89,6 +89,10 @@ Confirm the timezone guessed from your country.
*Guided, use entire disk* on the system drive, then *All files in one partition*, which gives you one big `/` plus a swap partition. Separate `/home` or `/var` partitions buy you very little here and mostly guarantee that one fills up while the others sit half empty. Pick LVM only if you already know you want snapshots or to grow volumes later. Your data disks are not touched at this stage, you'll mount them afterwards.
::warning{to="/serveex/advanced/btrfs-snapshots"}
__For advanced users:__ this is the moment to decide, not later. Picking *Manual* here instead of *Guided* lets you format the root partition as Btrfs instead of ext4, unlocking instant, near-free snapshots you can roll back to before a risky update or config change. Once this step is done and Debian is installed on ext4, switching to Btrfs isn't possible without wiping the disk and starting over. See **BTRFS snapshots** if you want to set it up, it's not a replacement for real backups either, a snapshot lives on the same disk.
::
Finish with *Finish partitioning and write changes to disk*, then confirm with *Yes*: this is the point of no return for that disk.
![Debian installer partitioning scheme, all files in one partition](/img/serveex/install/debian-install-partition.png)
@@ -216,7 +220,7 @@ The door is now closed for every other machine too, including the next one you'l
A machine that runs 24/7 for two hours of actual use burns power, spins fans and wears drives for nothing. Wake on LAN lets you shut it down properly when you're done and bring it back in a few seconds without walking to it: the network card stays powered in standby, listening for one specific broadcast (the *magic packet*) carrying the server's MAC address, and switches the machine on when it sees it. Handy for a backup target you only need at night, or a media server nobody watches during the day.
Two conditions before you start: the machine has to be wired to ethernet, WiFi cards almost never support this, and the packet has to be sent from the same local network, since a broadcast doesn't cross a router. The BIOS side was covered in [BIOS setup](#bios-setup), here is the Debian side.
Two conditions before you start: the machine has to be wired to ethernet, WiFi cards almost never support this, and the packet has to be sent from the same local network, since a broadcast doesn't cross a router, unless you use a dedicated app and port-forwarding rules on your router. The BIOS side was covered in [BIOS setup](#bios-setup), here is the Debian side.
::steps{level="4"}
#### Find the interface and its MAC address
+1 -1
View File
@@ -13,7 +13,7 @@ description: Set up SWAG as a reverse proxy with automatic SSL, expose your serv
SWAG is only useful for exposing your services to the internet, i.e. accessing them via a public URL like `https://service.mydomain.com`. If you dont want to expose your services and prefer to always use a VPN to connect remotely, you can go **here instead**.
::
Below is an example exposing Dockge. We will install SWAG along with the dbip mod for geolocation-based blocking, and the dashboard mod for managing swag, fail2ban, and geolocation.
Below is an example exposing Dockge. We will install SWAG along with the dbip mod for geolocation-based blocking, the dashboard mod for managing swag, fail2ban, and geolocation, and the auto-reload mod, which automatically reloads nginx whenever a config file changes, without having to restart the container.
**Reverse proxy principle and its application in our case:**
@@ -15,6 +15,8 @@ It supports a simple local username/password login out of the box, which is what
- [TinyAuth documentation](https://tinyauth.app/docs/getting-started)
- [TinyAuth on GitHub](https://github.com/tinyauthapp/tinyauth)
![Diagram of TinyAuth sitting behind SWAG as the forward-auth proxy in front of local services](/img/serveex/tinyauth.svg)
## Installation
::file-tree
@@ -15,6 +15,8 @@ This makes it a good fit if you just need a simple, fast SSO backend, for exampl
- [Pocket ID documentation](https://pocket-id.org/docs)
- [Pocket ID on GitHub](https://github.com/pocket-id/pocket-id)
![Diagram of Pocket ID acting as the native OIDC identity provider behind SWAG](/img/serveex/pocket-id-native.svg)
## Installation
::file-tree
@@ -230,6 +232,8 @@ Save, then copy the generated __Client ID__ and __Client Secret__. You'll need t
## Connecting Pocket ID to TinyAuth
[TinyAuth](/serveex/security/tinyauth) can delegate its login to Pocket ID instead of (or alongside) its local username/password, so anyone visiting a protected app authenticates with a passkey and gets forwarded through.
![Diagram of TinyAuth delegating login to Pocket ID via OIDC](/img/serveex/pocket-id.svg)
::steps{level="3"}
### Register TinyAuth as an OIDC client
@@ -39,6 +39,8 @@ services:
image: amir20/dozzle:latest
ports:
- 9135:8080
volumes:
- /docker/dozzle/data:/data
env_file:
- .env
environment:
@@ -87,7 +87,7 @@ PORT=3225 # port to access the web UI
✨ **Tip:** You can configure additional environment variables by referring to the **official documentation**.
::
Deploy the container and go to `http://yourserverip:3225`. Log in with the account `admin@exemple.com` and the password `password`. Dont forget to change your ID and password once logged in!
Deploy the container and go to `http://yourserverip:3225`. Log in with the account `admin@example.com` and the password `password`. Dont forget to change your ID and password once logged in!
### Done!
::
+8 -15
View File
@@ -8,7 +8,7 @@ description: Install UpSnap to remotely wake up machines on your local network v
[UpSnap](https://github.com/seriousm4x/UpSnap) is a container that allows you to remotely power on, shut down, or put your machines to sleep. It mainly uses Wake-On-Lan (WoL) over the network and offers advanced features.
![Beszel](/img/serveex/upsnap.webp)
![UpSnap](/img/serveex/upsnap.webp)
## Installation
@@ -101,9 +101,9 @@ We assume you've created a subdomain in your [DNS zone](/general/networking/dns)
::
::steps{level="3"}
### Add UpSnap's network to SWAG
### Make the host reachable from SWAG
Go to Dockge, and edit the SWAG compose by adding the UpSnap network:
UpSnap runs with `network_mode: host` (needed for Wake-on-LAN broadcasts and network scanning to work reliably), so it never joins a Docker network SWAG could attach to like other stacks. Instead, give SWAG a way to reach the host itself:
```yaml [compose.yaml]
---
@@ -111,22 +111,15 @@ services:
swag:
container_name: # ...
# ...
networks: # Connects the container to the custom network
# ...
- upsnap # Network name declared in the stack
networks: # Defines the custom network
# ...
upsnap: # Network name declared in the stack
name: upsnap_default # Actual name of the external network
external: true # Indicates it's an external network
extra_hosts:
- "host.docker.internal:host-gateway" # resolves to the Docker host's own IP
```
Restart the stack by clicking "deploy" and wait for SWAG to be fully operational.
::note
Here we assume the network name for upsnap is `upsnap_default`. You can check the connection in the SWAG dashboard at `http://yourserverip:81`.
`host-gateway` is a special value Docker resolves to the host machine's IP automatically, so this works regardless of your server's actual address.
::
### Create the subdomain.conf file
@@ -184,7 +177,7 @@ server {
include /config/nginx/proxy.conf;
include /config/nginx/resolver.conf;
set $upstream_app upsnap;
set $upstream_app host.docker.internal;
set $upstream_port 8095;
set $upstream_proto http;
proxy_pass $upstream_proto://$upstream_app:$upstream_port;
@@ -262,7 +255,7 @@ server {
include /config/nginx/proxy.conf;
include /config/nginx/resolver.conf;
set $upstream_app upsnap;
set $upstream_app host.docker.internal;
set $upstream_port 8095;
set $upstream_proto http;
proxy_pass $upstream_proto://$upstream_app:$upstream_port;
+1 -1
View File
@@ -44,7 +44,7 @@ tree:
Create the `movies`, `tvseries`, and `library` folders in `/media`:
```bash [Terminal]
mkdir -p /media/movies /media/library /media/tvseries
mkdir -p /media/movies /media/tvseries /media/library
```
### Deploy the stack
@@ -47,7 +47,7 @@ tree:
If not already done, create the `downloads` folder under `/media`:
```bash [Terminal]
mkdir -P /media/downloads
mkdir -p /media/downloads
```
### Deploy the stack
@@ -88,7 +88,7 @@ services:
devices:
- /dev/net/tun:/dev/net/tun
ports:
- ${UI_PORT}:5695 # Port de la web-ui
- ${UI_PORT}:${UI_PORT} # Port de la web-ui
- 8000:8000 # Port de controle de Gluetun
cap_add:
- NET_ADMIN
@@ -321,7 +321,7 @@ server {
include /config/nginx/proxy.conf;
include /config/nginx/resolver.conf;
set $upstream_app gluetun;
set $upstream_port 5555;
set $upstream_port 5695;
set $upstream_proto http;
proxy_pass $upstream_proto://$upstream_app:$upstream_port;
@@ -399,7 +399,7 @@ server {
include /config/nginx/proxy.conf;
include /config/nginx/resolver.conf;
set $upstream_app gluetun;
set $upstream_port 5555;
set $upstream_port 5695;
set $upstream_proto http;
proxy_pass $upstream_proto://$upstream_app:$upstream_port;
+3 -3
View File
@@ -133,8 +133,8 @@ services:
container_name: bazarr
restart: unless-stopped
environment:
- PUID=1000
- PGID=1000
- PUID=${PUID}
- PGID=${PGID}
- TZ=Europe/Paris
volumes:
- /srv/docker/bazarr/config:/config
@@ -394,7 +394,7 @@ Seerr has no built-in two-factor authentication. Only expose it if you're using
::note
We assume you have the subdomain `films.mydomain.com` with a `CNAME` pointing to `films.fr` in your [DNS zone](/general/networking/dns). And that [unless youre using Cloudflare Zero Trust](/serveex/security/cloudflare), port `443` on your router is forwarded to port `443` on your server via [NAT rules](/general/networking/nat).
We assume you have the subdomain `films.mydomain.com` with a `CNAME` pointing to `mydomain.com` in your [DNS zone](/general/networking/dns). And that [unless youre using Cloudflare Zero Trust](/serveex/security/cloudflare), port `443` on your router is forwarded to port `443` on your server via [NAT rules](/general/networking/nat).
::
::steps{level="3"}
@@ -89,7 +89,6 @@ Mount every folder you listed under `sources` in `config.yaml` at the same path
filebrowser-quantum:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
```
::
@@ -53,13 +53,11 @@ From here on, we assume the network name for SWAG is `swag_default`.
pingvin-share:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
clamav:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
```
::
@@ -63,7 +63,6 @@ services:
code-server:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
```
::
@@ -144,7 +143,7 @@ services:
networks: # Defines the custom network
# ...
code-server: # Name of the network defined in the stack
name: code-serveur # Actual name of the external network
name: code-server_default # Actual name of the external network
external: true # Indicates its an external network
```
@@ -36,7 +36,6 @@ services:
it-tools:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
```
::
+1 -1
View File
@@ -247,7 +247,7 @@ Press :kbd{value="Ctrl+O"}, then :kbd{value="Enter"} to save, and :kbd{value="Ct
### Done!
::
And there you go! Vaultwarden is now exposed! Visit `https://vault.yourdomain.com/admin` to access the admin panel and paste the password you specified when generatique the `ADMIN_TOKEN`. For more information, see the [Bitwarden documentation](https://bitwarden.com/help/).
And there you go! Vaultwarden is now exposed! Visit `https://vault.yourdomain.com/admin` to access the admin panel and paste the password you specified when generating the `ADMIN_TOKEN`. For more information, see the [Bitwarden documentation](https://bitwarden.com/help/).
Don't forget to install Bitwarden browser extensions (they work with Vaultwarden) for [Chrome](https://chromewebstore.google.com/detail/gestionnaire-de-mots-de-p/nngceckbapebfimnlniiiahkandclblb) and [Firefox](https://addons.mozilla.org/fr/firefox/addon/bitwarden-password-manager/), as well as [iOS](https://apps.apple.com/fr/app/bitwarden/id1137397744) and [Android](https://play.google.com/store/apps/details?id=com.x8bit.bitwarden&hl=fr) apps to sync your passwords.
@@ -459,7 +459,6 @@ authentik_host_insecure: false
container_image:
docker_network: null
docker_map_ports: true
docker_labels: null
```
Save with :kbd{value="Ctrl+O"}, then :kbd{value="Enter"}, and exit with :kbd{value="Ctrl+X"}.
@@ -475,7 +474,7 @@ On your remote machine, use [Dockge](/serveex/core/docker/#install-dockge-to-man
If you havent installed [Dockge](/serveex/core/docker/#install-dockge-to-manage-and-deploy-containers), create a folder `/srv/docker/authentik-outpost`, or directly via command line:
```bash [Terminal]
sudo mkdir -P /srv/docker/authentik-outpost
sudo mkdir -p /srv/docker/authentik-outpost
```
::tip{icon="" to="/serveex/files/file-browser-quantum"}
@@ -492,7 +491,7 @@ Via command line:
```bash [Terminal]
sudo nano /srv/docker/authentik-outpost/compose.yaml
```
Paste the following configuration, updating the version in `{AUTHENTIK_TAG:proxy:2024.2.3}`{lang=properties} to match your Authentik server version.
Paste the following configuration, updating the version in `ghcr.io/goauthentik/proxy:2026.2`{lang=properties} to match your Authentik server version.
```yaml [compose.yaml]
---
@@ -500,7 +499,7 @@ version: "3.5"
services:
authentik_proxy:
container_name: authentik-outpost
image: ghcr.io/goauthentik/proxy:2024.2.3
image: ghcr.io/goauthentik/proxy:2026.2
# Optionally specify which networks the container should be
# might be needed to reach the core authentik server
restart: unless-stopped
@@ -0,0 +1,253 @@
---
title: Backrest
description: Install Backrest, a friendly web UI for restic, and back up your server properly following the 3-2-1 rule, to a local disk, another server, S3, or Backblaze B2.
---
:ellipsis{left=0px width=40rem top=10rem blur=140px zIndex=60}
Let's be honest for a second: "backup strategy" for most homelabbers means copying a few folders to a USB stick that one time in 2019, then hoping for the best. [Backrest](https://github.com/garethgeorge/backrest) is here to fix that, without making you learn a scary command-line tool first.
Under the hood, Backrest is a clean web interface on top of [restic](https://restic.net/), a battle-tested, open-source backup engine. Restic does the actual work (encrypting, deduplicating, and shipping your data wherever you tell it to); Backrest gives you buttons and forms instead of a wall of flags to memorize.
![Backrest's dashboard, showing several repositories and their recent backup activity](/img/serveex/backrest-dashboard.png)
## The 3-2-1 rule, or why one backup is not a backup
Before installing anything, let's talk about the rule that actually matters here, because a backup done wrong gives you false confidence, which is worse than no backup at all.
The **3-2-1 rule** says:
- **3** copies of your data: the original, plus at least two backups.
- **2** different types of storage: not two copies sitting on the same disk, or on two disks in the same machine.
- **1** copy offsite: physically somewhere else, not in the same room, house, or building as the original.
Each number closes a specific failure scenario:
- Only **1** backup? A single mistake (a bad `rm -rf`, a botched restore, a corrupted file silently copied over the good one) can take out your only safety net at the same time as the original.
- Backups on the **same type of storage** (say, a second internal drive in the same server)? A power surge, a firmware bug, or a cheap PSU dying can very well take out every disk in the box at once.
- No **offsite** copy? Fire, flood, theft, or "I unplugged the wrong power strip" don't care how many drives you have, if they're all in the same room.
This is also exactly why [RAID is not a backup](/general/storage/raid): RAID keeps a service running when a disk dies, it does nothing against ransomware encrypting every file it can reach, a fat-fingered delete, or your house catching fire. Backrest, pointed at a destination outside your server, is what actually covers those cases.
## What Backrest actually backs up, and where
Two concepts to know before clicking around:
- A **repository** is the destination: an encrypted, deduplicated storage location. This is your "2" and your "1" from the rule above, an external disk, another server, or cloud storage.
- A **plan** is the rule you define: which folders to back up, into which repository, on what schedule, and how many old snapshots to keep around.
You can have several plans backing up to several repositories at once, which is exactly how you'd build a real 3-2-1 setup: one plan to a local repository for quick restores, another plan to an offsite repository for the "my house is on fire" scenario.
## Installation
::file-tree
---
tree:
/:
- srv:
- docker:
- backrest:
- data/
- config/
- cache/
- compose.yaml
---
::
::steps{level="3"}
### Deploy the stack
Open Dockge, click `compose`, name the stack `backrest`, and paste the following:
```yaml [compose.yaml]
---
services:
backrest:
image: garethgeorge/backrest:latest
container_name: backrest
restart: unless-stopped
ports:
- 9898:9898
volumes:
- ./data:/data
- ./config:/config
- ./cache:/cache
# Whatever you want Backrest to be able to back up has to be
# mounted here too: this stack only sees what it's given.
- /srv/docker:/userdata/docker:ro
- /etc:/userdata/etc:ro
- /home:/userdata/home:ro
environment:
- BACKREST_DATA=/data
- BACKREST_CONFIG=/config/config.json
- XDG_CACHE_HOME=/cache
- TZ=Europe/Paris
```
The `/srv/docker`, `/etc` and `/home` lines above cover what's actually worth an off-site backup on a homelab server, per [folders and partitions](/general/linux/filesystem): `/srv/docker` holds every stack's config and data (databases, uploaded files, Vaultwarden's vault, Pocket ID's users, and so on), `/etc` holds your system configuration (the SSH hardening from the [installation guide](/serveex/core/installation#close-the-door-behind-you), your SWAG `.subdomain.conf` files, systemd units), and `/home` holds your own scripts and notes. All three are mounted read-only, a backup tool has no business writing to what it's backing up.
What's usually **not** worth it: a big media library or a torrent download folder sitting on a separate data disk. It's often huge, replaceable, and rarely worth paying for cloud storage or SSH bandwidth to protect.
::tip{icon=""}
✨ __Tip:__ Add the Watchtower label to automate updates
```yaml [compose.yaml]
services:
backrest:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
```
::
Deploy the container, then open `http://yourserverip:9898`. The first visit asks you to set an admin username and password: do it immediately, Backrest has no account by default and the setup screen is wide open until you do.
### Done!
::
## Creating your first repository
![Backrest's Add Restic Repository form, showing a Backblaze B2 repository URI](/img/serveex/backrest.png)
In Backrest, go to **Add Repo**. The form is split into a few sections, here's what each field actually does:
- **Repo Name**: whatever helps you recognize it later, `usb-key` or `offsite-vps` for instance. You can't rename it afterwards, so pick something you won't regret.
- **Auto Unlock**: leave this off unless you understand what it does. Restic locks a repository while it's working on it, so a second process doesn't corrupt things by writing at the same time. Auto Unlock removes that lock automatically on startup, which is convenient if Backrest crashed mid-backup and left a stale lock behind, but genuinely unsafe if two machines ever write to the same repository at once. For the single-server homelab setup this article covers, it's a minor convenience; leave it off if in doubt.
- **Shared**: only relevant to Backrest's multihost feature (several of your machines managing the same repo config). Ignore it for a single server.
- **Repository URI**: where the data actually lives. This is the field that changes for every destination below.
- **Password**: the encryption password for this repository, click **Generate** for a strong random one. **Save it somewhere outside this server**, a password manager, a note on your phone, anywhere but a text file sitting next to the backups it protects. Lose it, and every single backup becomes an expensive pile of unreadable noise, no exceptions, not even for the developers of restic.
- **Env Vars**: where you'll paste credentials for destinations that need them (S3 and B2 below). Local disks and SFTP don't need any.
::note
The **Scheduling**, **Hooks**, and **Advanced** tabs of this form configure repository-wide maintenance (pruning old data, verifying integrity, notifications) rather than anything destination-specific. They're covered at the end of this article, once you've got a repository actually working.
::
### Backing up to a local disk or USB key
The simplest possible offsite copy is a drive you physically move somewhere else after each backup, or a second machine's disk reached over the network. Either way, from Backrest's point of view it's just a folder, so the setup is identical: plug in the drive (or mount the remote share) on the host, add it to the compose file's volumes the same way you did for `/srv/docker` above, then in the Repository URI field, use the path as it appears **inside the container**:
```text
/userdata/backup-drive
```
That's it, no credentials, no Env Vars. This is the fastest repository to restore from too, since there's no network round-trip involved, which makes it a great pick for your "quick recovery" copy, paired with a proper offsite one below for the "my house is on fire" scenario.
::caution
__If it fails:__ the path has to exist and be writable by the container before you submit the form. An empty folder is fine, restic initializes the repository structure itself on first use.
::
### Backing up to another server
No cloud account, no problem: if you have SSH access to another machine, a friend's server, a cheap VPS, a Raspberry Pi at a relative's house, that's a perfectly valid offsite repository, and it costs whatever that machine already costs you.
First, make sure this server can SSH into the other one without typing a password every time:
```bash [Terminal]
ssh-keygen -t ed25519 -f /srv/docker/backrest/config/id_ed25519 -N ""
ssh-copy-id -i /srv/docker/backrest/config/id_ed25519.pub youruser@theotherserver
```
Mount that key into the container by adding it to the compose file's volumes:
```yaml [compose.yaml]
volumes:
# ...
- ./config/id_ed25519:/root/.ssh/id_ed25519:ro
```
Redeploy the stack, then in Backrest use:
```text
sftp:youruser@theotherserver:/path/to/backups
```
::caution
__If it fails:__ the target folder (`/path/to/backups` above) has to already exist on the other server, and that user needs write access to it. SSH there once by hand first (`ssh youruser@theotherserver`) to confirm the connection works and accept the host key, Backrest running inside a container won't get the interactive prompt for that.
::
## Advanced: cloud object storage
A local drive or a friend's spare server covers the 3-2-1 rule perfectly well, and costs nothing beyond what you already own. Cloud object storage is the other classic option, worth it once you want an offsite copy that doesn't depend on anyone's spare hardware staying online, at the cost of a few cents to a few euros a month depending on how much you back up.
### Backblaze B2
[Backblaze B2](https://www.backblaze.com/cloud-storage) is object storage built with exactly this use case in mind, and it's usually the cheapest option for the "write often, read rarely" pattern a backup is.
Create a bucket in your Backblaze account, then generate an **application key** scoped to it. In Backrest, use:
```text
b2:your-bucket-name:backrest
```
With the following Env Vars:
| Variable | Value |
|----------|-------|
| `B2_ACCOUNT_ID` | The application key ID |
| `B2_ACCOUNT_KEY` | The application key itself |
### S3-compatible storage
S3 isn't just an Amazon thing, it's a storage protocol that most cloud providers speak (OVH, Scaleway, MinIO if you self-host your own, and plenty of others), which makes it a solid, portable choice if you'd rather not depend on one specific provider.
Create a bucket with your provider of choice, then in Backrest's Repository URI field, use:
```text
s3:https://s3.your-provider.com/your-bucket-name/backrest
```
For actual AWS S3, drop the custom endpoint:
```text
s3:s3.amazonaws.com/your-bucket-name/backrest
```
With the following Env Vars:
| Variable | Value |
|----------|-------|
| `AWS_ACCESS_KEY_ID` | The access key from your provider |
| `AWS_SECRET_ACCESS_KEY` | The secret key from your provider |
::note
Generate these from your provider's dashboard, usually under something like "API keys" or "S3 credentials", scoped to that one bucket only if the provider allows it. There's no reason for a backup job's key to be able to touch anything else on your account.
::
### Repository maintenance (optional, but worth setting up once)
Back in the **Scheduling** tab, three policies keep a repository healthy over time. None of them are required to start backing up, restic works fine without ever touching them, but they're worth understanding once your repository has been running for a while:
:::collapsible{name="the three maintenance policies"}
- **Prune Policy**: deletes data that's no longer referenced by any snapshot (because old snapshots holding it were forgotten, see the retention policy in the next section). This is the only operation that actually frees up space on your storage. It's slow and reads a lot of data, so schedule it rarely, once a month is Backrest's own suggestion. **Max Unused After Prune** controls how thorough it is: a higher percentage leaves more unused data behind but finishes faster and copies less.
- **Check Policy**: verifies your repository isn't silently corrupted. **Read Data %** controls how much of the actual backed-up data gets re-read and checksummed, not just the repository's internal structure. 100% means a full re-read of everything, which uses real bandwidth and time; a smaller percentage checks a random sample instead. Once a month is, again, a reasonable default.
- **Forget Policy**: an optional repository-wide retention rule, applied across every plan writing to this repository instead of per-plan. Leave this disabled unless you specifically want one retention policy shared by multiple plans, it disables each plan's own retention policy the moment you turn it on.
Every one of these has a **Schedule Type**: `Disabled`, a plain `Interval` in hours or days, or a `Cron Expression` for anything more specific, plus a **Reference Clock** (your server's local time, UTC, or relative to the last time it ran) to anchor that schedule against.
:::
## Creating a backup plan
Back in Backrest, go to **Add Plan**. This form covers what to back up and when, as opposed to the repository form above, which only covers where:
- **Plan Name**: same rule as the repo name, pick something clear, you can't change it later.
- **Repository**: the one you just created above.
- **Paths**: click **Add** to add a row, then type in the container-side path for whatever you mounted above, it's a plain text field, but it autocompletes real paths from the container's filesystem as you type, handy to confirm a mount actually landed where you think. `/userdata/docker` for your stacks, `/userdata/etc` for your system config, `/userdata/home` for your own files. Click **Add** again for each additional folder, the small `-` button removes a row you don't need.
- **Excludes** and **Excludes (Case Insensitive)**: patterns to skip within those paths, handy for cache folders or anything genuinely disposable that would otherwise bloat every snapshot for no reason.
- **Schedule Type**: same three choices as the repository's own schedules above, `Disabled`, an `Interval`, or a `Cron Expression`. A nightly cron like `0 3 * * *` (every day at 3 AM) is a reasonable default for a homelab.
- **Retention Policy**: how many snapshots to keep, and for how long. **By Time Period** lets you say "keep 7 daily, 4 weekly, 6 monthly" independently, which gives you plenty of restore points spread over time without the repository growing forever, since restic deduplicates unchanged data between snapshots anyway. **By Count** instead just keeps the last N snapshots regardless of age. **Latest (Count)** on top of either mode guarantees a minimum number of recent snapshots always survive, whatever the rest of the policy says.
- **Advanced**: **Backup Flags** let you pass extra options straight to the underlying `restic backup` command for anything this form doesn't expose; **Hooks** run scripts or send notifications on backup events, the same mechanism as the repository's own Hooks tab, just scoped to this one plan instead of every plan using the repository.
That retention policy is your real defense against ransomware, by the way: if something starts encrypting your files at 2 AM, tonight's backup is compromised, but last week's snapshot isn't, and restic lets you restore from any of them.
::tip{icon="" to="/nonsense/bash/backrest-docker-stop"}
✨ __Going further:__ if some of what you're backing up includes a live database, stopping its container for the few seconds a backup takes is safer than backing it up while it's being written to. See **Backrest Docker Stop** for a script that does exactly that, triggered automatically by Backrest itself.
::
## Restoring a backup
A backup you've never tried restoring is a guess, not a plan, so it's worth doing once before you actually need it. Open the plan, click into a snapshot, expand **Snapshot Browser** down to whatever you need, then click the **...** menu next to it and pick **Restore to path**.
Leave the path field empty and Backrest streams it straight to your browser's downloads instead, the simplest option for grabbing a single file. Type a path and Backrest writes the restored data inside the container at that location instead, and it pre-fills a scratch folder like `/userdata-backrest-restore-<snapshot id>`, deliberately not your original mount.
That default isn't an accident: `/srv/docker`, `/etc` and `/home` are mounted `:ro`, so restic can't write back into them, restoring straight into `/userdata/docker` fails with a read-only filesystem error. Restore to that suggested scratch path (or download instead), check what you got, then copy the files into their real place yourself with `sudo cp -a`, from the host, outside of Backrest entirely. It's one extra step, but it also means a restore can never silently clobber live data by accident, exactly the caution you want mid-incident.
And that's it, you now have an actual backup strategy instead of a folder called `backup_final_v2_REAL`.
@@ -0,0 +1,169 @@
---
title: BTRFS Snapshots
description: Format Debian's root filesystem with BTRFS and use Snapper to instantly roll back a risky update or config change, as a local complement to Backrest's off-site 3-2-1 backups.
---
:ellipsis{left=0px width=40rem top=10rem blur=140px zIndex=60}
[BTRFS](https://btrfs.readthedocs.io/) is a Linux filesystem with one killer feature for a homelab: **snapshots**. A snapshot freezes the exact state of a filesystem in an instant, at essentially zero cost, without copying a single byte of data upfront. Break something ten minutes after an `apt full-upgrade`, or overwrite the wrong `.env` file, and you can go back to exactly how things were before, without touching a backup at all.
This is not what [Backrest and the 3-2-1 rule](/serveex/advanced/backrest) are for, so it's worth being precise about the difference before setting anything up.
## Snapshots are not backups
A snapshot lives on the exact same disk as the data it protects. It's instant, needs no network, and it's perfect for undoing a mistake you just made, but it does nothing at all the day that disk itself dies, gets stolen, or your server burns down. That's what a real [3-2-1 backup](/serveex/advanced/backrest) is for: a copy on different media, ideally off-site.
Think of it this way:
- **Snapshot** = an undo button. Instant, local, cheap, only useful while the disk is alive.
- **Backup** = insurance. Slower, off-site, the only thing that survives the disk itself failing.
Keep both. Snapshots make you fearless about updates and experiments, backups make sure a dead drive stays an inconvenience instead of a catastrophe.
::note{to="/serveex/core/installation#partitioning"}
This guide assumes the root partition was formatted with Btrfs during [Debian's installation](/serveex/core/installation#partitioning). Btrfs can't be safely bolted onto an existing ext4 root after the fact, so this is a choice you make once, at install time.
::
## Formatting the root partition with BTRFS
Debian's *Guided* partitioning only ever offers ext4. To get Btrfs, pick *Manual* partitioning instead, at the same step [the main install guide](/serveex/core/installation#partitioning) describes:
::steps{level="3"}
### Select Manual partitioning
At the partitioning method screen, choose *Manual* instead of *Guided - use entire disk*.
### Create a partition table
Select the disk, confirm creating a new empty partition table, then select the resulting *FREE SPACE* and choose *Create a new partition*.
### Set the partition size and type
Give the partition the rest of the disk (minus a small EFI partition if you're on UEFI, handled the same way as a Guided install), and set *Use as* to __Btrfs journaling file system__, with the mount point `/`.
### Finish partitioning
*Finish partitioning and write changes to disk*, then confirm with *Yes*.
### Done!
::
Everything else in the [installer](/serveex/core/installation#install-debian) stays the same.
## Installing Snapper
Rather than juggling raw `btrfs subvolume` commands by hand, [Snapper](https://github.com/openSUSE/snapper) is a small tool that manages the whole snapshot lifecycle: creating them, storing them tidily, pruning old ones, and automatically bracketing every `apt` operation with a snapshot pair.
```bash [Terminal]
sudo apt install snapper
sudo snapper -c root create-config /
```
`create-config` registers a config named `root` for the `/` filesystem, and creates a dedicated `.snapshots` subvolume under it to store every snapshot, locked down to root. No `@`/`@home` subvolume split needed, this works fine on the plain single-subvolume layout the manual partitioning above just created.
Turn the config on by editing `/etc/default/snapper`:
```properties [/etc/default/snapper]
SNAPPER_CONFIGS="root"
```
Then enable the timers that run Snapper's periodic snapshots and cleanup:
```bash [Terminal]
sudo systemctl enable --now snapper-timeline.timer snapper-cleanup.timer
```
`snapper-timeline.timer` fires **every hour** by default, that's fixed by the unit itself, not by a config option. Each run takes one snapshot and files it under the appropriate bucket (hourly, daily, monthly, yearly); the `TIMELINE_LIMIT_*` settings covered further down only control how many of each bucket survive, not how often a snapshot is taken. `snapper-cleanup.timer` runs once a day (plus once 10 minutes after boot) to enforce those limits.
::tip
✨ To take timeline snapshots at a different frequency, for example every 6 hours instead of every hour, override the timer instead of editing the package's unit file directly:
```bash [Terminal]
sudo systemctl edit snapper-timeline.timer
```
```ini [override.conf]
[Timer]
OnCalendar=
OnCalendar=*-*-* 0/6:00:00
```
The empty `OnCalendar=` line clears the packaged `hourly` value first, since systemd otherwise adds new `OnCalendar` lines to the existing ones instead of replacing them. Apply it with `sudo systemctl daemon-reload && sudo systemctl restart snapper-timeline.timer`.
::
::note
Debian's package also ships an APT hook (`/etc/apt/apt.conf.d/80snapper`) that kicks in the moment a config is listed in `SNAPPER_CONFIGS`: from now on, every `apt install`, `apt upgrade` or `apt full-upgrade` automatically gets a snapshot right before and right after it runs, with zero extra effort on your part.
::
## Taking a snapshot
For anything outside apt, like editing a systemd unit or a Docker Compose file, take one yourself with a description that will actually mean something later:
```bash [Terminal]
sudo snapper create --description "before compose change on swag"
```
List every snapshot with:
```bash [Terminal]
sudo snapper list
```
```console [Output]
# | Type | Pre # | Date | Description
---+--------+-------+--------------------------+---------------------------------
0 | single | | | current
1 | single | | Tue 09 Sep 2026 18:30:00 | before compose change on swag
2 | pre | | Tue 09 Sep 2026 19:00:01 | apt install unattended-upgrades
3 | post | 2 | Tue 09 Sep 2026 19:00:14 | apt install unattended-upgrades
```
## Restoring files from a snapshot
Snapper keeps the full state of the filesystem at snapshot time under `/.snapshots/<number>/snapshot`, browsable like any other folder:
```bash [Terminal]
ls /.snapshots/1/snapshot/etc/ssh/
```
To see exactly what changed between a snapshot and the live system (`0` always means "current") before touching anything:
```bash [Terminal]
sudo snapper status 1..0
```
That prints every file created, modified or deleted since. To undo those changes automatically:
```bash [Terminal]
sudo snapper undochange 1..0
```
Or restore a single file by hand, which is often the safer, more surgical choice:
```bash [Terminal]
sudo cp -a /.snapshots/1/snapshot/etc/ssh/sshd_config /etc/ssh/sshd_config
```
::note
This covers the vast majority of real homelab accidents: a bad config, a deleted file, a package upgrade that broke one thing. Snapper can also `rollback` the entire root filesystem to an earlier snapshot (it creates a new default subvolume and boots into it on the next restart), for a system in a genuinely bad state rather than just missing one file. It's a more delicate, less common operation, worth testing once on a machine you don't mind rebooting before you actually need it for real. And if the disk itself is the problem, that's exactly the scenario your off-site [Backrest](/serveex/advanced/backrest) backup is for anyway.
::
## Managing and pruning snapshots
Snapshots are cheap, not free: the moment the live filesystem diverges from one, the old blocks it still references stick around. Left unchecked, months of snapshots on a server that changes a lot (container images, logs) can quietly eat real disk space.
The `snapper-cleanup.timer` enabled above already prunes automatically, based on the config at `/etc/snapper/configs/root`:
| Setting | Default | What it does |
|---------|---------|---------------|
| `TIMELINE_LIMIT_HOURLY` / `_DAILY` / `_MONTHLY` / `_YEARLY` | `10` | How many timeline snapshots of each granularity to keep |
| `TIMELINE_LIMIT_WEEKLY` | `0` | Off by default |
| `NUMBER_LIMIT` | `50` | How many manual (`single`) snapshots to keep |
Adjust these to taste, then delete one immediately by hand if you need the space back right now:
```bash [Terminal]
sudo snapper delete 1
```
Check actual disk usage with `df -h /`: the numbers above only cap how many snapshots exist, not the space a very active server can still burn through between cleanups.
That's it: a rolling, automatic undo button for your server, quietly bracketing every update and pruning itself, running alongside the real backups Backrest is already taking off-site.
+1 -1
View File
@@ -1,5 +1,5 @@
---
title: Introduction
title: Stockeex
description: Introduction to Stockeex, a personal project for stock and inventory management. Documentation coming soon.
navigation:
icon: i-lucide-bookmark
@@ -77,6 +77,6 @@ services:
More information is available on the repository:
::card{title="🐋 **Socat Proxy**" to="https://git.djeex.fr/Djeex/socat-proxy" target="_blank"}
::card{title="🐋 __Socat Proxy__" to="https://git.djeex.fr/Djeex/socat-proxy" target="_blank"}
A lightweight bind-mount socket proxy
::
@@ -156,7 +156,7 @@ sudo sysctl net.ipv4.conf.all.src_valid_mark=1
To configure clients, download the config files from the server:
- Visit `http://your-server-ip:51821`
- Visit `http://yourserverip:51821`
- Create a client
- Download the config file
- Rename it to `wg0.conf`
@@ -257,13 +257,13 @@ Repeat for each client
## Other Devices
- **Phone:** Install WireGuard and scan the QR code from the web UI (`http://your-server-ip:51821`)
- **Phone:** Install WireGuard and scan the QR code from the web UI (`http://yourserverip:51821`)
- **PC:** Install the WireGuard client and import the config file
::warning
__Warning:__ If a client device is on the same LAN as the server, edit `wg0.conf` and change the endpoint to the local server IP:
`Endpoint = your-server-ip:51820`
`Endpoint = yourserverip:51820`
::
And this is the result:
@@ -1,6 +1,6 @@
---
title: File Browser
description: Install File Browser to browse and manage your server files from a web interface, exposed securely with SWAG.
description: Archived guide to installing File Browser to browse and manage your server files, superseded by File Browser Quantum.
---
@@ -29,7 +29,7 @@ services:
container_name: filebrowser
volumes:
- /srv/docker/filebrowser/config:/config/
- /path/to/your/folders:/yourfolders #add your folders to browse as /srv/docker:/srv/docker for exemple
- /path/to/your/folders:/yourfolders #add your folders to browse as /srv/docker:/srv/docker for example
ports:
- 8010:80
image: filebrowser/filebrowser:s6
@@ -1,6 +1,6 @@
---
title: Plex
description: Install Plex Media Server with Tautulli on your homelab to stream movies and TV shows from anywhere on all your devices.
description: Archived guide to installing Plex Media Server with Tautulli, kept for reference — Serveex now recommends Jellyfin.
---
@@ -8,10 +8,10 @@ description: Install Plex Media Server with Tautulli on your homelab to stream m
::note{to="/serveex/media/jellyfin"}
This is an alternative to **Jellyfin**, kept here for reference. Plex isn't fully self-hosted: local playback still goes through Plex's own relay and requires a Plex account, and several features sit behind a Plex Pass paywall.
This is an alternative to **Jellyfin**, kept here for reference. Plex isn't fully self-hosted: it requires a Plex account even for local playback, remote access can fall back to Plex's own relay when a direct connection fails, and several features sit behind a Plex Pass paywall.
::
[Plex](https://www.plex.tv/fr/) is a self-hosted video streaming platform for managing your movie or TV show library and playing them locally or remotely. Plex has apps for TV, Android, iOS, Windows, and macOS, allowing you to stream your library just like Netflix.
[Plex](https://www.plex.tv/) is a self-hosted video streaming platform for managing your movie or TV show library and playing them locally or remotely. Plex has apps for TV, Android, iOS, Windows, and macOS, allowing you to stream your library just like Netflix.
With *Plex Pass*, you can also organize and play your music content similar to Spotify, the difference being that its your content, hosted and streamed from your server.
@@ -1,6 +1,6 @@
---
title: qBittorrent for Plex
description: Install qBittorrent with Gluetun and ProtonVPN to download torrents securely behind a VPN on your self-hosted server.
description: Archived guide to installing qBittorrent for a Plex setup, kept for reference — see the current qBittorrent guide instead.
---
@@ -52,7 +52,7 @@ tree:
If not already done, create the `downloads` folder under `/media`:
```bash [Terminal]
mkdir -P /media/downloads
mkdir -p /media/downloads
```
### Deploy the stack
@@ -93,7 +93,7 @@ services:
devices:
- /dev/net/tun:/dev/net/tun
ports:
- ${UI_PORT}:5695 # Port de la web-ui
- ${UI_PORT}:${UI_PORT} # Port de la web-ui
- 8000:8000 # Port de controle de Gluetun
cap_add:
- NET_ADMIN
@@ -206,7 +206,7 @@ Once done, deploy the container.
### Log in and secure your account
Login at `http://server-ip:5695` (or the port you set).
Login at `http://yourserverip:5695` (or the port you set).
::caution
@@ -262,7 +262,7 @@ Click "Deploy" and wait for SWAG to fully initialize.
::note
We assume the network name is `seedbox_default`. You can confirm by checking the SWAG dashboard at http://server-ip:81.
We assume the network name is `seedbox_default`. You can confirm by checking the SWAG dashboard at http://yourserverip:81.
::
### Create the subdomain.conf file
@@ -322,7 +322,7 @@ server {
include /config/nginx/proxy.conf;
include /config/nginx/resolver.conf;
set $upstream_app gluetun;
set $upstream_port 5555;
set $upstream_port 5695;
set $upstream_proto http;
proxy_pass $upstream_proto://$upstream_app:$upstream_port;
@@ -1,6 +1,6 @@
---
title: Servarr for Plex
description: Automate media downloads with the Servarr stack, Radarr, Sonarr, Bazarr, Prowlarr, and Overseerr for movies and TV shows.
description: Archived guide to the Servarr stack for a Plex setup, kept for reference — see the current Servarr guide instead.
---
@@ -415,7 +415,7 @@ It can be useful to expose Overseerr if you want to send requests from outside y
::note
We assume you have the subdomain `films.mydomain.com` with a `CNAME` pointing to `films.fr` in your [DNS zone](/general/networking/dns). And that [unless youre using Cloudflare Zero Trust](/serveex/security/cloudflare), port `443` on your router is forwarded to port `443` on your server via [NAT rules](/general/networking/nat).
We assume you have the subdomain `films.mydomain.com` with a `CNAME` pointing to `mydomain.com` in your [DNS zone](/general/networking/dns). And that [unless youre using Cloudflare Zero Trust](/serveex/security/cloudflare), port `443` on your router is forwarded to port `443` on your server via [NAT rules](/general/networking/nat).
::
::steps{level="3"}
@@ -1,6 +1,6 @@
---
title: Gitea
description: Install Gitea, a lightweight self-hosted Git service to manage your code repositories privately on your own server.
description: Archived guide to installing Gitea, kept for reference — Serveex now recommends Forgejo.
---
+1 -1
View File
@@ -43,7 +43,7 @@ Set up my homelab →
::::
::::div{class="flex flex-col gap-5 justify-start self-start"}
<h2 class="text-sm font-semibold text-muted uppercase tracking-wide mt-0 mb-0">And Other dumb things</h2>
<h2 class="text-sm font-semibold text-muted uppercase tracking-wide mt-0 mb-0">And other dumb things</h2>
:::::card
---
+2 -2
View File
@@ -18,7 +18,7 @@ __Docu[·]{style="color: #1ad6ff"}djeex__ est le site regroupant la documentatio
La documentation fournie ici est distribuée à titre expérimental, dans un esprit de partage d'expérience. Elle n'est en aucun cas faite pour construire une architecture de production ou pour de l'industrialisation. Il est possible qu'elle contienne des erreurs et/ou des approximations.
Evidemment, l'usage de cette documentation doit strictement se limiter au cadre légal.
Évidemment, l'usage de cette documentation doit strictement se limiter au cadre légal.
### Documentation disponible ou à venir
@@ -43,7 +43,7 @@ Votre homelab à déployer, pas à pas
Scripts personnels et projets annexes
::
::card{icon="i-noto-recycling-symbol" title="Poubelle" to="/recycled/deprecated/wireguard-14"}
::card{icon="i-noto-recycling-symbol" title="Recyclage" to="/recycled/deprecated/wireguard-14"}
Pages périmées, conservées pour archive ou alternatives
::
::
+1 -1
View File
@@ -11,7 +11,7 @@ description: Comprendre le NAT, la redirection de ports et le DHCP sur un routeu
## Qu'est-ce qu'un « port » ?
Les ports sont différents canaux par lesquels votre routeur envoie et reçoit des données, ce qui permet d'utiliser plusieurs services en meme temps. Lorsqu'il reçoit des données via un port, votre routeur transmet ensuite les données à la machine qui :
Les ports sont différents canaux par lesquels votre routeur envoie et reçoit des données, ce qui permet d'utiliser plusieurs services en même temps. Lorsqu'il reçoit des données via un port, votre routeur transmet ensuite les données à la machine qui :
- soit a émis la requête de départ,
- soit est configurée pour recevoir les données arrivant sur un port spécifique.
+1 -1
View File
@@ -8,7 +8,7 @@ description: Comprendre le fonctionnement du DNS, lire et éditer une zone DNS,
## Introduction
Lorsque vous naviguez sur un site, ou une application, des requêtes sont émises vers un ou des domaines afin d'afficher le contenu de votre page. Votre appareil ne connait pas les adresses IP de ces serveurs à joindre. Pour les connaitre, il va contacter un _serveur de nom_ (Domain Name Server) qui lui va lui répondre avec l'adresse IP la plus à jour pour le domaine de la requête.
Lorsque vous naviguez sur un site, ou une application, des requêtes sont émises vers un ou des domaines afin d'afficher le contenu de votre page. Votre appareil ne connait pas les adresses IP de ces serveurs à joindre. Pour les connaitre, il va contacter un _serveur de nom_ (Domain Name Server) qui va lui répondre avec l'adresse IP la plus à jour pour le domaine de la requête.
La zone DNS, c'est une sorte de registre avec des panneaux qui redirige vos requêtes vers la bonne destination.
+1 -1
View File
@@ -54,7 +54,7 @@ Utilisez vos disques sans RAID si vous navez pas peur de perdre des données
</ul>
</div>
Utilisez RAID 0 si vous souhaitez privilégier la performance et que la perte de données nest pas un problème. Idéal pour le stockage temporaire à haute vitesse (montage vidéo, IA, etc). Pas adapté au stockage à long terme.
Utilisez RAID 0 si vous souhaitez privilégier la performance et que la perte de données nest pas un problème. Idéal pour le stockage temporaire à haute vitesse (montage vidéo, IA, etc). Pas adapté au stockage à long terme, car la perte d'un seul disque entraîne la perte totale des données.
### RAID 1
+2 -2
View File
@@ -29,8 +29,8 @@ Ce qui nous intéresse le plus :
ZFS dispose d'une structure particulière :
- __vdev__ (virtual device) : une grappe de disques (physiques ou virtuel)
- __zpool__ : un ensemble de disques physiques ou virtuels en volume simple, Z-mirror ou RAIDZ. Un _zpool_ peut englober plusieurs _vdev_ mais pas l'inverse.
- __dataset__ : un système de de donnée dans un _zpool_. Chaque dataset peut avoir ses propres options (compression, quotas, permissions, etc.).
- __zpool__ : un ensemble de _vdev_ configuré comme un seul pool de stockage. Un _zpool_ peut englober plusieurs _vdev_ mais pas l'inverse.
- __dataset__ : un conteneur logique de données dans un _zpool_. Chaque dataset peut avoir ses propres options (compression, quotas, permissions, etc.).
Il existe plusieurs types de dataset :
+1 -1
View File
@@ -94,7 +94,7 @@ Contrairement aux HDD, ils ne disposent pas de parties mécaniques, sont très m
On les trouve dans plusieurs formats, aujourd'hui on privilégiera les versions M.2 NVMe, car ce sont les plus petits et plus rapides, et sont devenues un standard sur les cartes mères.
Ils sont en revanche beaucoup plus chers que les disque durs à capacité de stockage égale. Généralement, on y stockera au moins le système d'exploitation de la machine (Operating System ou OS) pour garantir une certaine rapidité d'exécution. Dans le cadre d'un serveur, on y stockera aussi si possible les conteneurs type [docker](/serveex/core/docker) et les bases de données. De manière générale, toute données dont un a besoin régulièrement et rapidement pour des calculs (site web, applications, etc.).
Ils sont en revanche beaucoup plus chers que les disque durs à capacité de stockage égale. Généralement, on y stockera au moins le système d'exploitation de la machine (Operating System ou OS) pour garantir une certaine rapidité d'exécution. Dans le cadre d'un serveur, on y stockera aussi si possible les conteneurs type [docker](/serveex/core/docker) et les bases de données. De manière générale, toutes les données dont on a besoin régulièrement et rapidement pour des calculs (site web, applications, etc.) devraient être stockées sur un SSD.
## La carte réseau
+3 -3
View File
@@ -19,7 +19,7 @@ Plus généralement, un routeur est composé :
- d'un port WAN (Wide Area Network) recevant les informations depuis l'internet (ou un réseau de hiérarchie supérieure). Par exemple un port recevant la fibre optique de votre opérateur, ou un port SFP+/RJ45 pour un routeur tiers.
- d'un switch, c'est-à-dire d'un hub composé de plusieurs ports __LAN__ (Local Area Network) permettant de connecter plusieurs lignes et appareils à votre routeur. Ils peuvent être RJ45 ou SFP/SFP+.
- parfois d'un emetteur/recepteur WiFi
- parfois d'un émetteur/récepteur WiFi
Le routeur peut posséder des capacités de _firewall_, c'est-à-dire de limiter le trafic d'appareils en particulier, et de _[NAT (Network Address Translation)](/general/networking/nat)_, c'est-à-dire de redirection de port. Il possède aussi généralement un _[DHCP (Dynamic Host Configuration Protocol)](/general/networking/nat#le-dhcp)_, servant à attribuer dynamiquement des _adresses IP_ à votre matériel branché au réseau.
@@ -74,7 +74,7 @@ Ils sont définis en plusieurs catégorie, définissant le débit maximal selon
| | CAT 5e | 30 m |
| 2.5 Gb/s | CAT 5e | 100 m |
| 1 Gb/s | CAT 5e | 100 m |
| 100 Mbs | CAT 5 | 100 m |
| 100 Mb/s | CAT 5 | 100 m |
Certains de ces câbles sont plats, ronds, blindés (à relier à la terre), etc. Choisissez en fonction de votre installation. ce qu'il faut comprendre, c'est que pour relier un appareil qui dispose d'une prise RJ45 ethernet 2.5 Gb/s sur un routeur 2.5G b/s, il faut au moins un câble `CAT 5e`.
@@ -85,7 +85,7 @@ Aujourd'hui, dans les nouvelles constructions, la norme est d'installer des câb
### Les câbles optiques
Très fins mais très fragiles, on commence à les voir de plus en plus dans les installations chez soi. A commencer par le câble opérateur qui relie votre prise fibre à votre box/routeur. Ils ont plusieurs avantages :
Très fins mais très fragiles, on commence à les voir de plus en plus dans les installations chez soi. À commencer par le câble opérateur qui relie votre prise fibre à votre box/routeur. Ils ont plusieurs avantages :
- Extrêmement compacts
- Consommation électrique nulle (contrairement au cuivre, qui perd de l'énergie en chaleur)
@@ -36,7 +36,7 @@ Un NAS (Network Attached Storage), c'est une machine conçue autour d'un espace
### Mais pourquoi un Mini PC avec un disque dur externe ne suffirait-il pas ?
Bien sûr, un simple mini PC avec ses 1 à 2To de stockage devraient suffire pour la plupart des gens. Et les films pourraient tenir dans un disque dur externe de quelques TB supplémentaires. En revanche ce n'est pas une solution fiable ni extensible de faire tourner ses applications et usages sur du stockage qui au moindre choc, au moindre problème, fait perdre vos données définitivement.
Bien sûr, un simple mini PC avec ses 1 à 2To de stockage devrait suffire pour la plupart des gens. Et les films pourraient tenir dans un disque dur externe de quelques TB supplémentaires. En revanche ce n'est pas une solution fiable ni extensible de faire tourner ses applications et usages sur du stockage qui au moindre choc, au moindre problème, fait perdre vos données définitivement.
Le vrai NAS est construit autour de la fiabilité du support qui contient vos données. Il nécessite de mettre en place des stratégies de stockages type [RAID](/general/storage/raid) afin de préserver vos données en cas de panne et de la sauvegarde en cas de corruption (comme les snapshot [ZFS](/general/storage/zfs)).
+2 -2
View File
@@ -190,7 +190,7 @@ grep -rin "password" /home/utilisateur/docker
Chaque ligne indique le fichier, puis le numéro de ligne à l'intérieur, puis la ligne correspondante elle-même. Très pratique le jour où vous ne vous souvenez plus dans quelle stack se trouve un réglage.
### `sudo`, lancer en privilèges administrateur
### `sudo`, lancer en tant qu'administrateur
*Substitute user do*. Afin d'éviter de casser votre serveur par accident, un utilisateur normal ne peut pas toucher aux fichiers du système. Préfixer une commande par `sudo` lance cette seule commande avec les droits administrateur. Cette commande vous demandera votre mot de passe au moins une fois par session, et parfois plusieurs fois selon le temps qui se sera écoulé depuis sa dernière utilisation.
@@ -243,7 +243,7 @@ Les commandes qui valent la peine d'être gardées sous la main, et d'où vienne
| `chmod` | change mode | Change les permissions d'un fichier |
| `chown` | change owner | Change le propriétaire d'un fichier |
| `sudo` | substitute user do | Lance une commande en administrateur |
| `apt` | advanced package tool | Installe, met à jour et supprime des paquets |
| `apt` | Advanced Package Tool | Installe, met à jour et supprime des paquets |
| `systemctl` | control systemd | Démarre, arrête et active des services |
| `ssh` | secure shell | Ouvre une session sur une machine distante |
| `scp` | secure copy | Copie des fichiers via SSH |
@@ -37,7 +37,7 @@ sudo apt install btop duf ncdu tealdeer ufw
## `btop`, surveiller ce que fait la machine
Le remplaçant moderne de `top` et `htop` : CPU, RAM, disques, réseau et processus sur un seul écran, avec des graphiques, des couleurs et une souris qui marche. C'est ce que vous ouvrez quand quelque chose semble lent, l'équivalent du gestionnaire de tache sur Windows ou du moniteur d'activité sur Mac.
Le remplaçant moderne de `top` et `htop` : CPU, RAM, disques, réseau et processus sur un seul écran, avec des graphiques, des couleurs et une souris qui marche. C'est ce que vous ouvrez quand quelque chose semble lent, l'équivalent du gestionnaire de tâches sur Windows ou du moniteur d'activité sur Mac.
::steps{level="4"}
#### L'installer
@@ -61,7 +61,7 @@ Cliquez sur un processus pour le sélectionner, :kbd{value="Esc"} ouvre le menu,
## `duf`, l'espace disque qui se lit comme un tableau
`df -h` affiche tous tous vos dossiers/fichiers et vous laisse vous exploser les yeux sur les colonnes, les chiffres, les tailles. `duf` montre les mêmes informations groupées, alignées et colorées, avec une barre d'utilisation par système de fichiers.
`df -h` affiche jusqu'au moindre loop device créé par Docker et vous laisse vous exploser les yeux sur les colonnes, les chiffres, les tailles. `duf` montre les mêmes informations groupées, alignées et colorées, avec une barre d'utilisation par système de fichiers.
::steps{level="4"}
#### L'installer
@@ -179,8 +179,8 @@ Il a besoin d'accéder au socket Docker, d'où le `sudo` à moins que votre util
| Touche | Ce qu'elle fait |
| --- | --- |
| `1` à `6` | Aller à un onglet : projets, services, conteneurs, images, volumes, réseaux |
| Flèches | Se déplacer dans le onglet, la partie droite suit la sélection |
| :kbd{value="Enter"} | Passer sur le onglet principal à droite, :kbd{value="Esc"} revient |
| Flèches | Se déplacer dans l'onglet, la partie droite suit la sélection |
| :kbd{value="Enter"} | Passer sur l'onglet principal à droite, :kbd{value="Esc"} revient |
| `x` | Ouvrir le menu de tout ce que vous pouvez faire avec la sélection |
| `m` | Suivre les logs |
| `s` / `r` / `p` | Arrêter, redémarrer, mettre en pause le conteneur sélectionné |
+11 -1
View File
@@ -189,7 +189,7 @@ Installer et déployer la stack Servarr
::
::
### Cloud & Photos
### Cloud Drive & Photos
:::div{class="relative"}
:ellipsis{left=0px width=40rem top=10rem blur=140px}
@@ -296,6 +296,8 @@ ui:
icon: text-[#175DDC]
---
Installer et déployer Vaultwarden
::
::
::
@@ -313,6 +315,14 @@ Installer et déployer Authentik
::card{icon="i-noto-crystal-ball" title="Gestionnaire Docker multi-hôtes" to="/serveex/advanced/arcane"}
Installer et déployer Arcane
::
::card{icon="i-lucide-database-backup" title="Sauvegardes en 3-2-1" to="/serveex/advanced/backrest"}
Installer et déployer Backrest
::
::card{icon="i-lucide-rotate-ccw" title="Retour en arrière instantané" to="/serveex/advanced/btrfs-snapshots"}
Mettre en place les snapshots BTRFS
::
::
## Bientôt
@@ -40,11 +40,11 @@ Si vous êtes en dual boot avec Windows, désactivez son *démarrage rapide* : i
Récupérez l'image **netinst** `amd64` sur [debian.org](https://www.debian.org/download.fr.html). Elle fait environ 700 Mo et récupère le reste des paquets sur le réseau pendant l'installation, ce qui est exactement ce qu'on veut sur un serveur branché en ethernet : vous obtenez des paquets à jour au lieu d'installer depuis un instantané vieux de plusieurs mois puis de tout mettre à jour derrière. Les images DVD complètes n'ont de sens que si la machine n'a pas de réseau pendant l'installation.
#### Créer une clée bootable avec Rufus
#### Créer une clé bootable avec Rufus
Sous Windows, utilisez [Rufus](https://rufus.ie/) (portable, aucune installation nécessaire). Branchez une clé USB de 2 Go ou plus, en gardant en tête qu'**elle sera entièrement effacée**, puis :
- **Périphérique** : votre clé USB. Vérifiez la capacité deux fois, Sinon Rufus écrira sans rechigner sur le mauvais disque si vous le laissez faire.
- **Périphérique** : votre clé USB. Vérifiez la capacité deux fois : sinon, Rufus écrira sans rechigner sur le mauvais disque si vous le laissez faire.
- **Type de démarrage** : `SÉLECTION`, puis choisissez l'ISO Debian que vous venez de télécharger.
- **Schéma de partition** : il doit correspondre au mode de démarrage réglé dans le BIOS plus haut. `GPT` pour l'UEFI, `MBR` uniquement si vous restez en legacy/CSM. Le champ système de destination suit automatiquement.
- Laissez les options de formatage par défaut, puis cliquez sur `DÉMARRER`. Si Rufus demande comment écrire l'image, gardez le *mode image ISO* recommandé.
@@ -89,6 +89,10 @@ Confirmez le fuseau horaire deviné à partir de votre pays.
*Assisté, utiliser un disque entier* sur le disque système, puis *Tout dans une seule partition*, ce qui vous donne un gros `/` plus une partition de swap. Des partitions `/home` ou `/var` séparées n'apportent pas grand-chose ici et garantissent surtout que l'une se remplit pendant que les autres restent à moitié vides. Ne prenez LVM que si vous savez déjà que vous voulez des snapshots ou agrandir des volumes plus tard. Vos disques de données ne sont pas touchés à ce stade, vous les monterez ensuite.
::warning{to="/serveex/advanced/btrfs-snapshots"}
__Pour les utilisateurs avancés :__ c'est maintenant qu'il faut décider, pas plus tard. Choisir *Manuel* ici plutôt qu'*Assisté* permet de formater la partition racine en Btrfs plutôt qu'en ext4, ce qui débloque des snapshots instantanés et quasi gratuits vers lesquels revenir avant une mise à jour risquée ou un changement de config. Une fois cette étape passée et Debian installé en ext4, passer à Btrfs n'est plus possible sans effacer le disque et tout recommencer. Voir **Snapshots BTRFS** pour la mise en place, ça ne remplace pas non plus de vraies sauvegardes, un snapshot vit sur le même disque.
::
Terminez avec *Terminer le partitionnement et appliquer les changements*, puis confirmez avec *Oui* : c'est le point de non-retour pour ce disque.
![Schéma de partitionnement de l'installateur Debian, tout dans une seule partition](/img/serveex/install/debian-install-partition.png)
@@ -160,7 +164,7 @@ Toujours sur l'autre machine, générez une clé.
ssh-keygen -t ed25519
```
Appuyez sur :kbd{value="Enter"} pour accepter le chemin par défaut, et mettez une passphrase (elle protège le fichier de clé lui-même, votre système la retiendra après le premier déverrouillage). Il s'agit ensuite de transmettre la clée publique à votre serveur. A noter que Windows n'a pas de `ssh-copy-id`, nous pousserons donc la clé manuellement dans ce cas :
Appuyez sur :kbd{value="Enter"} pour accepter le chemin par défaut, et mettez une passphrase (elle protège le fichier de clé lui-même, votre système la retiendra après le premier déverrouillage). Il s'agit ensuite de transmettre la clé publique à votre serveur. À noter que Windows n'a pas de `ssh-copy-id`, nous pousserons donc la clé manuellement dans ce cas :
::code-group
```bash [macOS]
+4 -4
View File
@@ -19,11 +19,11 @@ Il existe aussi des clients Windows, macOS, iOS et Android.
Le principe est le suivant :
- Sur internet, n'importe qui peut contacter n'importe quel box internet et donc essayer de contacter n'importe quel serveur exposé.
- Votre serveur est sur votre réseau local. Il est accessible depuis le réseau local mais pas depuis internet, mis à part les services exposés (comme nous l'avons fait avec Dockge). Pour accéder aux ressources non exposées, vous devez être connecté sur le même réseau que votre serveur et donc être chez vous. De plus, vous devez laisser ouvert les ports utilisés par vos services à travers le pare feu de votre serveur.
- Votre serveur est sur votre réseau local. Il est accessible depuis le réseau local mais pas depuis internet, mis à part les services exposés (comme nous l'avons fait avec Dockge). Pour accéder aux ressources non exposées, vous devez être connecté sur le même réseau que votre serveur et donc être chez vous. De plus, vous devez laisser ouverts les ports utilisés par vos services à travers le pare-feu de votre serveur.
- Nous souhaitons ici au contraire, depuis n'importe où, pouvoir accéder de manière sécurisée aux services non exposés sur internet du serveur, comme la console SSH qui permet de se connecter à la machine par exemple.
- Nous souhaitons aussi accéder aux services d'autres serveurs, et par exemple relier de manière sécurisée deux instances de Dockge pour tout contrôler depuis la même interface.
Pour cela nous allons créer un **réseau privé virtuel**, ou VPN, c'est-à-dire un tunnel sécurisé auquel personne n'a accès à part les machines que vous relierez entre elles. Elles feront partie d'un nouveau réseau et pourront dialoguer entre elle comme dans un réseau local.
Pour cela nous allons créer un **réseau privé virtuel**, ou VPN, c'est-à-dire un tunnel sécurisé auquel personne n'a accès à part les machines que vous relierez entre elles. Elles feront partie d'un nouveau réseau et pourront dialoguer entre elles comme dans un réseau local.
D'autre part, vous pourrez ajouter votre téléphone, un ordinateur portable ou n'importe quel appareil au réseau pour pouvoir utiliser vos ressources depuis vos appareils quotidiens, où que vous soyez.
@@ -34,9 +34,9 @@ Dans cette illustration, la machine 1 est sur deux réseaux :
- son réseau local (tous les appareils liés à la box, avec une adresse IP du type `192.168.x.x ` donc ici la machine 1 et la machine 2)
- le réseau du VPN (tous les appareils reliés au VPN, avec une seconde adresse IP du type `10.8.x.x` donc ici la machine 1 et 4)
On peut aussi faire en sorte que les machines reliées au réseau virtuel partagent les accès à leur réseau local. Ici nous ne le ferons pas, pour des raisons de sécurité, et de complexité en terme de sous-réseau (si les deux machines distantes ont des machines locales qui utilisent la même adresse IP locale, par exemple `192.168.1.1`, cela posera des conflits).
On peut aussi faire en sorte que les machines reliées au réseau virtuel partagent les accès à leur réseau local. Ici nous ne le ferons pas, pour des raisons de sécurité, et de complexité en termes de sous-réseau (si les deux machines distantes ont des machines locales qui utilisent la même adresse IP locale, par exemple `192.168.1.1`, cela posera des conflits).
Ainsi, sur le réseau virtuel, seules les machines directement reliées pourront dialoguer entre elle depuis ce réseau. Elles ne pourront pas dialoguer avec une machine situées sur un autre réseau local et non reliée au VPN.
Ainsi, sur le réseau virtuel, seules les machines directement reliées pourront dialoguer entre elles depuis ce réseau. Elles ne pourront pas dialoguer avec une machine située sur un autre réseau local et non reliée au VPN.
## Côté serveur
::note{icon=""}
@@ -8,7 +8,7 @@ description: Utiliser les tunnels Cloudflare et Zero Trust pour exposer des serv
![cloudfare_tunnels](/img/serveex/cloudflared.svg)
## Introduction
L'architecture _Zero Trust_ est la pratique consistant à concevoir des systèmes fondés sur le principe de __« ne jamais faire confiance__, __toujours vérifier »__, par opposition au principe traditionnel de __« confiance, mais vérifier »__. Ce concept est devenu très populaires récemment, à la suite des attaques toujours plus nombreuses concernant les données des utilisateurs. C'est un concept très large, nous nous concentrerons sur lapplication du _Zero Trust_ aux services Web que nous hébergeons.
L'architecture _Zero Trust_ est la pratique consistant à concevoir des systèmes fondés sur le principe de __« ne jamais faire confiance__, __toujours vérifier »__, par opposition au principe traditionnel de __« confiance, mais vérifier »__. Ce concept est devenu très populaire récemment, à la suite des attaques toujours plus nombreuses concernant les données des utilisateurs. C'est un concept très large, nous nous concentrerons sur lapplication du _Zero Trust_ aux services Web que nous hébergeons.
Les _tunnels Cloudflare_ offrent un moyen simple d'arriver au _Zero Trust_, en s'appuyant sur [SWAG](/serveex/core/swag) et [Authentik](/serveex/advanced/authentik).
@@ -42,17 +42,17 @@ Si vous avez plusieurs serveurs et donc plusieurs tunnels pour un même domaine
### Clé API
Pour commencer, nous devons créer un nouveau jeton API pour Cloudflare et récupérer nos identifiants de zone et de compte.
Pour commencer, vous devez créer un nouveau jeton API pour Cloudflare et récupérer vos identifiants de zone et de compte.
Sur le tableau de bord de Cloudflare, dans la page de présentation de votre domaine, vous pouvez voir les identifiants de `zone` et de `compte` en bas à droite de l'écran. Copiez précieusement ces deux identifiants.
![id and account](/img/serveex/cf-id.png)
Juste en dessous d'eux, il y a un lien intitulé _Obtenez votre jeton API_. Cliquez dessus. Le périmètre dont nous avons besoin pour le jeton doit inclure `Zone:DNS:Edit` et `Account:Cloudflare Tunnel:Edit`. Assurez-vous que votre page de création de token ressemble à celle illustrée dans la capture d'écran ci-dessous.
Juste en dessous d'eux, il y a un lien intitulé _Obtenez votre jeton API_. Cliquez dessus. Le périmètre dont vous avez besoin pour le jeton doit inclure `Zone:DNS:Edit` et `Account:Cloudflare Tunnel:Edit`. Assurez-vous que votre page de création de token ressemble à celle illustrée dans la capture d'écran ci-dessous.
![API token](/img/serveex/cf-token.png)
Une fois que nous aurons enregistré, notre jeton sera affiché une fois. copiez le précieusement, car vous ne pourrez plus le revoir après la fermeture.
Une fois que vous aurez enregistré, votre jeton sera affiché une fois. Copiez-le précieusement, car vous ne pourrez plus le revoir après la fermeture.
### Cloudflare Zero Trust
@@ -15,6 +15,8 @@ Nativement il gère une simple connexion locale identifiant/mot de passe, c'est
- [Documentation de TinyAuth](https://tinyauth.app/docs/getting-started)
- [TinyAuth sur GitHub](https://github.com/tinyauthapp/tinyauth)
![Schéma de TinyAuth placé derrière SWAG en tant que proxy de forward-auth devant les services locaux](/img/serveex/tinyauth.svg)
## Installation
::file-tree
@@ -15,6 +15,8 @@ C'est donc un bon choix si vous voulez simplement un backend SSO simple et rapid
- [Documentation de Pocket ID](https://pocket-id.org/docs)
- [Pocket ID sur GitHub](https://github.com/pocket-id/pocket-id)
![Schéma de Pocket ID agissant comme fournisseur d'identité OIDC natif derrière SWAG](/img/serveex/pocket-id-native.svg)
## Installation
::file-tree
@@ -230,6 +232,8 @@ Enregistrez, puis copiez le __Client ID__ et le __Client Secret__ générés. Vo
## Connecter Pocket ID à TinyAuth
[TinyAuth](/serveex/security/tinyauth) peut déléguer sa connexion à Pocket ID plutôt que (ou en plus de) son identifiant/mot de passe local, de sorte que quiconque visite une application protégée s'authentifie avec une passkey et se retrouve redirigé.
![Schéma de TinyAuth délégant la connexion à Pocket ID via OIDC](/img/serveex/pocket-id.svg)
::steps{level="3"}
### Enregistrer TinyAuth comme client OIDC
@@ -39,6 +39,8 @@ services:
image: amir20/dozzle:latest
ports:
- 9135:8080
volumes:
- /docker/dozzle/data:/data
env_file:
- .env
environment:
+8 -15
View File
@@ -8,7 +8,7 @@ description: Installer UpSnap pour réveiller à distance les machines de votre
[UpSnap](https://github.com/seriousm4x/UpSnap) est un conteneur qui permet d'allumer, d'éteindre ou de mettre en veille vos machines à distance. Il utilise principalement le Wake-On-Lan (WoL) sur le réseau et propose des fonctions avancées.
![Beszel](/img/serveex/upsnap.webp)
![UpSnap](/img/serveex/upsnap.webp)
## Installation
@@ -101,9 +101,9 @@ Nous partons du principe que vous avez créé un sous-domaine dans votre [zone D
::
::steps{level="3"}
### Ajouter le réseau d'UpSnap à SWAG
### Rendre l'hôte accessible depuis SWAG
Allez dans Dockge et modifiez le compose de SWAG en y ajoutant le réseau d'UpSnap :
UpSnap tourne en `network_mode: host` (nécessaire pour que la diffusion Wake-on-LAN et le scan réseau fonctionnent de manière fiable), il ne rejoint donc jamais de réseau Docker auquel SWAG pourrait se rattacher comme pour les autres stacks. Il faut à la place donner à SWAG un moyen d'atteindre l'hôte lui-même :
```yaml [compose.yaml]
---
@@ -111,22 +111,15 @@ services:
swag:
container_name: # ...
# ...
networks: # Rattache le conteneur au réseau personnalisé
# ...
- upsnap # Nom du réseau déclaré dans la stack
networks: # Définit le réseau personnalisé
# ...
upsnap: # Nom du réseau déclaré dans la stack
name: upsnap_default # Nom réel du réseau externe
external: true # Indique qu'il s'agit d'un réseau externe
extra_hosts:
- "host.docker.internal:host-gateway" # se résout vers l'IP de l'hôte Docker lui-même
```
Redémarrez la stack en cliquant sur « deploy » et attendez que SWAG soit pleinement opérationnel.
::note
Nous partons ici du principe que le nom du réseau d'upsnap est `upsnap_default`. Vous pouvez vérifier la connexion dans le tableau de bord de SWAG sur `http://ipdevotreserveur:81`.
`host-gateway` est une valeur spéciale que Docker résout automatiquement vers l'IP de la machine hôte, donc cela fonctionne quelle que soit l'adresse réelle de votre serveur.
::
### Créer le fichier subdomain.conf
@@ -184,7 +177,7 @@ server {
include /config/nginx/proxy.conf;
include /config/nginx/resolver.conf;
set $upstream_app upsnap;
set $upstream_app host.docker.internal;
set $upstream_port 8095;
set $upstream_proto http;
proxy_pass $upstream_proto://$upstream_app:$upstream_port;
@@ -262,7 +255,7 @@ server {
include /config/nginx/proxy.conf;
include /config/nginx/resolver.conf;
set $upstream_app upsnap;
set $upstream_app host.docker.internal;
set $upstream_port 8095;
set $upstream_proto http;
proxy_pass $upstream_proto://$upstream_app:$upstream_port;
+2 -2
View File
@@ -44,7 +44,7 @@ tree:
Créez les dossiers `movies`, `tvseries` et `library` dans `/media` :
```bash [Terminal]
mkdir -p /media/movies /media/library /media/tvseries
mkdir -p /media/movies /media/tvseries /media/library
```
### Déployer la stack
@@ -124,7 +124,7 @@ Si vos médias sont stockés sur un disque réseau (un NAS ou un disque dur exte
## Transcodage matériel
Jellyfin réencode la vidéo à la volée dès qu'un client ne peut pas lire un fichier tel quel : la résolution de l'écran de l'appareil est inférieure à celle de la source, sa connexion réseau est trop lente pour le débit du fichier, ou il ne prend pas en charge le codec, le format HDR ou le type de sous-titres du fichier. C'est ce qu'on appelle le **transcodage**. Lorsque le transcodage est logiciel et éxecuté par le CPU, cela prend énormément de ressources et cela peut saturer un serveur modeste avec seulement un ou deux flux simultanés. Le **transcodage matériel** délègue ce travail au GPU intégré à votre processeur (Intel QuickSync, sur la plupart du matériel de homelab), qui s'en occupe bien plus vite et laisse le CPU libre pour tout le reste.
Jellyfin réencode la vidéo à la volée dès qu'un client ne peut pas lire un fichier tel quel : la résolution de l'écran de l'appareil est inférieure à celle de la source, sa connexion réseau est trop lente pour le débit du fichier, ou il ne prend pas en charge le codec, le format HDR ou le type de sous-titres du fichier. C'est ce qu'on appelle le **transcodage**. Lorsque le transcodage est logiciel et exécuté par le CPU, cela prend énormément de ressources et cela peut saturer un serveur modeste avec seulement un ou deux flux simultanés. Le **transcodage matériel** délègue ce travail au GPU intégré à votre processeur (Intel QuickSync, sur la plupart du matériel de homelab), qui s'en occupe bien plus vite et laisse le CPU libre pour tout le reste.
Le **tone mapping** est une fonction liée mais distincte : convertir une vidéo HDR (qui a besoin d'un écran HDR compatible pour rendre correctement) en SDR pour qu'elle s'affiche correctement sur un écran, une TV ou un client qui ne gère pas le HDR, au lieu de paraître délavée ou trop sombre.
@@ -10,8 +10,8 @@ description: Installer qBittorrent avec Gluetun et ProtonVPN pour télécharger
Afin de télécharger vos media favoris en toute sécurité, nous allons monter un système à base de :
- [Qbittorent](https://github.com/linuxserver/docker-qbittorrent) comme logiciel de téléchargement bittorent
- [Proton VPN Plus](https://protonvpn.com/torrenting), VPN pour sécuriser vos échanges, auquel vous devez souscrire (il y a de nombreux codes promo) pour accéder au protocole Bittorent, mais vous pouvez également en choisir un autre, à condition qu'il propose le protocole bittorent.
- [qBittorrent](https://github.com/linuxserver/docker-qbittorrent) comme logiciel de téléchargement BitTorrent
- [Proton VPN Plus](https://protonvpn.com/torrenting), VPN pour sécuriser vos échanges, auquel vous devez souscrire (il y a de nombreux codes promo) pour accéder au protocole BitTorrent, mais vous pouvez également en choisir un autre, à condition qu'il propose le protocole BitTorrent.
- [Gluetun](https://github.com/qdm12/gluetun)
- [qBittorrent port update](https://codeberg.org/TechnoSam/qbittorrent-gluetun-port-update) pour mettre automatiquement à jour le port de votre VPN (qui change régulièrement).
- Et le mode [vuetorrent](https://github.com/gabe565/linuxserver-mod-vuetorrent) pour une interface moderne et intuitive.
@@ -47,7 +47,7 @@ tree:
Si ce n'est pas déjà fait, créez le dossier `downloads` dans `/media` :
```bash [Terminal]
mkdir -P /media/downloads
mkdir -p /media/downloads
```
### Déployer la stack
@@ -88,7 +88,7 @@ services:
devices:
- /dev/net/tun:/dev/net/tun
ports:
- ${UI_PORT}:5695 # Port de la web-ui
- ${UI_PORT}:${UI_PORT} # Port de la web-ui
- 8000:8000 # Port de controle de Gluetun
cap_add:
- NET_ADMIN
@@ -321,7 +321,7 @@ server {
include /config/nginx/proxy.conf;
include /config/nginx/resolver.conf;
set $upstream_app gluetun;
set $upstream_port 5555;
set $upstream_port 5695;
set $upstream_proto http;
proxy_pass $upstream_proto://$upstream_app:$upstream_port;
@@ -399,7 +399,7 @@ server {
include /config/nginx/proxy.conf;
include /config/nginx/resolver.conf;
set $upstream_app gluetun;
set $upstream_port 5555;
set $upstream_port 5695;
set $upstream_proto http;
proxy_pass $upstream_proto://$upstream_app:$upstream_port;
+3 -3
View File
@@ -133,8 +133,8 @@ services:
container_name: bazarr
restart: unless-stopped
environment:
- PUID=1000
- PGID=1000
- PUID=${PUID}
- PGID=${PGID}
- TZ=Europe/Paris
volumes:
- /srv/docker/bazarr/config:/config
@@ -394,7 +394,7 @@ Seerr n'a pas d'authentification à deux facteurs intégrée. Ne l'exposez que s
::note
Nous partons du principe que vous avez le sous-domaine `films.mondomaine.fr` avec un `CNAME` pointant vers `films.fr` dans votre [zone DNS](/general/networking/dns). Et que, [à moins d'utiliser Cloudflare Zero Trust](/serveex/security/cloudflare), le port `443` de votre box est redirigé vers le port `443` de votre serveur via les [règles NAT](/general/networking/nat).
Nous partons du principe que vous avez le sous-domaine `films.mondomaine.fr` avec un `CNAME` pointant vers `mondomaine.fr` dans votre [zone DNS](/general/networking/dns). Et que, [à moins d'utiliser Cloudflare Zero Trust](/serveex/security/cloudflare), le port `443` de votre box est redirigé vers le port `443` de votre serveur via les [règles NAT](/general/networking/nat).
::
::steps{level="3"}
@@ -89,7 +89,6 @@ Montez chaque dossier listé sous `sources` dans `config.yaml` au même chemin
filebrowser-quantum:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
```
::
@@ -53,13 +53,11 @@ services:
pingvin-share:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
clamav:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
```
::
@@ -63,7 +63,6 @@ services:
code-server:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
```
::
@@ -144,7 +143,7 @@ services:
networks: # Définit le réseau personnalisé
# ...
code-server: # Nom du réseau défini dans la stack
name: code-serveur # Nom réel du réseau externe
name: code-server_default # Nom réel du réseau externe
external: true # Indique qu'il s'agit d'un réseau externe
```
@@ -36,7 +36,6 @@ services:
it-tools:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
```
::
+2 -2
View File
@@ -25,7 +25,7 @@ AdGuard lui, va s'intercaler entre le serveur de nom et votre appareil. Si vous
- Si le domaine n'est pas dans une blocklist, il contactera des serveurs de noms génériques (dit upstreams) et répondra vers vos appareils avec l'adresse IP recherchée.
- Si le domaine est dans une blocklist, il ne contactera pas les DNS upstream et ne répondra pas à vos appareils. Le contenu affilié à cette requête ne s'affichera pas.
C'est ainsi que les pubs et domaines malveillants sont bloqués : leurs domaines sont présents dans la blocklist, le reste de la page lui charge correctement.
C'est ainsi que les pubs et domaines malveillants sont bloqués : leurs domaines sont présents dans la blocklist, le reste de la page se charge correctement.
![Schéma d'AdGuard filtrant une requête DNS selon une liste de blocage](/img/serveex/adguard.svg)
@@ -360,7 +360,7 @@ Le chiffrement est essentiel si vous souhaitez garder privées les requêtes que
Afin de configurer le chiffrement :
- Allez dans _paramètre_ puis dans _chiffrement_.
- Allez dans _paramètres_ puis dans _chiffrement_.
- Paramétrez comme suit
![Écran des réglages de chiffrement d'AdGuard Home](/img/serveex/adguard-chiffrement.png)
@@ -460,7 +460,6 @@ authentik_host_insecure: false
container_image:
docker_network: null
docker_map_ports: true
docker_labels: null
```
Enregistrez avec :kbd{value="Ctrl+O"}, puis :kbd{value="Enter"}, et quittez avec :kbd{value="Ctrl+X"}.
@@ -476,7 +475,7 @@ Sur votre machine distante, utilisez [Dockge](/serveex/core/docker/#installer-do
Si vous n'avez pas installé [Dockge](/serveex/core/docker/#installer-dockge-pour-gérer-et-déployer-les-conteneurs), créez un dossier `/srv/docker/authentik-outpost`, ou directement en ligne de commande :
```bash [Terminal]
sudo mkdir -P /srv/docker/authentik-outpost
sudo mkdir -p /srv/docker/authentik-outpost
```
::tip{icon="" to="/serveex/files/file-browser-quantum"}
@@ -0,0 +1,253 @@
---
title: Backrest
description: Installer Backrest, une interface web conviviale pour restic, et sauvegarder son serveur comme il faut avec la règle 3-2-1, vers un disque local, un autre serveur, S3 ou Backblaze B2.
---
:ellipsis{left=0px width=40rem top=10rem blur=140px zIndex=60}
Soyons honnêtes deux secondes : la "stratégie de sauvegarde" de la plupart des homelabbers, c'est avoir copié quelques dossiers sur une clé USB une fois en 2019, et espérer que tout ira bien. [Backrest](https://github.com/garethgeorge/backrest) est là pour arranger ça, sans vous forcer à apprendre un outil en ligne de commande qui fait peur.
Sous le capot, Backrest est une interface web propre posée sur [restic](https://restic.net/), un moteur de sauvegarde open-source qui a fait ses preuves. Restic fait le vrai travail (chiffrer, dédupliquer, et envoyer vos données là où vous le lui dites) ; Backrest vous donne des boutons et des formulaires plutôt qu'un mur d'options à retenir.
![Tableau de bord de Backrest, montrant plusieurs dépôts et leur activité de sauvegarde récente](/img/serveex/backrest-dashboard.png)
## La règle du 3-2-1, ou pourquoi une seule sauvegarde n'en est pas une
Avant d'installer quoi que ce soit, parlons de la règle qui compte vraiment ici, parce qu'une sauvegarde mal pensée vous donne une fausse confiance, ce qui est pire que pas de sauvegarde du tout.
La **règle du 3-2-1** dit :
- **3** copies de vos données : l'originale, plus au moins deux sauvegardes.
- **2** types de stockage différents : pas deux copies sur le même disque, ni sur deux disques dans la même machine.
- **1** copie hors site : physiquement ailleurs, pas dans la même pièce, la même maison ou le même bâtiment que l'original.
Chaque chiffre ferme un scénario de panne précis :
- Une seule **(1)** sauvegarde ? Une seule erreur (un `rm -rf` malheureux, une restauration ratée, un fichier corrompu copié par-dessus le bon sans que vous le voyiez) peut emporter votre seul filet de sécurité en même temps que l'original.
- Des sauvegardes sur le **même type de stockage** (disons, un second disque interne dans le même serveur) ? Une surtension, un bug de firmware, ou une alimentation bas de gamme qui lâche peuvent très bien emporter tous les disques du boîtier d'un coup.
- Pas de copie **hors site** ? Un incendie, une inondation, un vol, ou "j'ai débranché la mauvaise multiprise" se moquent du nombre de disques que vous avez, s'ils sont tous dans la même pièce.
C'est aussi exactement pour ça que [le RAID n'est pas une sauvegarde](/general/storage/raid) : le RAID garde un service en marche quand un disque meurt, il ne fait rien contre un ransomware qui chiffre tous les fichiers qu'il peut atteindre, une suppression malheureuse, ou votre maison qui prend feu. Backrest, pointé vers une destination en dehors de votre serveur, est ce qui couvre réellement ces cas-là.
## Ce que Backrest sauvegarde, et où
Deux concepts à connaître avant de cliquer partout :
- Un **dépôt** (repository) est la destination : un espace de stockage chiffré et dédupliqué. C'est votre "2" et votre "1" de la règle ci-dessus, un disque externe, un autre serveur, ou du stockage cloud.
- Un **plan** est la règle que vous définissez : quels dossiers sauvegarder, vers quel dépôt, selon quel planning, et combien d'anciens instantanés (snapshots) conserver.
Vous pouvez avoir plusieurs plans sauvegardant vers plusieurs dépôts en même temps, ce qui est exactement comment on construit un vrai 3-2-1 : un plan vers un dépôt local pour des restaurations rapides, un autre plan vers un dépôt hors site pour le scénario "ma maison brûle".
## Installation
::file-tree
---
tree:
/:
- srv:
- docker:
- backrest:
- data/
- config/
- cache/
- compose.yaml
---
::
::steps{level="3"}
### Déployer la stack
Ouvrez Dockge, cliquez sur `compose`, nommez la stack `backrest`, et collez ce qui suit :
```yaml [compose.yaml]
---
services:
backrest:
image: garethgeorge/backrest:latest
container_name: backrest
restart: unless-stopped
ports:
- 9898:9898
volumes:
- ./data:/data
- ./config:/config
- ./cache:/cache
# Tout ce que vous voulez que Backrest puisse sauvegarder doit
# aussi être monté ici : la stack ne voit que ce qu'on lui donne.
- /srv/docker:/userdata/docker:ro
- /etc:/userdata/etc:ro
- /home:/userdata/home:ro
environment:
- BACKREST_DATA=/data
- BACKREST_CONFIG=/config/config.json
- XDG_CACHE_HOME=/cache
- TZ=Europe/Paris
```
Les lignes `/srv/docker`, `/etc` et `/home` ci-dessus couvrent ce qui vaut réellement la peine d'être sauvegardé hors site sur un serveur homelab, selon [dossiers et partitions](/general/linux/filesystem) : `/srv/docker` contient la config et les données de chaque stack (bases de données, fichiers uploadés, le coffre de Vaultwarden, les utilisateurs de Pocket ID, etc.), `/etc` contient votre configuration système (le durcissement SSH du [guide d'installation](/serveex/core/installation#refermer-la-porte-derrière-vous), vos fichiers `.subdomain.conf` de SWAG, les unités systemd), et `/home` contient vos propres scripts et notes. Les trois sont montées en lecture seule, un outil de sauvegarde n'a aucune raison d'écrire dans ce qu'il sauvegarde.
Ce qui ne vaut généralement **pas** le coup : une grosse bibliothèque média ou un dossier de téléchargement torrent sur un disque de données séparé. C'est souvent énorme, remplaçable, et rarement justifié de payer du stockage cloud ou de la bande passante SSH pour le protéger.
::tip{icon=""}
__Astuce :__ ajoutez le label Watchtower pour automatiser les mises à jour
```yaml [compose.yaml]
services:
backrest:
#...
labels:
- com.centurylinklabs.watchtower.enable=true
```
::
Déployez le conteneur, puis ouvrez `http://ipdevotreserveur:9898`. La première visite vous demande de définir un identifiant et un mot de passe administrateur : faites-le immédiatement, Backrest n'a pas de compte par défaut et l'écran de configuration est grand ouvert tant que vous ne l'avez pas fait.
### Terminé !
::
## Créer votre premier dépôt
![Formulaire "Add Restic Repository" de Backrest, montrant une URI de dépôt Backblaze B2](/img/serveex/backrest.png)
Dans Backrest, allez dans **Add Repo**. Le formulaire est découpé en plusieurs sections, voici ce que fait chaque champ :
- **Repo Name** : ce qui vous aidera à le reconnaître plus tard, `cle-usb` ou `vps-hors-site` par exemple. Impossible de le renommer ensuite, choisissez quelque chose que vous ne regretterez pas.
- **Auto Unlock** : laissez désactivé sauf si vous comprenez bien ce que ça fait. Restic verrouille un dépôt pendant qu'il y travaille, pour qu'un second processus ne corrompe pas tout en écrivant en même temps. Auto Unlock retire ce verrou automatiquement au démarrage, pratique si Backrest a planté en pleine sauvegarde et laissé un verrou fantôme, mais réellement dangereux si deux machines écrivent un jour dans le même dépôt en même temps. Pour la configuration mono-serveur de cet article, c'est un confort mineur ; laissez désactivé en cas de doute.
- **Shared** : ne concerne que la fonctionnalité multihost de Backrest (plusieurs de vos machines gérant la même configuration de dépôt). Ignorez-le pour un serveur unique.
- **Repository URI** : là où les données vivent réellement. C'est ce champ qui change pour chaque destination ci-dessous.
- **Password** : le mot de passe de chiffrement de ce dépôt, cliquez sur **Generate** pour en générer un solide aléatoirement. **Conservez-le quelque part en dehors de ce serveur**, un gestionnaire de mots de passe, une note sur votre téléphone, n'importe où sauf un fichier texte posé à côté des sauvegardes qu'il protège. Perdez-le, et chaque sauvegarde devient un tas de bruit illisible et coûteux, sans exception, même pour les développeurs de restic.
- **Env Vars** : là où vous collerez les identifiants pour les destinations qui en ont besoin (S3 et B2 plus bas). Un disque local et le SFTP n'en ont besoin d'aucun.
::note
Les onglets **Scheduling**, **Hooks** et **Advanced** de ce formulaire configurent la maintenance du dépôt dans son ensemble (purge des anciennes données, vérification d'intégrité, notifications) plutôt que quoi que ce soit de spécifique à une destination. Ils sont couverts à la fin de cet article, une fois que vous avez un dépôt qui fonctionne réellement.
::
### Sauvegarder vers un disque local ou une clé USB
La copie hors site la plus simple qui soit est un disque que vous déplacez physiquement ailleurs après chaque sauvegarde, ou le disque d'une seconde machine joint par le réseau. Dans les deux cas, du point de vue de Backrest c'est juste un dossier, donc la configuration est identique : branchez le disque (ou montez le partage réseau) sur l'hôte, ajoutez-le aux volumes du fichier compose comme vous l'avez fait pour `/srv/docker` plus haut, puis dans le champ Repository URI, utilisez le chemin tel qu'il apparaît **à l'intérieur du conteneur** :
```text
/userdata/disque-sauvegarde
```
Voilà, aucun identifiant, aucune variable d'environnement. C'est aussi le dépôt le plus rapide pour restaurer, puisqu'il n'y a aucun aller-retour réseau, ce qui en fait un excellent choix pour votre copie de "récupération rapide", accompagnée d'une vraie copie hors site ci-dessous pour le scénario "ma maison brûle".
::caution
__Si ça ne marche pas :__ le chemin doit exister et être accessible en écriture par le conteneur avant de valider le formulaire. Un dossier vide convient très bien, restic initialise lui-même la structure du dépôt à la première utilisation.
::
### Sauvegarder vers un autre serveur
Pas de compte cloud, pas de problème : si vous avez un accès SSH à une autre machine, le serveur d'un ami, un petit VPS pas cher, un Raspberry Pi chez de la famille, c'est un dépôt hors site parfaitement valable, et ça ne coûte que ce que cette machine vous coûte déjà.
D'abord, assurez-vous que ce serveur peut se connecter en SSH à l'autre sans taper de mot de passe à chaque fois :
```bash [Terminal]
ssh-keygen -t ed25519 -f /srv/docker/backrest/config/id_ed25519 -N ""
ssh-copy-id -i /srv/docker/backrest/config/id_ed25519.pub votreutilisateur@lautreserveur
```
Montez cette clé dans le conteneur en l'ajoutant aux volumes du fichier compose :
```yaml [compose.yaml]
volumes:
# ...
- ./config/id_ed25519:/root/.ssh/id_ed25519:ro
```
Redéployez la stack, puis dans Backrest utilisez :
```text
sftp:votreutilisateur@lautreserveur:/chemin/vers/les/sauvegardes
```
::caution
__Si ça ne marche pas :__ le dossier cible (`/chemin/vers/les/sauvegardes` ci-dessus) doit déjà exister sur l'autre serveur, et cet utilisateur doit avoir le droit d'y écrire. Connectez-vous une fois à la main (`ssh votreutilisateur@lautreserveur`) pour confirmer que la connexion fonctionne et accepter la clé de l'hôte, Backrest tournant dans un conteneur n'aura pas l'invite interactive pour ça.
::
## Avancé : stockage objet dans le cloud
Un disque local ou le serveur de secours d'un ami couvre très bien la règle du 3-2-1, et ne coûte rien de plus que ce que vous possédez déjà. Le stockage objet dans le cloud est l'autre option classique, intéressante quand vous voulez une copie hors site qui ne dépend pas du matériel de quelqu'un d'autre restant allumé, pour un coût de quelques centimes à quelques euros par mois selon ce que vous sauvegardez.
### Backblaze B2
[Backblaze B2](https://www.backblaze.com/cloud-storage) est du stockage objet pensé exactement pour cet usage, et c'est généralement l'option la moins chère pour le schéma "on écrit souvent, on lit rarement" d'une sauvegarde.
Créez un bucket dans votre compte Backblaze, puis générez une **clé d'application** limitée à celui-ci. Dans Backrest, utilisez :
```text
b2:nom-de-votre-bucket:backrest
```
Avec les variables d'environnement suivantes :
| Variable | Valeur |
|----------|-------|
| `B2_ACCOUNT_ID` | L'identifiant de la clé d'application |
| `B2_ACCOUNT_KEY` | La clé d'application elle-même |
### Stockage compatible S3
S3 n'est pas juste un truc Amazon, c'est un protocole de stockage que la plupart des fournisseurs cloud parlent (OVH, Scaleway, MinIO si vous auto-hébergez le vôtre, et bien d'autres), ce qui en fait un choix solide et portable si vous préférez ne pas dépendre d'un fournisseur en particulier.
Créez un bucket chez le fournisseur de votre choix, puis dans le champ Repository URI de Backrest, utilisez :
```text
s3:https://s3.votre-fournisseur.com/nom-de-votre-bucket/backrest
```
Pour du vrai AWS S3, retirez le endpoint personnalisé :
```text
s3:s3.amazonaws.com/nom-de-votre-bucket/backrest
```
Avec les variables d'environnement suivantes :
| Variable | Valeur |
|----------|-------|
| `AWS_ACCESS_KEY_ID` | La clé d'accès de votre fournisseur |
| `AWS_SECRET_ACCESS_KEY` | La clé secrète de votre fournisseur |
::note
Générez ces clés depuis le tableau de bord de votre fournisseur, généralement sous un intitulé du genre "Clés API" ou "Identifiants S3", limitées à ce seul bucket si le fournisseur le permet. Il n'y a aucune raison que la clé d'un job de sauvegarde puisse toucher à autre chose sur votre compte.
::
### Maintenance du dépôt (optionnel, mais à mettre en place une fois pour toutes)
Retour dans l'onglet **Scheduling**, trois politiques gardent un dépôt en bonne santé dans le temps. Aucune n'est nécessaire pour commencer à sauvegarder, restic fonctionne très bien sans jamais y toucher, mais elles valent la peine d'être comprises une fois que votre dépôt tourne depuis un moment :
:::collapsible{name="les trois politiques de maintenance"}
- **Prune Policy** : supprime les données qui ne sont plus référencées par aucun instantané (parce que les anciens instantanés qui les contenaient ont été oubliés, voir la politique de rétention plus bas). C'est la seule opération qui libère réellement de l'espace sur votre stockage. C'est lent et ça lit beaucoup de données, donc planifiez-la rarement, une fois par mois est la suggestion de Backrest lui-même. **Max Unused After Prune** contrôle à quel point c'est minutieux : un pourcentage plus élevé laisse plus de données inutilisées derrière mais termine plus vite et copie moins.
- **Check Policy** : vérifie que votre dépôt n'est pas silencieusement corrompu. **Read Data %** contrôle quelle proportion des données réellement sauvegardées est relue et vérifiée par somme de contrôle, pas juste la structure interne du dépôt. 100% signifie relire l'intégralité du dépôt, ce qui consomme de la bande passante et du temps réels ; un pourcentage plus faible vérifie un échantillon aléatoire à la place. Une fois par mois est, encore une fois, un défaut raisonnable.
- **Forget Policy** : une règle de rétention optionnelle pour tout le dépôt, appliquée à travers tous les plans qui y écrivent au lieu d'être par plan. Laissez-la désactivée sauf si vous voulez spécifiquement une seule politique de rétention partagée par plusieurs plans, elle désactive la politique de rétention propre à chaque plan dès que vous l'activez.
Chacune de ces politiques a un **Schedule Type** : `Disabled`, un simple `Interval` en heures ou en jours, ou une `Cron Expression` pour quelque chose de plus précis, plus une **Reference Clock** (l'heure locale de votre serveur, UTC, ou relative à la dernière exécution) pour ancrer ce planning.
:::
## Créer un plan de sauvegarde
Retour dans Backrest, allez dans **Add Plan**. Ce formulaire couvre quoi sauvegarder et quand, contrairement au formulaire de dépôt ci-dessus, qui ne couvre que où :
- **Plan Name** : même règle que le nom du dépôt, choisissez quelque chose de clair, impossible à changer ensuite.
- **Repository** : celui que vous venez de créer plus haut.
- **Paths** : cliquez sur **Add** pour ajouter une ligne, puis tapez le chemin côté conteneur de ce que vous avez monté plus haut, c'est un champ texte, mais il autocomplète les vrais chemins du système de fichiers du conteneur au fur et à mesure, pratique pour confirmer qu'un montage a bien atterri là où vous pensez. `/userdata/docker` pour vos stacks, `/userdata/etc` pour votre config système, `/userdata/home` pour vos propres fichiers. Cliquez à nouveau sur **Add** pour chaque dossier supplémentaire, le petit bouton `-` retire une ligne dont vous n'avez plus besoin.
- **Excludes** et **Excludes (Case Insensitive)** : des motifs à ignorer au sein de ces chemins, pratique pour les dossiers de cache ou tout ce qui est vraiment jetable et qui gonflerait chaque instantané pour rien.
- **Schedule Type** : les trois mêmes choix que les plannings du dépôt ci-dessus, `Disabled`, un `Interval`, ou une `Cron Expression`. Un cron nocturne du type `0 3 * * *` (tous les jours à 3h du matin) est un défaut raisonnable pour un homelab.
- **Retention Policy** : combien d'instantanés conserver, et pendant combien de temps. **By Time Period** vous permet de dire "garder 7 quotidiens, 4 hebdomadaires, 6 mensuels" indépendamment, ce qui vous donne largement assez de points de restauration étalés dans le temps sans que le dépôt grossisse indéfiniment, puisque restic déduplique de toute façon les données inchangées entre les instantanés. **By Count** conserve à la place simplement les N derniers instantanés, quel que soit leur âge. **Latest (Count)** en plus de l'un ou l'autre mode garantit qu'un nombre minimum d'instantanés récents survit toujours, quoi que dise le reste de la politique.
- **Advanced** : **Backup Flags** vous permet de passer des options supplémentaires directement à la commande `restic backup` sous-jacente pour tout ce que ce formulaire n'expose pas ; **Hooks** exécute des scripts ou envoie des notifications sur les événements de sauvegarde, le même mécanisme que l'onglet Hooks du dépôt, mais limité à ce seul plan au lieu de tous les plans utilisant le dépôt.
Cette politique de rétention est d'ailleurs votre vraie défense contre les ransomwares : si quelque chose commence à chiffrer vos fichiers à 2h du matin, la sauvegarde de ce soir est compromise, mais celle de la semaine dernière ne l'est pas, et restic vous permet de restaurer depuis n'importe laquelle d'entre elles.
::tip{icon="" to="/nonsense/bash/backrest-docker-stop"}
__Pour aller plus loin :__ si ce que vous sauvegardez inclut une base de données en cours d'exécution, arrêter son conteneur le temps des quelques secondes que prend la sauvegarde est plus sûr que de la sauvegarder pendant qu'elle écrit. Voir **Backrest Docker Stop** pour un script qui fait exactement ça, déclenché automatiquement par Backrest lui-même.
::
## Restaurer une sauvegarde
Une sauvegarde qu'on n'a jamais essayé de restaurer est un pari, pas un plan, ça vaut le coup de le faire une fois avant d'en avoir vraiment besoin. Ouvrez le plan, cliquez sur un instantané, dépliez **Snapshot Browser** jusqu'à ce dont vous avez besoin, puis cliquez sur le menu **...** à côté et choisissez **Restore to path**.
Laissez le champ de chemin vide et Backrest l'envoie directement vers les téléchargements de votre navigateur, l'option la plus simple pour récupérer un seul fichier. Tapez un chemin et Backrest écrit plutôt les données restaurées dans le conteneur à cet endroit, et il pré-remplit un dossier temporaire du type `/userdata-backrest-restore-<id du snapshot>`, volontairement pas votre montage d'origine.
Ce choix par défaut n'est pas un hasard : `/srv/docker`, `/etc` et `/home` sont montés en `:ro`, donc restic ne peut pas y réécrire, restaurer directement dans `/userdata/docker` échoue avec une erreur de système de fichiers en lecture seule. Restaurez vers ce dossier temporaire suggéré (ou téléchargez à la place), vérifiez ce que vous avez récupéré, puis recopiez les fichiers à leur vraie place vous-même avec `sudo cp -a`, depuis l'hôte, en dehors de Backrest. Une étape de plus, mais ça garantit aussi qu'une restauration ne peut jamais écraser silencieusement des données en cours d'utilisation, exactement la prudence qu'on veut en plein incident.
Et voilà, vous avez maintenant une vraie stratégie de sauvegarde plutôt qu'un dossier appelé `sauvegarde_finale_v2_LAVRAIE`.
@@ -0,0 +1,169 @@
---
title: Snapshots BTRFS
description: Formater la partition racine de Debian en BTRFS et utiliser Snapper pour annuler instantanément une mise à jour ratée ou un mauvais changement de config, en complément local des sauvegardes 3-2-1 hors site de Backrest.
---
:ellipsis{left=0px width=40rem top=10rem blur=140px zIndex=60}
[BTRFS](https://btrfs.readthedocs.io/) est un système de fichiers Linux avec une fonctionnalité redoutable pour un homelab : les **snapshots**. Un snapshot fige l'état exact d'un système de fichiers en un instant, à coût quasi nul, sans copier le moindre octet de données au départ. Cassez quelque chose dix minutes après un `apt full-upgrade`, ou écrasez le mauvais fichier `.env`, et vous pouvez revenir exactement à l'état d'avant, sans toucher à une sauvegarde.
Ce n'est pas le rôle de [Backrest et de la règle 3-2-1](/serveex/advanced/backrest), donc autant être précis sur la différence avant de mettre quoi que ce soit en place.
## Un snapshot n'est pas une sauvegarde
Un snapshot vit sur le même disque que les données qu'il protège. Il est instantané, ne demande aucun réseau, et il est parfait pour annuler une bêtise que vous venez de faire, mais il ne sert strictement à rien le jour où ce disque lâche, se fait voler, ou où votre serveur part en fumée. C'est le rôle d'une vraie [sauvegarde 3-2-1](/serveex/advanced/backrest) : une copie sur un support différent, idéalement hors site.
Voyez ça comme ça :
- **Snapshot** = un bouton annuler. Instantané, local, gratuit, utile seulement tant que le disque est vivant.
- **Sauvegarde** = une assurance. Plus lente, hors site, la seule chose qui survit à la mort du disque lui-même.
Gardez les deux. Les snapshots vous rendent serein face aux mises à jour et aux expérimentations, les sauvegardes garantissent qu'un disque mort reste un désagrément plutôt qu'une catastrophe.
::note{to="/serveex/core/installation#partitionnement"}
Ce guide suppose que la partition racine a été formatée en Btrfs pendant [l'installation de Debian](/serveex/core/installation#partitionnement). Btrfs ne peut pas être ajouté proprement à un `/` déjà en ext4 après coup, c'est donc un choix à faire une seule fois, à l'installation.
::
## Formater la partition racine en BTRFS
Le partitionnement *Assisté* de Debian ne propose que de l'ext4. Pour obtenir du Btrfs, choisissez plutôt le partitionnement *Manuel*, à la même étape que décrit [le guide d'installation principal](/serveex/core/installation#partitionnement) :
::steps{level="3"}
### Sélectionner le partitionnement manuel
Sur l'écran de méthode de partitionnement, choisissez *Manuel* plutôt que *Assisté, utiliser un disque entier*.
### Créer une table de partitions
Sélectionnez le disque, confirmez la création d'une nouvelle table de partitions vide, puis sélectionnez l'*ESPACE LIBRE* obtenu et choisissez *Créer une nouvelle partition*.
### Définir la taille et le type de la partition
Donnez à la partition le reste du disque (moins une petite partition EFI si vous êtes en UEFI, gérée comme dans une installation Assistée), et réglez *Utiliser comme* sur __Système de fichiers journalisé Btrfs__, avec comme point de montage `/`.
### Terminer le partitionnement
*Terminer le partitionnement et appliquer les changements*, puis confirmez avec *Oui*.
### Terminé !
::
Tout le reste de [l'installeur](/serveex/core/installation#installer-debian) reste identique.
## Installer Snapper
Plutôt que de jongler à la main avec des commandes `btrfs subvolume` brutes, [Snapper](https://github.com/openSUSE/snapper) est un petit outil qui gère tout le cycle de vie des snapshots : les créer, les ranger proprement, supprimer les anciens, et encadrer automatiquement chaque opération `apt` d'une paire de snapshots.
```bash [Terminal]
sudo apt install snapper
sudo snapper -c root create-config /
```
`create-config` enregistre une configuration nommée `root` pour le système de fichiers `/`, et crée un sous-volume `.snapshots` dédié en dessous pour y stocker chaque snapshot, verrouillé pour root uniquement. Pas besoin de découpage `@`/`@home`, ça fonctionne très bien sur le layout à sous-volume unique que le partitionnement manuel vient de créer.
Activez la configuration en éditant `/etc/default/snapper` :
```properties [/etc/default/snapper]
SNAPPER_CONFIGS="root"
```
Puis activez les timers qui exécutent les snapshots périodiques et le nettoyage de Snapper :
```bash [Terminal]
sudo systemctl enable --now snapper-timeline.timer snapper-cleanup.timer
```
`snapper-timeline.timer` se déclenche **toutes les heures** par défaut, c'est fixé par l'unité elle-même, pas par une option de configuration. Chaque exécution prend un snapshot et le range dans la bonne catégorie (horaire, quotidien, mensuel, annuel) ; les réglages `TIMELINE_LIMIT_*` vus plus bas ne contrôlent que combien de snapshots de chaque catégorie survivent, pas la fréquence à laquelle ils sont pris. `snapper-cleanup.timer` tourne une fois par jour (plus une fois 10 minutes après le démarrage) pour appliquer ces limites.
::tip
✨ Pour prendre des snapshots de chronologie à une fréquence différente, par exemple toutes les 6 heures plutôt que toutes les heures, surchargez le timer plutôt que de modifier directement le fichier d'unité du paquet :
```bash [Terminal]
sudo systemctl edit snapper-timeline.timer
```
```ini [override.conf]
[Timer]
OnCalendar=
OnCalendar=*-*-* 0/6:00:00
```
La ligne `OnCalendar=` vide efface d'abord la valeur `hourly` du paquet, puisque systemd ajoute sinon les nouvelles lignes `OnCalendar` à celles déjà présentes au lieu de les remplacer. Appliquez avec `sudo systemctl daemon-reload && sudo systemctl restart snapper-timeline.timer`.
::
::note
Le paquet Debian embarque aussi un hook APT (`/etc/apt/apt.conf.d/80snapper`) qui s'active dès qu'une configuration figure dans `SNAPPER_CONFIGS` : à partir de maintenant, chaque `apt install`, `apt upgrade` ou `apt full-upgrade` obtient automatiquement un snapshot juste avant et juste après son exécution, sans aucun effort de votre part.
::
## Prendre un snapshot
Pour tout ce qui sort du cadre d'apt, comme modifier une unité systemd ou un fichier Docker Compose, prenez-en un vous-même avec une description qui voudra vraiment dire quelque chose plus tard :
```bash [Terminal]
sudo snapper create --description "avant changement compose sur swag"
```
Listez-les tous avec :
```bash [Terminal]
sudo snapper list
```
```console [Output]
# | Type | Pre # | Date | Description
---+--------+-------+--------------------------+---------------------------------
0 | single | | | current
1 | single | | Tue 09 Sep 2026 18:30:00 | avant changement compose sur swag
2 | pre | | Tue 09 Sep 2026 19:00:01 | apt install unattended-upgrades
3 | post | 2 | Tue 09 Sep 2026 19:00:14 | apt install unattended-upgrades
```
## Restaurer des fichiers depuis un snapshot
Snapper conserve l'état complet du système de fichiers au moment du snapshot sous `/.snapshots/<numéro>/snapshot`, consultable comme n'importe quel autre dossier :
```bash [Terminal]
ls /.snapshots/1/snapshot/etc/ssh/
```
Pour voir exactement ce qui a changé entre un snapshot et le système actuel (`0` désigne toujours "l'état actuel") avant de toucher à quoi que ce soit :
```bash [Terminal]
sudo snapper status 1..0
```
Ça affiche chaque fichier créé, modifié ou supprimé depuis. Pour annuler ces changements automatiquement :
```bash [Terminal]
sudo snapper undochange 1..0
```
Ou restaurez un seul fichier à la main, souvent le choix le plus sûr et le plus chirurgical :
```bash [Terminal]
sudo cp -a /.snapshots/1/snapshot/etc/ssh/sshd_config /etc/ssh/sshd_config
```
::note
Ça couvre l'immense majorité des vrais accidents de homelab : une mauvaise config, un fichier supprimé, une mise à jour de paquet qui a cassé un truc. Snapper peut aussi faire un `rollback` de toute la partition racine vers un snapshot antérieur (il crée un nouveau sous-volume par défaut et démarre dessus au prochain redémarrage), pour un système dans un état vraiment cassé plutôt qu'un simple fichier manquant. C'est une opération plus délicate et bien plus rare, à tester une fois sur une machine où redémarrer ne vous dérange pas, avant d'en avoir vraiment besoin. Et si le disque lui-même est le problème, c'est exactement le scénario pour lequel votre sauvegarde [Backrest](/serveex/advanced/backrest) hors site existe.
::
## Gérer et nettoyer les snapshots
Les snapshots sont bon marché, pas gratuits : dès que le système de fichiers actif diverge d'un snapshot, les anciens blocs qu'il référence toujours restent occupés. Sans surveillance, des mois de snapshots sur un serveur qui change beaucoup (images de conteneurs, logs) peuvent discrètement grignoter de l'espace disque réel.
Le `snapper-cleanup.timer` activé plus haut nettoie déjà automatiquement, selon la configuration de `/etc/snapper/configs/root` :
| Réglage | Défaut | Ce que ça fait |
|---------|---------|---------------|
| `TIMELINE_LIMIT_HOURLY` / `_DAILY` / `_MONTHLY` / `_YEARLY` | `10` | Combien de snapshots de chronologie garder pour chaque granularité |
| `TIMELINE_LIMIT_WEEKLY` | `0` | Désactivé par défaut |
| `NUMBER_LIMIT` | `50` | Combien de snapshots manuels (`single`) garder |
Ajustez ça à votre goût, puis supprimez-en un immédiatement à la main si vous avez besoin de la place tout de suite :
```bash [Terminal]
sudo snapper delete 1
```
Vérifiez l'usage disque réel avec `df -h /` : les chiffres ci-dessus ne plafonnent que le nombre de snapshots, pas l'espace qu'un serveur très actif peut encore consommer entre deux nettoyages.
Et voilà : un bouton annuler automatique et permanent pour votre serveur, qui encadre discrètement chaque mise à jour et se nettoie tout seul, en tournant à côté des vraies sauvegardes que Backrest prend déjà hors site.
+1 -1
View File
@@ -1,5 +1,5 @@
---
title: Introduction
title: Stockeex
description: Introduction à Stockeex, un projet personnel de gestion de stock et d'inventaire. Documentation en cours de rédaction.
navigation:
icon: i-lucide-bookmark
+1 -1
View File
@@ -9,7 +9,7 @@ navigation:
:ellipsis{left=0px width=40rem top=10rem blur=140px zIndex=60}
## Scripts et projets annexes
Cette section rassemble mes projets Python et Bash écrits en chemin : des scripts qui automatisent une des usages précis, répond à des besoins particuliers, créés au fil du temps. Vous les trouverez peut-être utiles, les voici en vrac.
Cette section rassemble mes projets Python et Bash écrits en chemin : des scripts qui automatisent un des usages précis, répondent à des besoins particuliers, créés au fil du temps. Vous les trouverez peut-être utiles, les voici en vrac.
### Python
@@ -6,11 +6,11 @@ description: Un bot Python qui surveille la disponibilité des GPU en temps rée
:ellipsis{left=0px width=40rem top=10rem blur=140px zIndex=60}
Depuis déjà 4 ans, la pénurie de materiel electronique fait rage. Et les cartes graphiques ne sont pas épargnées. En 2020, j'ai du attendre 2 mois pour obtenir mon exemplaire de RTX 3080, et pour cela j'ai du m'inscrire sur [JV Hardware](https://discord.gg/gxffg3GA96) où une poignée de geek avait mis en place un bot qui envoyait un ping lorsqu'elles étaient disponibles.
Depuis déjà 4 ans, la pénurie de materiel electronique fait rage. Et les cartes graphiques ne sont pas épargnées. En 2020, j'ai dû attendre 2 mois pour obtenir mon exemplaire de RTX 3080, et pour cela j'ai dû m'inscrire sur [JV Hardware](https://discord.gg/gxffg3GA96) où une poignée de geek avait mis en place un bot qui envoyait un ping lorsqu'elles étaient disponibles.
4 ans après et 5000 abonnés plus tard, vient la sortie des RTX 5000. Et là aucun bot dispo sur le marché ne semble fonctionner correctement. Je ne parle même pas d'un certain "influenceur" qui se permet de faire payer l'accès à son bot qui ne fonctionne meme pas. Il copie à la main les alertes provenant d'autres serveurs, comme le notre qui ont résolu le problème.
4 ans après et 5000 abonnés plus tard, vient la sortie des RTX 5000. Et là aucun bot dispo sur le marché ne semble fonctionner correctement. Je ne parle même pas d'un certain "influenceur" qui se permet de faire payer l'accès à son bot qui ne fonctionne même pas. Il copie à la main les alertes provenant d'autres serveurs, comme le nôtre qui ont résolu le problème.
Quoiqu'il en soit, désireux d'obtenir une RTX 5090 pour ma machine dédiée à l'IA, je me suis dit qu'il était peut etre le temps de plonger dans le monde de python et de ChatGPT pour m'épauler. A l'aide d'un autre membre du serveur, KevOut, qui a principalement guidé sur le principe de départ et les sources des différentes API, j'ai réussi à obtenir un bot propre, fonctionnel, qui envoie différents types d'alertes via Discord. Avec un simple conteneur docker à déployer.
Quoiqu'il en soit, désireux d'obtenir une RTX 5090 pour ma machine dédiée à l'IA, je me suis dit qu'il était peuttre le temps de plonger dans le monde de python et de ChatGPT pour m'épauler. A l'aide d'un autre membre du serveur, KevOut, qui a principalement guidé sur le principe de départ et les sources des différentes API, j'ai réussi à obtenir un bot propre, fonctionnel, qui envoie différents types d'alertes via Discord. Avec un simple conteneur docker à déployer.
Après moult déconvenues, je suis passé de ceci :
@@ -6,21 +6,21 @@ description: Un script Python pour synchroniser automatiquement les listes CIDR
:ellipsis{left=0px width=40rem top=10rem blur=140px zIndex=60}
AdGuard Home est une solution merveilleuse pour filter ses requêtes DNS et ainsi se débarasser de la publicité ou des DNS des fournisseurs d'accès, ou encore réécrire des requetes.
AdGuard Home est une solution merveilleuse pour filtrer ses requêtes DNS et ainsi se débarrasser de la publicité ou des DNS des fournisseurs d'accès, ou encore réécrire des requêtes.
Quand c'est en local, c'est très chouette. Mais quand on veut que tout ses appareils en profitent même à l'exterieur, on est obligé de l'exposer sur le net. Et n'importe qui peut s'en servir et saturer le petit remote à 1€ qu'on a pris pour l'heberger.
Quand c'est en local, c'est très chouette. Mais quand on veut que tous ses appareils en profitent même à l'extérieur, on est obligé de l'exposer sur le net. Et n'importe qui peut s'en servir et saturer le petit remote à 1€ qu'on a pris pour l'héberger.
AdGuard permet d'avoir des listes de clients autorisés ou bloqués. Problème, pour autoriser un client il faut son IP, et dans le cas d'un téléphone sur le réseau mobile, beh elle change régulièrement. L'idée est donc plutot de bloquer des listes générales plutot que d'autoriser des IP qui de toute façon changent régulièrement.
AdGuard permet d'avoir des listes de clients autorisés ou bloqués. Problème, pour autoriser un client il faut son IP, et dans le cas d'un téléphone sur le réseau mobile, beh elle change régulièrement. L'idée est donc plutôt de bloquer des listes générales plutôt que d'autoriser des IP qui de toute façon changent régulièrement.
CIDRE est un outil qui permet de synchroniser des listes de plages IP géolocalisées mises à jour régulièrement avec un pare feu. Plutot que de faire tourner CIDRE sur le remote complet avec des règles de pare feu complexes, je me suis dit qu'il fallait simplement s'arranger pour ajouter les plages IP à jour que CIDRE propose au systeme de block list d'AdGuard, selon les pays que l'on souhaite bloquer.
CIDRE est un outil qui permet de synchroniser des listes de plages IP géolocalisées mises à jour régulièrement avec un pare feu. Plutôt que de faire tourner CIDRE sur le remote complet avec des règles de pare-feu complexes, je me suis dit qu'il fallait simplement s'arranger pour ajouter les plages IP à jour que CIDRE propose au système de block list d'AdGuard, selon les pays que l'on souhaite bloquer.
C'est ainsi qu'est né AdGuard CIDRE Sync, un conteneur qui synchronise régulièrement la block list d'AdGuard avec les plages IP recensées par CIDRE à la fréquence que vous voulez.
L'idée etant de :
L'idée étant de :
- Backup le fichier de conf d'AdGuard au premier lancement (le fichier jamais touché par le robot est ainsi conservé au cas où)
- Télécharger la liste des pays selectionnés via une variable d'environnement
- Permettre d'ajouter soi-meme des IP "à la main" dans un fichier
- Télécharger la liste des pays sélectionnés via une variable d'environnement
- Permettre d'ajouter soi-même des IP "à la main" dans un fichier
- Concaténer le tout, backup le fichier de conf (dernière update), et injecter la liste dans la bonne section du fichier de conf d'AdGuard
- Recharger AdGuard en relançant le container (accès au socket via docker socket proxy pour limiter les permissions)
@@ -28,6 +28,6 @@ Tout ceci de manière complètement autonome, avec une fréquence choisie en var
Plus d'infos directement sur le repo :
::card{title="🐋 __AdGuard CIDRE Sync__"}
[Robot de synchronisation de la blocklist d'AdGuard](https://git.djeex.fr/Djeex/adguard-cidre)
::card{title="🐋 __AdGuard CIDRE Sync__" to="https://git.djeex.fr/Djeex/adguard-cidre" target="_blank"}
Robot de synchronisation de la blocklist d'AdGuard
::
@@ -25,7 +25,7 @@ Je me suis alors inspiré d'un [fork du premier projet](https://github.com/kosti
En gros, voilà ce que donne mon workflow à présent pour poster sur Insta :
![Instameex](/img/nonsense/instameex-workflow.svg)
![Workflow Instameex](/img/nonsense/instameex-workflow.svg)
Je vous présente donc **Instam[eex]{style="color: #1ad6ff"}**
@@ -6,7 +6,7 @@ description: Un script bash pour détecter et corriger les fichiers médias en d
:ellipsis{left=0px width=40rem top=10rem blur=140px zIndex=60}
Six mois après avoir téléchargé des térabytes de media, je me suis rendu compte que Sonarr et Radarr les copaient dans ma biblio Plex au lieu de créer des hardlinks. C'est dû à un mécanisme contre intuitif qui est que si vous montez plusieurs dossiers dans Sonarr/Radarr, il les voit comme deux systemes de fichiers différents. Et ne peut donc pas créer de hardlinks. C'est pour cela qu'il ne faut monter qu'un seul dossier parent, qui contient tous les enfants (`downloads`, `movies`, `tvseries` dans le dossier parent `media` par exemple).
Six mois après avoir téléchargé des térabytes de media, je me suis rendu compte que Sonarr et Radarr les copaient dans ma biblio Plex au lieu de créer des hardlinks. C'est dû à un mécanisme contre intuitif qui est que si vous montez plusieurs dossiers dans Sonarr/Radarr, il les voit comme deux systèmes de fichiers différents. Et ne peut donc pas créer de hardlinks. C'est pour cela qu'il ne faut monter qu'un seul dossier parent, qui contient tous les enfants (`downloads`, `movies`, `tvseries` dans le dossier parent `media` par exemple).
J'ai donc restructuré mes dossiers, remis à la main chaque chemin dans qBittorrent, Plex, et autres. Il restait à trouver un moyen de détecter les doublons existants et d'automatiquement les supprimer et de créer des hardlinks à la place, pour économiser de l'espace.
@@ -29,7 +29,7 @@ Mes dossiers originaux sont dans `seedbox`, et il ne faut surtout pas les modifi
L'idée est donc de :
- lister les originaux dans seedbox
- lister les fichiers dans movies
- lister les fichiers dans movies et tvseries
- comparer les deux listes et isoler les chemins des doublons
- supprimer les doublons
- hardlinker les originaux dans les dossiers des doublons supprimés
+25 -25
View File
@@ -6,80 +6,80 @@ description: Un script bash pour extraire automatiquement les headers LUKS de to
:ellipsis{left=0px width=40rem top=10rem blur=140px zIndex=60}
Je me suis rendu compte il y a peu qu'il ne suffisait pas d'avoir le mot de passe pour deverouiller un volume luks apres une panne ou une corruption. J'ai ainsi appris à dump les headers luks des disques/volumes et à utiliser les numéros de série + noms de partitions pour pouvoir bien identifier quel header correspond à quel disque/partition (j'en ai 10 !).
Je me suis rendu compte il y a peu qu'il ne suffisait pas d'avoir le mot de passe pour déverrouiller un volume luks après une panne ou une corruption. J'ai ainsi appris à dump les headers luks des disques/volumes et à utiliser les numéros de série + noms de partitions pour pouvoir bien identifier quel header correspond à quel disque/partition (j'en ai 10 !).
Après avoir bien galéré à la main, j'avoue avoir demandé à Qwen3 (llm hebergé sur ma RTX 5090) de me faire un script qui automatise le listing et identification des disques, dump les headers et les stock dans une archive chiffrée prete à etre backupée sur mon serveur de sauvegarde.
Après avoir bien galéré à la main, j'avoue avoir demandé à Qwen3 (llm hébergé sur ma RTX 5090) de me faire un script qui automatise le listing et identification des disques, dump les headers et les stocke dans une archive chiffrée prête à être sauvegardée sur mon serveur de sauvegarde.
Ainsi, ce script :
* Liste et identifie les disques avec leur numéro de série
* Liste les partition
* Liste les partitions
* Dump les headers dans un dossier dans `/root` (dossier sécurisé)
* Cree une archive temporaire
* Crée une archive temporaire
* Prompt pour saisir un mot de passe
* Chiffre avec le mot de passe
* Détruit l'archive non chiffrée
```
```bash [Terminal]
#!/bin/bash
# Directory where LUKS headers will be backed up
# Dossier où seront sauvegardés les headers LUKS
DEST="/root/luks-headers-backup"
mkdir -p "$DEST"
echo "🔍 Searching for LUKS containers on all partitions..."
echo "🔍 Recherche des conteneurs LUKS sur toutes les partitions..."
# Loop through all possible disk partitions (including NVMe and SATA)
# Parcourt toutes les partitions disque possibles (y compris NVMe et SATA)
for part in /dev/sd? /dev/sd?? /dev/nvme?n?p?; do
# Skip if the device doesn't exist
# Ignore si le périphérique n'existe pas
if [ ! -b "$part" ]; then
continue
fi
# Check if the partition is a LUKS encrypted volume
# Vérifie si la partition est un volume chiffré LUKS
if cryptsetup isLuks "$part"; then
# Find the parent disk device (e.g. nvme0n1p4 → nvme0n1)
# Trouve le disque parent (ex. nvme0n1p4 → nvme0n1)
disk=$(lsblk -no pkname "$part" | head -n 1)
full_disk="/dev/$disk"
# Get the serial number of the parent disk
# Récupère le numéro de série du disque parent
SERIAL=$(udevadm info --query=all --name="$full_disk" | grep ID_SERIAL= | cut -d= -f2)
if [ -z "$SERIAL" ]; then
SERIAL="unknown"
fi
# Extract the partition name (e.g. nvme0n1p4)
# Extrait le nom de la partition (ex. nvme0n1p4)
PART_NAME=$(basename "$part")
# Build the output filename with partition name and disk serial
# Construit le nom du fichier de sortie avec le nom de partition et le numéro de série
OUTPUT="$DEST/luks-header-${PART_NAME}__${SERIAL}.img"
echo "🔐 Backing up LUKS header of $part (Serial: $SERIAL)..."
echo "🔐 Sauvegarde du header LUKS de $part (Numéro de série : $SERIAL)..."
# Backup the LUKS header to the output file
# Sauvegarde le header LUKS dans le fichier de sortie
cryptsetup luksHeaderBackup "$part" --header-backup-file "$OUTPUT"
if [[ $? -eq 0 ]]; then
echo "✅ Backup successful → $OUTPUT"
echo "✅ Sauvegarde réussie → $OUTPUT"
else
echo "❌ Backup failed for $part"
echo "❌ Échec de la sauvegarde pour $part"
fi
fi
done
# Create a timestamped compressed tar archive of all header backups
# Crée une archive tar compressée et horodatée de toutes les sauvegardes de headers
ARCHIVE_NAME="/root/luks-headers-$(date +%Y%m%d_%H%M%S).tar.gz"
echo "📦 Creating archive $ARCHIVE_NAME..."
echo "📦 Création de l'archive $ARCHIVE_NAME..."
tar -czf "$ARCHIVE_NAME" -C "$DEST" .
# Encrypt the archive symmetrically using GPG with AES256 cipher
echo "🔐 Encrypting the archive with GPG..."
# Chiffre l'archive symétriquement avec GPG et le chiffrement AES256
echo "🔐 Chiffrement de l'archive avec GPG..."
gpg --symmetric --cipher-algo AES256 "$ARCHIVE_NAME"
if [[ $? -eq 0 ]]; then
echo "✅ Encrypted archive created: ${ARCHIVE_NAME}.gpg"
# Remove the unencrypted archive for security
echo "✅ Archive chiffrée créée : ${ARCHIVE_NAME}.gpg"
# Supprime l'archive non chiffrée pour plus de sécurité
rm -f "$ARCHIVE_NAME"
else
echo "❌ Encryption failed"
echo "❌ Échec du chiffrement"
fi
```
@@ -8,18 +8,18 @@ description: Utiliser socat pour proxifier le socket Docker via Docker Socket Pr
Ce projet répond à un cas d'usage problématique :
- J'ai [Beszel](https://beszel.dev/), un conteneur de monitoring en mode host, nécessitant d'exposer le socket de Docker afin qu'il récupère les stats des conteneurs
- Afin de ne pas laisser le socket complètement ouvert pour Beszel, j'ai [Docker Socket Proxy](https://github.com/Tecnativa/docker-socket-proxy), un conteneur qui se place entre le scoket de docker et le conteneur qui en a besoin, et qui filtre le requêtes en paramétrant les bonnes permissions pour ne pas tout exposer au conteneur qui l'utilise.
- Afin de ne pas laisser le socket complètement ouvert pour Beszel, j'ai [Docker Socket Proxy](https://github.com/Tecnativa/docker-socket-proxy), un conteneur qui se place entre le socket de docker et le conteneur qui en a besoin, et qui filtre les requêtes en paramétrant les bonnes permissions pour ne pas tout exposer au conteneur qui l'utilise.
Problème, si __Beszel__ est en mode host, il doit contacter __Docker Socket Proxy__ directement sur un port de l'host, c'est à dire en exposant un port de __Docker Socket Proxy__. Ce qui fait que n'importe quel conteneur/application sur mon host peut l'appeler et utiliser le socket docker.
C'est là qu'intervient [Socat Proxy](https://git.djeex.fr/Djeex/socat-proxy). Ce dernier est un conteneur qui :
- Crée un socket UNIX
- Ecoute ce socket
- Envoie les requetes vers Docker Socket Proxy et vice versa
- Écoute ce socket
- Envoie les requêtes vers Docker Socket Proxy et vice versa
- Permet de remplacer le vrai socket docker en exposant le socket proxy créé, dans le conteneur final via un bind mount (ici, Beszel)
Ainsi, un filtre comme Docker Socket Proxy dialogue avec Socat Proxy dans leur propre réseau isolé (en mode bridge), et le bind mount du socket UNIX créé est localisé sur l'host dans un dossier avec les permissions nécessaires pour ne pas etre visible des autres conteneurs/applicatifs.
Ainsi, un filtre comme Docker Socket Proxy dialogue avec Socat Proxy dans leur propre réseau isolé (en mode bridge), et le bind mount du socket UNIX créé est localisé sur l'host dans un dossier avec les permissions nécessaires pour ne pas être visible des autres conteneurs/applicatifs.
En gros :
@@ -77,6 +77,6 @@ services:
Plus d'infos directement sur le repo :
::card{title="🐋 __Socat Proxy__"}
[A lighteweight bind mount socket proxy](https://git.djeex.fr/Djeex/socat-proxy)
::card{title="🐋 __Socat Proxy__" to="https://git.djeex.fr/Djeex/socat-proxy" target="_blank"}
Un proxy de socket léger basé sur un bind mount
::
+2 -2
View File
@@ -8,7 +8,7 @@ description: Un script bash qui surveille la température des disques durs et é
Quand on a un NAS avec plusieurs disques dans une buanderie, les températures peuvent vite grimper.
Un disque dur est très sensible à la chaleur et peut subir de gros dommages s'il dépasse une température seuil trop longtemps.
Après un été très chaud qui a fournit son lot de sueur froide en regardant la température de mes disques, j'ai cherché un moyen de pouvoir automatiser l'extinction du serveur en cas de dépassement prolonger de la température maximale supportée par mes disques.
Après un été très chaud qui a fourni son lot de sueur froide en regardant la température de mes disques, j'ai cherché un moyen de pouvoir automatiser l'extinction du serveur en cas de dépassement prolongé de la température maximale supportée par mes disques.
N'ayant rien trouvé de convaincant, je l'ai donc fait moi-même.
@@ -34,7 +34,7 @@ Le script d'installation permet aussi de régler différents paramètres :
Il exécute aussi un autre script qui paramètre **logrotate** avec les éléments configurés précédemment.
Et enfin, le script d'installation peut être exécuté directement via un simple `curl` suivi d'un dernier script de configuration, parfait pour les plus flemmards.
Il a fallu également gérer le sujet du root sans sudo, du sudo seul, de l'utilisateur sans sudo, les divers cas d'erreur (dépendances manquantes, erreur dans les permissions, créations de fichier, de lecture des données des disques, etc...)
Il a fallu également gérer le sujet du root sans sudo, du sudo seul, de l'utilisateur sans sudo, les divers cas d'erreur (dépendances manquantes, erreur dans les permissions, créations de fichier, de lecture des données des disques, etc.)
Et l'acces concurrent au fichier de statuts.
@@ -8,16 +8,16 @@ description: Un script bash qui arrête les conteneurs Docker avant une sauvegar
[Backrest](https://github.com/garethgeorge/backrest) est un formidable outil de backup. Dans le cas de [Serveex](/serveex/introduction), la majeure partie des données à sauvegarder sont des conteneurs, et souvent ces conteneurs possèdent des bases de données.
Le problème ? On ne peut pas sauvegarder proprement une BDD qui est en route. Alors, il existe plein de solutions complexe à base de dump des bases de données, mais souvent le plus simple cela reste de stopper les conteneurs, de sauvegarder, et de redémarrer les conteneurs.
Le problème ? On ne peut pas sauvegarder proprement une BDD qui est en route. Alors, il existe plein de solutions complexes à base de dump des bases de données, mais souvent le plus simple cela reste de stopper les conteneurs, de sauvegarder, et de redémarrer les conteneurs.
**Backrest** ne propose pas de solutions native, mais il propose d'executer des scripts customisés à déclencher sur des évenements, comme le démarrage et la fin de la sauvegarde par exemple. Notre besoin est donc de stopper les conteneurs dont on veut sauvegarder la BDD, à chaque démarrage du plan de sauvegarde, et de les redémarrer à la fin de l'execution du plan de sauvegarde. Pour cela nous allons avoir besoin d'un script bash et d'une connexion sécurisée entre Backrest et le socket de Docker, afin d'avoir la cinématique suivante :
**Backrest** ne propose pas de solutions natives, mais il propose d'exécuter des scripts customisés à déclencher sur des événements, comme le démarrage et la fin de la sauvegarde par exemple. Notre besoin est donc de stopper les conteneurs dont on veut sauvegarder la BDD, à chaque démarrage du plan de sauvegarde, et de les redémarrer à la fin de l'exécution du plan de sauvegarde. Pour cela nous allons avoir besoin d'un script bash et d'une connexion sécurisée entre Backrest et le socket de Docker, afin d'avoir la cinématique suivante :
- Le plan de sauvegarde se met en route
- L'evenement déclenche l'execution d'un script custom
- L'événement déclenche l'exécution d'un script custom
- Le script contacte docker et demande la liste des conteneurs qui comportent le label `backrest.backup.stop=true`
- Il récupère cette liste et leur envoie une commande d'extinction
- Le plan de sauvegarde s'arrête
- L'evenement déclenche l'execution d'un script custom
- L'événement déclenche l'exécution d'un script custom
- Le script recontacte docker, récupère la même liste, et redémarre ces conteneurs
## Faire communiquer Backrest et Docker en toute sécurité
@@ -67,7 +67,7 @@ Et voilà, Backrest pourra ainsi communiquer avec Docker en toute sécurité.
## Les scripts
Vous trouverez ci-dessous les scripts à renseigner en action pour les évèvenements de démarrage et d'arrêt de la sauvegarde dans **Backrest**.
Vous trouverez ci-dessous les scripts à renseigner en action pour les événements de démarrage et d'arrêt de la sauvegarde dans **Backrest**.
::code-group
```sh [Stop]
+1 -1
View File
@@ -1,2 +1,2 @@
title: Poubelle
title: Recyclage
icon: i-noto-recycling-symbol
+2 -2
View File
@@ -1,5 +1,5 @@
---
title: Poubelle
title: Recyclage
description: Des tutoriels obsolètes gardés pour référence, et des applications alternatives remplacées ailleurs sur le site mais qui fonctionnent toujours très bien.
navigation:
icon: i-lucide-bookmark
@@ -9,7 +9,7 @@ navigation:
:ellipsis{left=0px width=40rem top=10rem blur=140px zIndex=60}
## Le grenier
Au fil des mois et années, certaines solutions deviennent obsolètes. Soit parce qu'elles ne sont plus maintenues, soit parce qu'elles ont trouvé de meilleurs remplaçants. Cette section les gardes au cas où vous les trouveriez parfaitement valables, même si ce ne sont pas celles que [Serveex](/serveex/introduction) recommande aujourd'hui. Rien ici n'est activement maintenu.
Au fil des mois et années, certaines solutions deviennent obsolètes. Soit parce qu'elles ne sont plus maintenues, soit parce qu'elles ont trouvé de meilleurs remplaçants. Cette section les garde au cas où vous les trouveriez parfaitement valables, même si ce ne sont pas celles que [Serveex](/serveex/introduction) recommande aujourd'hui. Rien ici n'est activement maintenu.
### Obsolète
@@ -12,11 +12,11 @@ wg-easy 15 est devenu bien plus compliqué, « not so easy » dirait-on. C'est j
::
## Introduction
L'utilisation d'un VPN permet d'accéder à distance aux ressources locales du serveur sans les exposer sur internet. C'est notamment une manière propre de sécuriser l'accès à la console SSH, plutot que d'exposer le port sur internet. C'est pouvoir se connecter à son réseau où que l'on soit, de maniere sécurisée, et de faire dialoguer des machines qui sont sur des réseaux différents.
L'utilisation d'un VPN permet d'accéder à distance aux ressources locales du serveur sans les exposer sur internet. C'est notamment une manière propre de sécuriser l'accès à la console SSH, plutôt que d'exposer le port sur internet. C'est pouvoir se connecter à son réseau où que l'on soit, de manière sécurisée, et de faire dialoguer des machines qui sont sur des réseaux différents.
Ici nous utiliserons [WireGuard](https://www.wireguard.com/), un serveur VPN sécurisé et très performant, à l'aide des conteneurs :
- [wg-easy](https://github.com/wg-easy/wg-easy) pour le serveur, qui propose une interface web très simple pour controler les connexions et télécharger les fichiers de conf (notamment par QR code pour les téléphones)
- [wg-easy](https://github.com/wg-easy/wg-easy) pour le serveur, qui propose une interface web très simple pour contrôler les connexions et télécharger les fichiers de conf (notamment par QR code pour les téléphones)
- [WireGuard](https://docs.linuxserver.io/images/docker-wireguard/?h=wireguard) pour les clients Linux
Il existe aussi des clients Windows, macOS, iOS et Android.
@@ -24,13 +24,13 @@ Il existe aussi des clients Windows, macOS, iOS et Android.
Le principe est le suivant :
- Sur internet, n'importe qui peut contacter n'importe quel box internet et donc essayer de contacter n'importe quel serveur exposé.
- Votre serveur est sur votre réseau local. Il est accessible depuis le réseau local mais pas depuis internet, mis à part les services exposés (comme nous l'avons fait avec Dockge). Pour accéder aux ressources non exposées, vous devez être connecté sur le meme réseau que votre serveur et donc etre chez vous. De plus, vous devez laisser ouvert les ports utilisés par vos services à travers le pare feu de votre serveur.
- Nous souhaitons ici au contraire, depuis n'importe où, pouvoir accéder de maniere securisée aux services non exposés sur internet du serveur, comme la console SSH qui permet de se connecter à la machine par exemple.
- Nous souhaitons aussi accéder aux services d'autres serveurs, et par exemple relier de maniere sécurisée deux instances de Dockge pour tout controler depuis la meme interface.
- Votre serveur est sur votre réseau local. Il est accessible depuis le réseau local mais pas depuis internet, mis à part les services exposés (comme nous l'avons fait avec Dockge). Pour accéder aux ressources non exposées, vous devez être connecté sur le même réseau que votre serveur et donc être chez vous. De plus, vous devez laisser ouverts les ports utilisés par vos services à travers le pare-feu de votre serveur.
- Nous souhaitons ici au contraire, depuis n'importe où, pouvoir accéder de manière sécurisée aux services non exposés sur internet du serveur, comme la console SSH qui permet de se connecter à la machine par exemple.
- Nous souhaitons aussi accéder aux services d'autres serveurs, et par exemple relier de manière sécurisée deux instances de Dockge pour tout contrôler depuis la même interface.
Pour cela nous allons créer un **réseau privé virtuel**, ou VPN, c'est à dire un tunnel sécurisé auquel personne n'a accès à part les machines que vous relierez entre elles. Elles feront partie d'un nouveau réseau et pourront dialoguer entre elle comme dans un réseau local.
D'autre part, vous pourrez ajouter votre téléphone, un ordinateur portable ou n'importe quel appareil au réseau pour pouvoir utiliser vos ressources depuis vos appareils quotidiens, où que vous soyiez.
D'autre part, vous pourrez ajouter votre téléphone, un ordinateur portable ou n'importe quel appareil au réseau pour pouvoir utiliser vos ressources depuis vos appareils quotidiens, où que vous soyez.
![Schéma d'un tunnel VPN reliant un appareil distant au réseau domestique](/img/serveex/vpn.svg)
@@ -39,7 +39,7 @@ Dans cette illustration, la machine 1 est sur deux réseaux :
- son réseau local (tous les appareils liés à la box, avec une adresse IP du type `192.168.x.x ` donc ici la machine 1 et la machine 2)
- le réseau du VPN (tous les appareils reliés au VPN, avec une seconde adresse IP du type `10.8.x.x` donc ici la machine 1 et 4)
On peut aussi faire en sorte que les machines reliées au réseau virtuel partagent les acces à leur réseau local. Ici nous ne le ferons pas, pour des raisons de sécurité, et de complexité en terme de sous-réseau (si les deux machines distantes ont des machines locales qui utilisent la meme adresse IP locale, par exemple `192.168.1.1`, cela posera des conflits).
On peut aussi faire en sorte que les machines reliées au réseau virtuel partagent les accès à leur réseau local. Ici nous ne le ferons pas, pour des raisons de sécurité, et de complexité en termes de sous-réseau (si les deux machines distantes ont des machines locales qui utilisent la même adresse IP locale, par exemple `192.168.1.1`, cela posera des conflits).
Ainsi, sur le réseau virtuel, seules les machines directement reliées pourront dialoguer entre elle depuis ce réseau. Elles ne pourront pas dialoguer avec une machine situées sur un autre réseau local et non reliée au VPN.
@@ -263,7 +263,7 @@ Répétez pour chaque client
::warning
__Attention :__ si un appareil client est sur le même réseau local que le serveur, modifiez `wg0.conf` et remplacez l'endpoint par l'IP locale du serveur :
`Endpoint = ip-de-votre-serveur:51820`
`Endpoint = ipdevotreserveur:51820`
::
Et voici le résultat :
@@ -1,6 +1,6 @@
---
title: File Browser
description: Installer File Browser pour parcourir et gérer les fichiers de votre serveur depuis une interface web, exposée en toute sécurité avec SWAG.
description: Ancien guide File Browser conservé à titre archivé, voir le guide File Browser Quantum pour une installation actuelle.
---
@@ -1,6 +1,6 @@
---
title: Plex
description: Installer Plex Media Server avec Tautulli sur votre homelab pour diffuser films et séries depuis n'importe où sur tous vos appareils.
description: Ancien guide Plex Media Server conservé à titre archivé, voir le guide Jellyfin pour une installation actuelle.
---
@@ -8,7 +8,7 @@ description: Installer Plex Media Server avec Tautulli sur votre homelab pour di
::note{to="/serveex/media/jellyfin"}
C'est une alternative à **Jellyfin**, conservée ici pour référence. Plex n'est pas entièrement auto-hébergé : même la lecture locale passe par le relais de Plex et exige un compte Plex, et plusieurs fonctions sont derrière le paywall du Plex Pass.
C'est une alternative à **Jellyfin**, conservée ici pour référence. Plex n'est pas entièrement auto-hébergé : il exige un compte Plex même pour la lecture locale, l'accès à distance peut basculer sur le relais de Plex si une connexion directe échoue, et plusieurs fonctions sont derrière le paywall du Plex Pass.
::
[Plex](https://www.plex.tv/fr/) est une plateforme de streaming vidéo auto-hébergée pour gérer votre bibliothèque de films ou de séries et les lire en local ou à distance. Plex propose des applications pour TV, Android, iOS, Windows et macOS, permettant de diffuser votre bibliothèque comme sur Netflix.
@@ -1,6 +1,6 @@
---
title: qBittorrent pour Plex
description: Installer qBittorrent avec Gluetun et ProtonVPN pour télécharger des torrents de manière sécurisée derrière un VPN sur votre serveur auto-hébergé.
description: Ancien guide qBittorrent pour Plex conservé à titre archivé, voir le guide qBittorrent à jour pour une installation actuelle.
---
@@ -15,8 +15,8 @@ C'est l'installation de la seedbox associée à Plex plutôt qu'à Jellyfin, con
Afin de télécharger vos media favoris en toute sécurité, nous allons monter un système à base de :
- [Qbittorent](https://github.com/linuxserver/docker-qbittorrent) comme logiciel de téléchargement bittorent
- [Proton VPN Plus](https://protonvpn.com/torrenting), VPN pour sécuriser vos échanges, auquel vous devez souscrire (il y a de nombreux codes promo) pour accéder au protocole Bittorent, mais vous pouvez également en choisir un autre, à condition qu'il propose le protocole bittorent.
- [qBittorrent](https://github.com/linuxserver/docker-qbittorrent) comme logiciel de téléchargement BitTorrent
- [Proton VPN Plus](https://protonvpn.com/torrenting), VPN pour sécuriser vos échanges, auquel vous devez souscrire (il y a de nombreux codes promo) pour accéder au protocole BitTorrent, mais vous pouvez également en choisir un autre, à condition qu'il propose le protocole BitTorrent.
- [Gluetun](https://github.com/qdm12/gluetun)
- [qBittorrent port update](https://codeberg.org/TechnoSam/qbittorrent-gluetun-port-update) pour mettre automatiquement à jour le port de votre VPN (qui change régulièrement).
- Et le mode [vuetorrent](https://github.com/gabe565/linuxserver-mod-vuetorrent) pour une interface moderne et intuitive.
@@ -52,7 +52,7 @@ tree:
Si ce n'est pas déjà fait, créez le dossier `downloads` dans `/media` :
```bash [Terminal]
mkdir -P /media/downloads
mkdir -p /media/downloads
```
### Déployer la stack
@@ -93,7 +93,7 @@ services:
devices:
- /dev/net/tun:/dev/net/tun
ports:
- ${UI_PORT}:5695 # Port de la web-ui
- ${UI_PORT}:${UI_PORT} # Port de la web-ui
- 8000:8000 # Port de controle de Gluetun
cap_add:
- NET_ADMIN
@@ -206,7 +206,7 @@ Une fois fait, déployez le conteneur.
### Se connecter et sécuriser son compte
Connectez-vous sur `http://ipduserveur:5695` (ou le port que vous avez défini).
Connectez-vous sur `http://ipdevotreserveur:5695` (ou le port que vous avez défini).
::caution
@@ -262,7 +262,7 @@ Cliquez sur « Deploy » et attendez que SWAG soit complètement initialisé.
::note
Nous partons du principe que le nom du réseau est `seedbox_default`. Vous pouvez le confirmer en consultant le tableau de bord de SWAG sur http://ipduserveur:81.
Nous partons du principe que le nom du réseau est `seedbox_default`. Vous pouvez le confirmer en consultant le tableau de bord de SWAG sur http://ipdevotreserveur:81.
::
### Créer le fichier subdomain.conf
@@ -322,7 +322,7 @@ server {
include /config/nginx/proxy.conf;
include /config/nginx/resolver.conf;
set $upstream_app gluetun;
set $upstream_port 5555;
set $upstream_port 5695;
set $upstream_proto http;
proxy_pass $upstream_proto://$upstream_app:$upstream_port;
@@ -1,6 +1,6 @@
---
title: Servarr pour Plex
description: Automatiser les téléchargements de médias avec la suite Servarr, Radarr, Sonarr, Bazarr, Prowlarr et Overseerr pour les films et les séries.
description: Ancien guide Servarr pour Plex conservé à titre archivé, voir le guide Servarr à jour pour une installation actuelle.
---
@@ -415,7 +415,7 @@ Il peut être utile d'exposer Overseerr si vous voulez envoyer des demandes depu
::note
Nous partons du principe que vous avez le sous-domaine `films.mondomaine.fr` avec un `CNAME` pointant vers `films.fr` dans votre [zone DNS](/general/networking/dns). Et que, [à moins d'utiliser Cloudflare Zero Trust](/serveex/security/cloudflare), le port `443` de votre box est redirigé vers le port `443` de votre serveur via les [règles NAT](/general/networking/nat).
Nous partons du principe que vous avez le sous-domaine `films.mondomaine.fr` avec un `CNAME` pointant vers `mondomaine.fr` dans votre [zone DNS](/general/networking/dns). Et que, [à moins d'utiliser Cloudflare Zero Trust](/serveex/security/cloudflare), le port `443` de votre box est redirigé vers le port `443` de votre serveur via les [règles NAT](/general/networking/nat).
::
::steps{level="3"}
@@ -1,6 +1,6 @@
---
title: Gitea
description: Installer Gitea, un service Git auto-hébergé et léger pour gérer vos dépôts de code en privé sur votre propre serveur.
description: Ancien guide Gitea conservé à titre archivé, voir le guide Forgejo pour une installation actuelle.
---
+2 -2
View File
@@ -25,7 +25,7 @@ seo:
---
color: primary
size: xl
to: /fr/about/welcome
to: /about/welcome/
---
Accéder à la doc
::::::
@@ -55,7 +55,7 @@ class: my-0!
ui:
icon: text-[#1ad6ff]
---
Jetez un oeil à mes âneries
Jetez un œil à mes âneries
:::::
:::::card
Binary file not shown.

After

Width:  |  Height:  |  Size: 341 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 96 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 114 KiB

After

Width:  |  Height:  |  Size: 51 KiB

File diff suppressed because one or more lines are too long

After

Width:  |  Height:  |  Size: 31 KiB

File diff suppressed because one or more lines are too long

After

Width:  |  Height:  |  Size: 34 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 135 KiB

After

Width:  |  Height:  |  Size: 80 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 137 KiB

After

Width:  |  Height:  |  Size: 141 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 91 KiB

After

Width:  |  Height:  |  Size: 31 KiB

File diff suppressed because one or more lines are too long

After

Width:  |  Height:  |  Size: 30 KiB

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 81 KiB

After

Width:  |  Height:  |  Size: 68 KiB