mirror of
https://github.com/vhaudiquet/homeprod.git
synced 2026-05-08 17:47:24 +00:00
Compare commits
35 Commits
901a5e1a9a
...
dependabot
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
427e45f625 | ||
|
d5831fd1e3
|
|||
| cbf7842e8b | |||
| 0d5d688c18 | |||
|
|
de093a27bf | ||
|
|
2f615136c2 | ||
|
|
98359d5181 | ||
|
|
0d57085ba6 | ||
|
|
9f6fa770cf | ||
|
|
6c43d08174 | ||
|
|
fdf77dbd88 | ||
|
|
8cd97a2413 | ||
| 46c897e865 | |||
| 10d97e09bd | |||
|
|
f9affb5269 | ||
|
|
487a8d48ee | ||
|
dcbef2cd0a
|
|||
|
7465ecedf8
|
|||
|
256c337db4
|
|||
|
0ddeb75508
|
|||
|
896002da8c
|
|||
|
ef892b38a7
|
|||
|
20d8e07a24
|
|||
|
d9a1063630
|
|||
|
3860f5849c
|
|||
|
f732f7247f
|
|||
|
883330996a
|
|||
|
c90caed623
|
|||
|
cfd521f502
|
|||
|
f71faa0ae8
|
|||
|
ce30776eeb
|
|||
|
be092af161
|
|||
|
0b75f66f30
|
|||
|
e595bb2c45
|
|||
|
d82ce7a80f
|
2
.github/dependabot.yml
vendored
2
.github/dependabot.yml
vendored
@@ -16,6 +16,7 @@ updates:
|
||||
- "/docker/infrastructure/network/traefik"
|
||||
- "/docker/infrastructure/squid"
|
||||
- "/docker/infrastructure/sshportal"
|
||||
- "/docker/personal/fireshare"
|
||||
- "/docker/personal/gramps"
|
||||
- "/docker/personal/media/films-series/jackett"
|
||||
- "/docker/personal/media/films-series/jellyfin"
|
||||
@@ -52,6 +53,7 @@ updates:
|
||||
- "/kubernetes/personal/photoprism"
|
||||
- "/kubernetes/production/umami"
|
||||
- "/kubernetes/system/blocky"
|
||||
- "/kubernetes/system/caddy"
|
||||
- "/kubernetes/system/coredns"
|
||||
- "/kubernetes/system/csi-driver-nfs"
|
||||
- "/kubernetes/system/external-dns"
|
||||
|
||||
@@ -3,7 +3,7 @@ creation_rules:
|
||||
encrypted_regex: ^(password|value|ssh-key|api-key|user|username|privateKey|clientSecret|clientId|apiKey|extraArgs.*|.*Secret.*|extraEnvVars|.*SECRET.*|.*secret.*|key|.*Password|.*\.ya?ml)$
|
||||
pgp: DC6910268E657FF70BA7EC289974494E76938DDC
|
||||
- path_regex: .*.yaml
|
||||
encrypted_regex: ^(data|stringData)$
|
||||
encrypted_regex: ^(data|stringData|.*.key|.*.crt)$
|
||||
pgp: DC6910268E657FF70BA7EC289974494E76938DDC
|
||||
- path_regex: .*.env$
|
||||
input_type: dotenv
|
||||
|
||||
@@ -53,6 +53,13 @@ sshportal:
|
||||
branch: main
|
||||
compose_file: docker/infrastructure/sshportal/docker-compose.yml
|
||||
|
||||
fireshare:
|
||||
repo: homeprod
|
||||
branch: main
|
||||
compose_file: docker/personal/fireshare/docker-compose.yml
|
||||
sops_files:
|
||||
- docker/personal/fireshare/.env
|
||||
|
||||
gramps:
|
||||
repo: homeprod
|
||||
branch: main
|
||||
|
||||
10
README.md
10
README.md
@@ -80,3 +80,13 @@ This setup allows running multiple applications, either self-hosted applications
|
||||
| <img width=32 src="https://avatars.githubusercontent.com/u/26692192"> | Navidrome | Personal music streaming service |
|
||||
| <img width=32 src="https://avatars.githubusercontent.com/u/102734415"> | TubeArchivist | YouTube archiver |
|
||||
| <img width=24 src="https://radicale.org/assets/logo.svg"> | Radicale | Calendar and contacts server |
|
||||
|
||||
|
||||
## Docs (internal, using this repository)
|
||||
|
||||
This repository uses pre-commit hooks to automate tasks like file encryption and configuration generation.
|
||||
|
||||
After cloning, install the pre-commit hooks:
|
||||
```bash
|
||||
pre-commit install
|
||||
```
|
||||
|
||||
@@ -355,6 +355,13 @@ canada:
|
||||
ttl: 300
|
||||
type: A
|
||||
value: 192.99.6.159
|
||||
clips:
|
||||
octodns:
|
||||
cloudflare:
|
||||
auto-ttl: true
|
||||
ttl: 300
|
||||
type: A
|
||||
value: 83.113.30.49
|
||||
flix:
|
||||
octodns:
|
||||
cloudflare:
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
services:
|
||||
esphome:
|
||||
image: ghcr.io/esphome/esphome:2026.4.3
|
||||
image: ghcr.io/esphome/esphome:2026.4.4
|
||||
ports:
|
||||
- "6052"
|
||||
networks:
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
services:
|
||||
n8n:
|
||||
image: docker.n8n.io/n8nio/n8n:2.18.4
|
||||
image: docker.n8n.io/n8nio/n8n:2.19.2
|
||||
environment:
|
||||
- TZ=Europe/Paris
|
||||
- N8N_SECURE_COOKIE=false
|
||||
|
||||
@@ -2,7 +2,7 @@ services:
|
||||
zigbee2mqtt:
|
||||
container_name: zigbee2mqtt
|
||||
restart: unless-stopped
|
||||
image: koenkk/zigbee2mqtt:2.9.2
|
||||
image: koenkk/zigbee2mqtt:2.10.1
|
||||
networks:
|
||||
- default
|
||||
- proxy
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
services:
|
||||
stalwart:
|
||||
image: stalwartlabs/stalwart:v0.16.2
|
||||
image: stalwartlabs/stalwart:v0.16.4
|
||||
container_name: stalwart
|
||||
networks:
|
||||
- default
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
services:
|
||||
traefik:
|
||||
image: traefik:3.6
|
||||
image: traefik:v3.7
|
||||
command:
|
||||
- "--configFile=/etc/traefik/traefik.yml"
|
||||
ports:
|
||||
|
||||
11
docker/personal/fireshare/.env
Normal file
11
docker/personal/fireshare/.env
Normal file
@@ -0,0 +1,11 @@
|
||||
ADMIN_USERNAME=ENC[AES256_GCM,data:8ngfC8VHpaaGCQ==,iv:Ze7ThfWmAWj0ZvV3A7Pd+aqAW/pahkTZhdFC/TnAwZ0=,tag:KCFdGV1dEw3e+q6FBgy2cw==,type:str]
|
||||
ADMIN_PASSWORD=ENC[AES256_GCM,data:UhxEMnqYDyfgffqUf3Q=,iv:VvNX867P+w20Y7laG0R0c4BUw1uICeyF5SU3+waosRE=,tag:JL4GC+UZY3TqSmCq14CTpg==,type:str]
|
||||
SECRET_KEY=ENC[AES256_GCM,data:uahYXYr4DvavNMTTdcDA0hdp5wj3OLret3fPF1DEc2lis+E7/fe45DWFuhUu8RAK76tuheA=,iv:Lofc+PP7Rtg99l36yOx6bt0i8hg1DJXzwSKQNJCRYPw=,tag:AiUGZOiLyjKItf++Gya+eA==,type:str]
|
||||
DOMAIN=ENC[AES256_GCM,data:LyJ7RAgrioTltNQ/BKoPbEN8XQ==,iv:IHrT5TkaXuIhkfN/nHcapz4CNBG0t9lbzrHDjp04JLw=,tag:gjSa/tSVEqk6pXrfhjs7gQ==,type:str]
|
||||
sops_lastmodified=2026-05-06T17:05:48Z
|
||||
sops_mac=ENC[AES256_GCM,data:wRtDnVQkNsc1MtxSpbuVDuACkCwunYeyYSaQX2Tglm2kwOnx9iCyhuWY6RMYu5nfyJ1CT1kfqeGrGxhJ5uMDee29eLUv844X3hIXwpMT50jHFXEtfKLfRMfqpv9r9mbp2EP9VNDUtPyIwDk5vSjGeaYqEWtHW/q5y9qIrzqqy5g=,iv:UG4XGi3Qo8/nAddY+rzJm1AKIAmJjtR+2bDqSeaVxG4=,tag:SL2rvrxFmMfgyUyMqFIZEQ==,type:str]
|
||||
sops_pgp__list_0__map_created_at=2026-05-06T17:05:48Z
|
||||
sops_pgp__list_0__map_enc=-----BEGIN PGP MESSAGE-----\n\nhQIMA7uy4qQr71wiAQ//b6zlRVKrqzzszBJmnOUlfeZd5m2ekYv/zIBr4oxHyn5L\neLLff+N7hjBVSajg9Qg7GBQv7s3DX70vHTpdUP38UEO1aM0l3eU1JCwA4Hdh7Ds5\nnq330vUKhIAd+K8Vv4Ei9YHpj+kgMnt+R780qZUg18D39TAnx36q9b5SKzZCUsks\n3YM+G8pHLRipZhxp6zwhOPHVSnImOFjty4d6JV6Zes9zfslaETgva7p5DIKP0ttf\nI2JRacvL75MMp1USyqGKt7Bpl6Yz4VxY49aea+FxDlbzCVLuBBgZMoEjhPQifQfh\nB6OObmu1cVhECidrMHmqDBNqgKsNLble+g3Le+gJdn/zKxVc+q+cPPuk/JdT8tfv\nZTei6jg66IREZOrZCP3Gt4OB5LbkLdS0NET2CMVAYkGQvGrSC+diwUnFkI+WEh+p\noZhvgp/ytBgaw6ZyNPmvkGkFeFg1/ISpOHkVQ+P6Pnot8h4HvuI/KcBwJRCrtdbg\n+XMpqeQdmCnM04v5Uq1NVqRWHD0yvd7GHDOZCqJPMFHP0M6R+SwHq+8+pgbO3jxt\n+426MvhNKw8xWMtnUIO8sSSkzgOfT6vFXmzQvIawbXvitjGjiElkpmT5Hz3hn1Bm\nnu8CivqLwL4Gs1Uc2m6qHGkvGqxWwcHABWqftAk3VfhmjcFDwAyWROlCuD+A15PS\nXgE1wn9jLesXaiCwzAp4AOstkk0fR2yio4fa9dCeenzuedULNLuCyJfYtSm4QlSU\nvffH4iL8X/R24s6SdPsCIuNnAeKc0P4E55AlOaeZN4HcZzfspVikAZx+bK14JS8=\n=KGp6\n-----END PGP MESSAGE-----
|
||||
sops_pgp__list_0__map_fp=DC6910268E657FF70BA7EC289974494E76938DDC
|
||||
sops_unencrypted_suffix=_unencrypted
|
||||
sops_version=3.10.2
|
||||
58
docker/personal/fireshare/docker-compose.yml
Normal file
58
docker/personal/fireshare/docker-compose.yml
Normal file
@@ -0,0 +1,58 @@
|
||||
services:
|
||||
fireshare:
|
||||
container_name: fireshare
|
||||
image: shaneisrael/fireshare:1.6.10-lite
|
||||
ports:
|
||||
- "80"
|
||||
volumes:
|
||||
- data:/data
|
||||
- processed:/processed
|
||||
- video:/videos
|
||||
- images:/images
|
||||
env_file:
|
||||
- .env
|
||||
environment:
|
||||
# PUID/PGID: the user/group ID the container runs as. Files written to your
|
||||
# volumes (data, processed, videos, images) will be owned by this user. Set these to
|
||||
# match the owner of your host directories to avoid permission errors.
|
||||
# Run `id` on your host to find your UID and GID.
|
||||
- PUID=1000
|
||||
- PGID=1000
|
||||
networks:
|
||||
- default
|
||||
- proxy
|
||||
labels:
|
||||
- "traefik.enable=true"
|
||||
- "traefik.http.routers.fireshare.rule=Host(`clips.vhaudiquet.fr`)"
|
||||
- "traefik.http.services.fireshare.loadbalancer.server.port=80"
|
||||
|
||||
volumes:
|
||||
data:
|
||||
driver: local
|
||||
driver_opts:
|
||||
type: 'none'
|
||||
o: 'bind'
|
||||
device: '/app/fireshare/data'
|
||||
processed:
|
||||
driver: local
|
||||
driver_opts:
|
||||
type: 'none'
|
||||
o: 'bind'
|
||||
device: '/app/fireshare/processed'
|
||||
video:
|
||||
driver: local
|
||||
driver_opts:
|
||||
type: 'none'
|
||||
o: 'bind'
|
||||
device: '/app/fireshare/video'
|
||||
images:
|
||||
driver: local
|
||||
driver_opts:
|
||||
type: 'none'
|
||||
o: 'bind'
|
||||
device: '/app/fireshare/images'
|
||||
|
||||
networks:
|
||||
proxy:
|
||||
external: true
|
||||
name: proxy
|
||||
@@ -1,7 +1,7 @@
|
||||
services:
|
||||
grampsweb:
|
||||
container_name: grampsweb
|
||||
image: ghcr.io/gramps-project/grampsweb:26.4.3
|
||||
image: ghcr.io/gramps-project/grampsweb:26.5.0
|
||||
restart: always
|
||||
networks:
|
||||
- default
|
||||
@@ -31,7 +31,7 @@ services:
|
||||
|
||||
grampsweb_celery:
|
||||
container_name: grampsweb_celery
|
||||
image: ghcr.io/gramps-project/grampsweb:26.4.3
|
||||
image: ghcr.io/gramps-project/grampsweb:26.5.0
|
||||
restart: always
|
||||
environment:
|
||||
- GRAMPSWEB_TREE="Gramps Web" # will create a new tree if not exists
|
||||
@@ -52,7 +52,7 @@ services:
|
||||
command: celery -A gramps_webapi.celery worker --loglevel=INFO --concurrency=2
|
||||
|
||||
grampsweb_redis:
|
||||
image: docker.io/library/redis:8.6.2-alpine
|
||||
image: docker.io/library/redis:8.6.3-alpine
|
||||
container_name: grampsweb_redis
|
||||
restart: always
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
services:
|
||||
jackett:
|
||||
container_name: jackett
|
||||
image: ghcr.io/hotio/jackett:release-v0.24.1789
|
||||
image: ghcr.io/hotio/jackett:release-v0.24.1815
|
||||
ports:
|
||||
- "9117"
|
||||
networks:
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
services:
|
||||
jellyfin:
|
||||
image: jellyfin/jellyfin:2026042706
|
||||
image: jellyfin/jellyfin:2026050514
|
||||
container_name: jellyfin
|
||||
networks:
|
||||
- default
|
||||
|
||||
@@ -10,7 +10,7 @@ services:
|
||||
env_file: .env
|
||||
|
||||
match_collector:
|
||||
image: git.vhaudiquet.fr/vhaudiquet/lolstats-match_collector:ee32060a7f05bd963bed4337369e146ba6313d64
|
||||
image: git.vhaudiquet.fr/vhaudiquet/lolstats-match_collector:b2178fec85027348157a5442a81d00479154e581
|
||||
build: ./match_collector
|
||||
volumes:
|
||||
- bpcdragon_cache:/cdragon
|
||||
@@ -23,7 +23,7 @@ services:
|
||||
env_file: .env
|
||||
|
||||
frontend:
|
||||
image: git.vhaudiquet.fr/vhaudiquet/lolstats-frontend:ee32060a7f05bd963bed4337369e146ba6313d64
|
||||
image: git.vhaudiquet.fr/vhaudiquet/lolstats-frontend:b2178fec85027348157a5442a81d00479154e581
|
||||
build: ./frontend
|
||||
restart: always
|
||||
volumes:
|
||||
|
||||
@@ -61,7 +61,7 @@ resource "proxmox_virtual_environment_vm" "docker-machine" {
|
||||
}
|
||||
|
||||
memory {
|
||||
floating = 16192
|
||||
floating = 22222
|
||||
dedicated = 38768
|
||||
}
|
||||
|
||||
|
||||
@@ -4,8 +4,12 @@ image:
|
||||
tag: v0.24
|
||||
pullPolicy: IfNotPresent
|
||||
controller:
|
||||
replicas: 1
|
||||
replicas: 2
|
||||
dnsPolicy: ClusterFirst
|
||||
strategy: RollingUpdate
|
||||
rollingUpdate:
|
||||
maxUnavailable: 0
|
||||
maxSurge: 1
|
||||
env:
|
||||
TZ: Europe/Paris
|
||||
service:
|
||||
@@ -21,6 +25,37 @@ service:
|
||||
dns:
|
||||
port: 53
|
||||
protocol: UDP
|
||||
probes:
|
||||
liveness:
|
||||
enabled: true
|
||||
custom: true
|
||||
spec:
|
||||
tcpSocket:
|
||||
port: 53
|
||||
initialDelaySeconds: 10
|
||||
periodSeconds: 10
|
||||
timeoutSeconds: 5
|
||||
failureThreshold: 3
|
||||
readiness:
|
||||
enabled: true
|
||||
custom: true
|
||||
spec:
|
||||
tcpSocket:
|
||||
port: 53
|
||||
initialDelaySeconds: 5
|
||||
periodSeconds: 5
|
||||
timeoutSeconds: 3
|
||||
failureThreshold: 3
|
||||
startup:
|
||||
enabled: true
|
||||
custom: true
|
||||
spec:
|
||||
tcpSocket:
|
||||
port: 53
|
||||
initialDelaySeconds: 5
|
||||
periodSeconds: 2
|
||||
timeoutSeconds: 3
|
||||
failureThreshold: 30
|
||||
resources:
|
||||
limits:
|
||||
cpu: 200m
|
||||
@@ -31,27 +66,27 @@ resources:
|
||||
# Full list of options https://github.com/0xERR0R/blocky/blob/main/docs/config.yml
|
||||
config: "upstreams:\n groups:\n default:\n - 1.1.1.1\n - 1.0.0.1\n lan:\n - 10.101.207.1\n\nconditional:\n mapping:\n lan: 10.101.207.1\n cluster.local: 10.96.0.10\n in-addr.arpa: 10.96.0.10\n\nblocking:\n allowlists:\n ads:\n - |\n dealabs.digidip.net\n s.click.aliexpress.com\n fonts.googleapis.com\n fonts.gstatic.com\n wl.spotify.com\n www.googleadservices.com\n \n denylists:\n ads:\n - https://raw.githubusercontent.com/StevenBlack/hosts/master/hosts\n - https://adaway.org/hosts.txt\n \n clientGroupsBlock:\n default:\n - ads\n \n blockType: zeroIp\n blockTTL: 1m\n loading:\n refreshPeriod: 4h\n downloads:\n timeout: 60s\n\ncaching:\n minTime: 5m\n maxTime: 30m\n # Disable negative caching (NXDOMAIN responses) for dynamic DNS\n cacheTimeNegative: 0\n prefetching: true\n prefetchExpires: 2h\n prefetchThreshold: 5\n\nprometheus:\n enable: true\n path: /metrics\n\nports:\n dns: 53\n http: 4000\n\nbootstrapDns: tcp+udp:1.1.1.1\n\nlog:\n level: info\n format: text\n timestamp: true\n"
|
||||
sops:
|
||||
lastmodified: "2026-05-02T14:36:10Z"
|
||||
mac: ENC[AES256_GCM,data:1SV8u2ozDlB/m8uo7I7AIa/1njmu1bJ5vKilcirfNByz8wp/LRTtRgWwpUOrxzd1+qg+ZC1/mSLQY/kdwWcTU9uP6uBNSLemWJgIRBobFmExDvtfidkJXRhTMUm9zdSNGS/EbQQOz+DV8AAuByTwbP6i5fTiVNVes8kBlYbPvjc=,iv:Ox25bYW8ch63eJgCkOTZxUP/6+w43lKjC2lzYdBzUjw=,tag:LgXken02vzuXDuxg4Iovrw==,type:str]
|
||||
lastmodified: "2026-05-02T17:51:26Z"
|
||||
mac: ENC[AES256_GCM,data:J7EovwsXi2L9XocZoi5ann71DQ+wWZk2aCUbjvaGpv0yZC5g2HNccPVRvAj3y9SyMttLT8QlESXzHpEV2A6bOfmJf5v0ACYuWn5wKNlkaBdmTs1xwXp/RcpeOb+FCL9D+9hzjBO9XF6iXZLSj4pO/n1C0IhfeqYKdDC4tHkxOHA=,iv:Qm3Uh+UUSDWCxh7gWJ9x597aWXdMHxtpixE2BVlb6c8=,tag:aHbK26P4f9YV2uGLhpT6OA==,type:str]
|
||||
pgp:
|
||||
- created_at: "2026-05-02T14:36:09Z"
|
||||
- created_at: "2026-05-02T17:51:25Z"
|
||||
enc: |-
|
||||
-----BEGIN PGP MESSAGE-----
|
||||
|
||||
hQIMA7uy4qQr71wiARAAtdzdOgPBhpRSSnw5ZNXHpb6//E5SpCTDDOUbgpvw4FQj
|
||||
ndqJwONMEm7RlZELlxpXq4Gr621j5hcdcc2vUl4ak8wC+1Ml2AAEYf0rrL2SQVVC
|
||||
DAiRdHXilzOKJBx+qA+afZT4SNXnN8kv8LRq354mEpxMZ21ot0nZ+sjJiHrVGbSO
|
||||
B2l39o3POLoTmzB/0+iTn953txjijVn/Hm7JoQ7yqQXBwnzjK1F7IkOdv0hyvpW1
|
||||
/Sba+yqZQTqdpH/EwRfQxf6OJpxMBIAj6/COzcp143O3tjVQAEHTaqHbY4rbrt07
|
||||
yxvOZKy2tNP/xY62E35rTzGvMrRqUzFNtaYeycx5F0jHgYNITtlCPh1txf5PBq5H
|
||||
kmR9NFCOHncX5BFTAXbWaGVQiWxa71mn3vy49BZCwwz21D3u5/PI0Vqe5JBccyVu
|
||||
4yqqIdwIrj5i0BdlIFHig1WbYzDjRriR4H1z/Y2Vvv1wtRao99rf8DhCxcWwEgNo
|
||||
vAOM1wSBHacr9uZrgAOvObkMWZ4m1UekIJXkA5803cb8J+ceneJ+EOWyYiFVPV8h
|
||||
MshaL9M1zuEydZqHwDHfMgR/BgVvSVFwPQSkfXnKYJHNS8QGTfZKFudBiP0Ij7DB
|
||||
pjRf5f2b4FhDgCIg5BopWBxES0LscpFmHgrV0QDKiXOXJNMkVUF5+ITz6HwwwlnS
|
||||
XAEwKWrC58GzNBKFCvSMeD83xy7icfdTkXvO30EW9CbEUAMYN4twgsHG+J5NDrUR
|
||||
yaET3e2kmOWStkQsPmMtYEVRfRHOWr8XKQXMJfrA87ZC0P19UwUM0eRXJVCN
|
||||
=0h7d
|
||||
hQIMA7uy4qQr71wiAQ/+Po8UdkiFGt0LmcvCeSE23aoWwY4qi2FsGKdik+7sL3RN
|
||||
gOt/VQ6geefhd4YDhH0jfd7TDXs7UTtYvKQ+IaKcRUyOrZzhrfTpNeT/lXuaTkHf
|
||||
LAUiqyprq1RDzxxIPvgMh4DynfehgN8B81iMJox2/fD0oV7B6dIIABvAl87gzANw
|
||||
7snQLJwdhNXFylKfrdC9A4AfYz7ycXBzEyYlY5BMZENw9yBGgZ1dZITU2KxeYCo/
|
||||
gdVTCevybSBQ/Cq0+hI25ZF+nEIGjrVCN2AxPEUO98ljp4OZEu0p6KsMB4xgCD2j
|
||||
l5LN6YPAu95TRx/bZinoHMMzth6WhFdUG0Anj2cIIYXOcreyzPxYGj+vwRlZFrkZ
|
||||
gTU2vfpt/1Wx8ORRqocCkxZ3dMtm4KsGqe3xpd1y84ezL/bMLxSApn5e7Zzn1cEg
|
||||
DoLwJGnZzSY4nRzfoGXOv6mjyTUVkqNexRlL2wIsgDP9VP/ohS9K2fFZzzJ/fXa1
|
||||
G9DUg64SwfYIFzAgsyWwdE3kCJ/GSIAgrgNwBfZlLGdfB/PB2BkHNpzX4LROUEcD
|
||||
HqqHtVlUIikiFdDQWwB5tS+APBCO6VuzKl1z3ROgV6xhvr4ZYkd9CHYu1S1r1XAs
|
||||
JRCyow0zTLRYGQnDD8+RPQ4MsbzJsugA8Ac4bE4sVJpP8hloZBqHb38AkoUruDTS
|
||||
XgE+Nxcy0/aznBgEscE/VuY/GTH1vwYl5/dAcV8GDYcNmd1tE9E1QwWsSurHt39u
|
||||
+QdGZYoUbHPtsk/zODgEVqn0iTsqO7Y4Qmu93bYlYFQwCygAPKKpCaqmmu2U+rI=
|
||||
=hq5F
|
||||
-----END PGP MESSAGE-----
|
||||
fp: DC6910268E657FF70BA7EC289974494E76938DDC
|
||||
encrypted_regex: ^(password|value|ssh-key|api-key|user|username|privateKey|clientSecret|clientId|apiKey|extraArgs.*|.*Secret.*|extraEnvVars|.*SECRET.*|.*secret.*|key|.*Password|.*\.ya?ml)$
|
||||
|
||||
69
kubernetes/system/caddy/caddyfile.yaml
Normal file
69
kubernetes/system/caddy/caddyfile.yaml
Normal file
@@ -0,0 +1,69 @@
|
||||
# Caddy Routes - External ConfigMap
|
||||
# This file contains all route definitions, imported by the main Caddyfile.
|
||||
# Edit this file to add/modify routes.
|
||||
#
|
||||
# Certificate files are mounted from the caddy-certificates Secret
|
||||
# at /etc/caddy/certs/
|
||||
|
||||
apiVersion: v1
|
||||
kind: ConfigMap
|
||||
metadata:
|
||||
name: caddy-routes
|
||||
namespace: caddy
|
||||
labels:
|
||||
app.kubernetes.io/name: caddy
|
||||
app.kubernetes.io/component: routes
|
||||
data:
|
||||
Caddyfile: |
|
||||
vhaudiquet.fr {
|
||||
tls /etc/caddy/certs/vhaudiquet-fr.crt /etc/caddy/certs/vhaudiquet-fr.key
|
||||
reverse_proxy 10.1.2.212:80
|
||||
}
|
||||
|
||||
*.vhaudiquet.fr {
|
||||
tls /etc/caddy/certs/wildcard-vhaudiquet-fr.crt /etc/caddy/certs/wildcard-vhaudiquet-fr.key
|
||||
|
||||
# Kubernetes services (via Traefik)
|
||||
@authentik host authentik.vhaudiquet.fr
|
||||
|
||||
@auth-nook host auth-nook.vhaudiquet.fr
|
||||
@nook-mg host n.vhaudiquet.fr
|
||||
@nook host nook.vhaudiquet.fr
|
||||
@sse-nook host sse-nook.vhaudiquet.fr
|
||||
|
||||
@gitea host git.vhaudiquet.fr
|
||||
|
||||
@flux-wh host flux-webhook.vhaudiquet.fr
|
||||
|
||||
@umami host umami.vhaudiquet.fr
|
||||
|
||||
handle @authentik { reverse_proxy traefik.traefik.svc.cluster.local:80 }
|
||||
handle @auth-nook { reverse_proxy traefik.traefik.svc.cluster.local:80 }
|
||||
handle @nook-mg { reverse_proxy traefik.traefik.svc.cluster.local:80 }
|
||||
handle @nook { reverse_proxy traefik.traefik.svc.cluster.local:80 }
|
||||
handle @sse-nook { reverse_proxy traefik.traefik.svc.cluster.local:80 }
|
||||
handle @gitea { reverse_proxy traefik.traefik.svc.cluster.local:80 }
|
||||
handle @flux-wh { reverse_proxy traefik.traefik.svc.cluster.local:80 }
|
||||
handle @umami { reverse_proxy traefik.traefik.svc.cluster.local:80 }
|
||||
|
||||
# Docker VM services (via Traefik)
|
||||
@alexscript host alexscript.vhaudiquet.fr
|
||||
@clips host clips.vhaudiquet.fr
|
||||
@jellyfin host flix.vhaudiquet.fr
|
||||
@mail host mail.vhaudiquet.fr
|
||||
|
||||
handle @alexscript { reverse_proxy 10.1.2.212:80 }
|
||||
handle @clips { reverse_proxy 10.1.2.212:80 }
|
||||
handle @jellyfin { reverse_proxy 10.1.2.212:80 }
|
||||
handle @mail { reverse_proxy 10.1.2.212:80 }
|
||||
}
|
||||
|
||||
semery.fr {
|
||||
tls /etc/caddy/certs/semery-fr.crt /etc/caddy/certs/semery-fr.key
|
||||
reverse_proxy 10.1.2.212:80
|
||||
}
|
||||
|
||||
buildpath.win {
|
||||
tls /etc/caddy/certs/buildpath-win.crt /etc/caddy/certs/buildpath-win.key
|
||||
reverse_proxy 10.1.2.212:80
|
||||
}
|
||||
54
kubernetes/system/caddy/certificates-secret.yaml
Normal file
54
kubernetes/system/caddy/certificates-secret.yaml
Normal file
File diff suppressed because one or more lines are too long
15
kubernetes/system/caddy/kustomization.yaml
Normal file
15
kubernetes/system/caddy/kustomization.yaml
Normal file
@@ -0,0 +1,15 @@
|
||||
apiVersion: kustomize.config.k8s.io/v1beta1
|
||||
kind: Kustomization
|
||||
namespace: caddy
|
||||
resources:
|
||||
- namespace.yaml
|
||||
- repository.yaml
|
||||
- release.yaml
|
||||
- certificates-secret.yaml
|
||||
- caddyfile.yaml
|
||||
secretGenerator:
|
||||
- name: caddy-values
|
||||
files:
|
||||
- values.yaml=values.yaml
|
||||
configurations:
|
||||
- kustomizeconfig.yaml
|
||||
6
kubernetes/system/caddy/kustomizeconfig.yaml
Normal file
6
kubernetes/system/caddy/kustomizeconfig.yaml
Normal file
@@ -0,0 +1,6 @@
|
||||
nameReference:
|
||||
- kind: Secret
|
||||
version: v1
|
||||
fieldSpecs:
|
||||
- path: spec/valuesFrom/name
|
||||
kind: HelmRelease
|
||||
7
kubernetes/system/caddy/namespace.yaml
Normal file
7
kubernetes/system/caddy/namespace.yaml
Normal file
@@ -0,0 +1,7 @@
|
||||
apiVersion: v1
|
||||
kind: Namespace
|
||||
metadata:
|
||||
name: caddy
|
||||
labels:
|
||||
app.kubernetes.io/name: caddy
|
||||
app.kubernetes.io/component: edge-proxy
|
||||
19
kubernetes/system/caddy/release.yaml
Normal file
19
kubernetes/system/caddy/release.yaml
Normal file
@@ -0,0 +1,19 @@
|
||||
apiVersion: helm.toolkit.fluxcd.io/v2
|
||||
kind: HelmRelease
|
||||
metadata:
|
||||
name: caddy
|
||||
namespace: caddy
|
||||
spec:
|
||||
interval: 1m
|
||||
chart:
|
||||
spec:
|
||||
sourceRef:
|
||||
kind: HelmRepository
|
||||
name: caddy
|
||||
namespace: caddy
|
||||
chart: caddy
|
||||
interval: 1m
|
||||
version: "0.7.1"
|
||||
valuesFrom:
|
||||
- kind: Secret
|
||||
name: caddy-values
|
||||
8
kubernetes/system/caddy/repository.yaml
Normal file
8
kubernetes/system/caddy/repository.yaml
Normal file
@@ -0,0 +1,8 @@
|
||||
apiVersion: source.toolkit.fluxcd.io/v1
|
||||
kind: HelmRepository
|
||||
metadata:
|
||||
name: caddy
|
||||
namespace: caddy
|
||||
spec:
|
||||
interval: 1m
|
||||
url: https://charts.alekc.dev/
|
||||
104
kubernetes/system/caddy/values.yaml
Normal file
104
kubernetes/system/caddy/values.yaml
Normal file
@@ -0,0 +1,104 @@
|
||||
# Caddy Edge Proxy
|
||||
replicaCount: 2
|
||||
# Listen on standard HTTP port
|
||||
listenPort: 80
|
||||
# Enable HTTPS
|
||||
https:
|
||||
enabled: true
|
||||
port: 443
|
||||
image:
|
||||
repository: caddy
|
||||
pullPolicy: IfNotPresent
|
||||
tagSuffix: ""
|
||||
tag: 2.11.2
|
||||
service:
|
||||
type: LoadBalancer
|
||||
annotations:
|
||||
io.cilium/lb-ipam-ips: 10.1.2.152
|
||||
externalTrafficPolicy: Local
|
||||
# Disable ingress - Caddy IS the edge proxy
|
||||
ingress:
|
||||
enabled: false
|
||||
resources:
|
||||
requests:
|
||||
cpu: 100m
|
||||
memory: 128Mi
|
||||
limits:
|
||||
cpu: 500m
|
||||
memory: 256Mi
|
||||
podSecurityContext:
|
||||
runAsNonRoot: true
|
||||
runAsUser: 1000
|
||||
runAsGroup: 1000
|
||||
fsGroup: 1000
|
||||
securityContext:
|
||||
allowPrivilegeEscalation: false
|
||||
capabilities:
|
||||
drop:
|
||||
- ALL
|
||||
readOnlyRootFilesystem: true
|
||||
health:
|
||||
path: /
|
||||
port: 9999
|
||||
# Extra volumes: certificates + external routes ConfigMap
|
||||
volumes:
|
||||
- name: certificates
|
||||
secret:
|
||||
secretName: ENC[AES256_GCM,data:hpxK4mqVNwVRWutC4ufnqhzu,iv:D/7vhjkr5buSFJ42UeGKicPJA7YxHhv+vmakFFE11Vk=,tag:AExbVZIQu+wrUb5jq86toA==,type:str]
|
||||
optional: ENC[AES256_GCM,data:y19uLw==,iv:S5VEP6p7GspKtXeTDumHy1xJ0yW1qu/t4yqy3bhlZSE=,tag:mkZiVVboLoOhGd1EcE9PaA==,type:bool]
|
||||
- name: routes
|
||||
configMap:
|
||||
name: caddy-routes
|
||||
# Extra volume mounts
|
||||
volumeMounts:
|
||||
- name: certificates
|
||||
mountPath: /etc/caddy/certs
|
||||
readOnly: true
|
||||
- name: routes
|
||||
mountPath: /etc/caddy/routes
|
||||
readOnly: true
|
||||
# Caddy configuration
|
||||
config:
|
||||
debug: false
|
||||
# Global options (goes inside the global {} block)
|
||||
global: |
|
||||
auto_https off
|
||||
# The main Caddyfile content - imports routes from external ConfigMap
|
||||
# This keeps routes in a separate, easily editable file
|
||||
caddyFile: |
|
||||
import /etc/caddy/routes/Caddyfile
|
||||
affinity:
|
||||
podAntiAffinity:
|
||||
preferredDuringSchedulingIgnoredDuringExecution:
|
||||
- weight: 100
|
||||
podAffinityTerm:
|
||||
labelSelector:
|
||||
matchLabels:
|
||||
app.kubernetes.io/name: caddy
|
||||
topologyKey: kubernetes.io/hostname
|
||||
sops:
|
||||
lastmodified: "2026-05-07T22:47:47Z"
|
||||
mac: ENC[AES256_GCM,data:LQqoe/wDLAUJWLiEGoID3CSI4bQmdVaroAkq7Kk9Ullt85X3VmYMOrLXjn1Qew95rpG6gB9Bl7rvv0J7mUDJtewhfkSsSXKTYJAcn4VVoNGZ3PZu9/w5HNvOqDhTkXBWKEgQK4+HMKKEhW8iQ5aJ+oTAEZfKsp9k8+mqgHId100=,iv:E/v+fY9iKM9W9NFSGNtiJV6ZeaAb2Fy2hGDgOBwmFyU=,tag:JOD69j8SUS5339+zrV9L4g==,type:str]
|
||||
pgp:
|
||||
- created_at: "2026-05-07T22:47:46Z"
|
||||
enc: |-
|
||||
-----BEGIN PGP MESSAGE-----
|
||||
|
||||
hQIMA7uy4qQr71wiARAAt5P8/X84OYKnWvKc5qRpwHNQwbfqrB/SHkX82oJ8ZlXJ
|
||||
/vlKVDOBrlntePt4cyKT6c3Ubw4xDj/1U3PkvM44AXSRHH8E5dSUI+5T/0+SBlfU
|
||||
6XlkF6cpng/ydMvImTAi3+8bmC3yHE/NEegreldjFj7l2hdFuvfyOp7pmE//Ljox
|
||||
D7tkq9v1/IlvPfeAY0xIEotr1nb41OEhM7OhPQjtGUeufD0eCUhCQaZSo+CjTrf2
|
||||
cG+eE/O2jCLNjWJ33wK1AHtHX1mlyzW8sRkRVgg511G8iquFjD11ZuDZPEIC8Yle
|
||||
idftTlPh0ZTOGXcfDVn5Pq9dgkZ3K6ufhvEb8mw0NrPsysY21PdDaIzLo58b4t2m
|
||||
akJ1xCciwsQDorKfFjpG7gFzV1KvMzw/KjEUFxg5JfKaFGTPhgsf50OiM6VPf4gP
|
||||
cTS5QNewdnbnzHE756PkZqfqdt6Tt9xqji8r72PwTSUy6yaK/lV9owAIZ6V2yTdt
|
||||
l3DckDp0HsU/w98fabiX9CsrJUWeUfioElw2ibXWcXNHmqPoFl1Bf/AbF20t6P9p
|
||||
+1J0vMu6ONsBGv2Flmle2Ya7OQbZF4lQB4dQLUBDKdZArsB5Sspm3Rf+4iP9qUF+
|
||||
Pr/OotbiaOLsEZybIf+L2d5ON4zCbNAU5VbpfWMKH0AsPcIH5Ruw7d/OutAGZOvS
|
||||
XAGAEBjVlZ2IRU6CSPJDG/9TqBHyBHfriV+BoGlKlXbPMoJAZI2wX1o7+M6S65ho
|
||||
aiR70aCo2kIgFvxxBeY1FxtB0DB8Zeoul7ovvhKIq2u9s7X/OSIa0X5dm6sZ
|
||||
=fg1O
|
||||
-----END PGP MESSAGE-----
|
||||
fp: DC6910268E657FF70BA7EC289974494E76938DDC
|
||||
encrypted_regex: ^(password|value|ssh-key|api-key|user|username|privateKey|clientSecret|clientId|apiKey|extraArgs.*|.*Secret.*|extraEnvVars|.*SECRET.*|.*secret.*|key|.*Password|.*\.ya?ml)$
|
||||
version: 3.10.2
|
||||
@@ -6,3 +6,4 @@ spec:
|
||||
blocks:
|
||||
- cidr: "10.1.2.171/32"
|
||||
- cidr: "10.1.2.148/32"
|
||||
- cidr: "10.1.2.152/32"
|
||||
|
||||
@@ -12,7 +12,7 @@ spec:
|
||||
name: coredns
|
||||
namespace: coredns
|
||||
chart: coredns
|
||||
version: "1.x.x"
|
||||
version: "1.45.2"
|
||||
interval: 1m
|
||||
valuesFrom:
|
||||
- kind: Secret
|
||||
|
||||
@@ -1,8 +1,31 @@
|
||||
replicaCount: 1
|
||||
replicaCount: 2
|
||||
image:
|
||||
repository: coredns/coredns
|
||||
tag: 1.12.0
|
||||
tag: 1.14.3
|
||||
pullPolicy: IfNotPresent
|
||||
deployment:
|
||||
dnsPolicy: ClusterFirst
|
||||
strategy:
|
||||
type: RollingUpdate
|
||||
rollingUpdate:
|
||||
maxUnavailable: 0
|
||||
maxSurge: 1
|
||||
livenessProbe:
|
||||
httpGet:
|
||||
path: /health
|
||||
port: 8080
|
||||
initialDelaySeconds: 10
|
||||
periodSeconds: 10
|
||||
timeoutSeconds: 5
|
||||
failureThreshold: 3
|
||||
readinessProbe:
|
||||
httpGet:
|
||||
path: /ready
|
||||
port: 8181
|
||||
initialDelaySeconds: 5
|
||||
periodSeconds: 5
|
||||
timeoutSeconds: 3
|
||||
failureThreshold: 3
|
||||
resources:
|
||||
limits:
|
||||
cpu: 100m
|
||||
@@ -16,21 +39,35 @@ service:
|
||||
io.cilium/lb-ipam-ips: ""
|
||||
servers:
|
||||
- zones:
|
||||
- zone: lan
|
||||
- zone: cluster.local
|
||||
port: 53
|
||||
plugins:
|
||||
- name: kubernetes
|
||||
parameters: cluster.local in-addr.arpa ip6.arpa
|
||||
configBlock: |-
|
||||
pods insecure
|
||||
fallthrough in-addr.arpa ip6.arpa
|
||||
ttl 30
|
||||
- zones:
|
||||
- zone: .
|
||||
port: 53
|
||||
plugins:
|
||||
- name: errors
|
||||
- name: health
|
||||
configBlock: lameduck 5s
|
||||
- name: ready
|
||||
- name: debug
|
||||
- name: file
|
||||
parameters: /etc/coredns/zones/lan.zone lan
|
||||
configBlock: |-
|
||||
reload 10s
|
||||
fallthrough
|
||||
- name: etcd
|
||||
parameters: lan
|
||||
configBlock: |-
|
||||
path /skydns
|
||||
endpoint http://etcd.coredns.svc.cluster.local:2379
|
||||
fallthrough
|
||||
- name: file
|
||||
parameters: /etc/coredns/zones/lan.zone
|
||||
configBlock: reload 10s
|
||||
- name: cache
|
||||
parameters: 30
|
||||
- name: loadbalance
|
||||
@@ -44,27 +81,27 @@ extraVolumes:
|
||||
configMap:
|
||||
name: coredns-lan-zone
|
||||
sops:
|
||||
lastmodified: "2026-05-02T14:39:47Z"
|
||||
mac: ENC[AES256_GCM,data:Gu0D9opwQSxNgqtv2KLMd9XGh3SbEDFXUZbPPbxuLT1jT+TwWEYSEu60PKUnU8nOdukYIoiSE3hj29Wsg3IqqjUc0oEUHn1IRPGpn/UhsvURcKgrbyEv3mGjSDicKNMyDgbTTqiPJz/K++SvmRbjJbpDtiQhRrPvw/oaVf0Cj28=,iv:DD4sk2jp6zIkRQaMTXmhfvRwz/Nnt1ecN0HjqlG9zFU=,tag:nGYLN1djfe/GzBofLPuT8g==,type:str]
|
||||
lastmodified: "2026-05-02T16:59:44Z"
|
||||
mac: ENC[AES256_GCM,data:H4uRid1Fqx4JzsF43TSGa7QcGjpXLAHiM0N3Kf4z7ab4eMlTy1+RXMV7xVT9BinjZzH6P+ENxo0yVOsdt0Yu467KJhGznNWlb2MC2TElPxZ9/yItJ+hdVGHGWbVGFWUL5NOUQ9fY2NPGw0CGr8qyftLr5Qkx0LO/VUgKWkq6RWM=,iv:9+V/sCBhfWAsIvr4DsWQgkeqQZQyT4Ti3Y+qCEZqU5c=,tag:JCRONb54BpXQzYhhPs7VGA==,type:str]
|
||||
pgp:
|
||||
- created_at: "2026-05-02T14:39:46Z"
|
||||
- created_at: "2026-05-02T16:59:43Z"
|
||||
enc: |-
|
||||
-----BEGIN PGP MESSAGE-----
|
||||
|
||||
hQIMA7uy4qQr71wiARAAic/5FcANctn1HG4gfBM8p6ElQG3oo056iQDK1dbHzkNs
|
||||
HJ3KIZjP0BPwBag2jO6TJ51Y7Wtq62lvrggIifAEHt2FiV4oxDL+oRGwPq5l6l73
|
||||
46xiTygo4X1zDcDLIX2wNv1UeiGdKA2mw2D33lHAxLQSkxuQE3/Pukb8YvXVgYNi
|
||||
2hpRFed4TpjccXkvTNL2d/yEvdqnDdHlxqboqvygIGw0u7KIhCIh+IRkjEFx0nvU
|
||||
eKEq04jTWjE8SRCbFJu1jXMNQ0jkPkwU9XkM0FtuSus48lwe+jKdo4+uYXZBDQdC
|
||||
mUkZwQy0dzOMJGSa+1kJ9V3xt/pEEEsQKNfepz1QHjgoTYsU84JOwbPRBEBBNFB0
|
||||
kvbuOYUGu9chuo9gt5ByGxetJBsH2ckKE5mNHxJ4KQOSBRM5dmaxjv8XVmVb60jo
|
||||
GXaq4Q7dVGtPiSBz0SUOdTna5+RKs1VHNbn54hRB54YNZoltJlbsjvS7weTkuDKF
|
||||
QHm0DgK9maebHSa/s434xYzyc7X3vsZ76xdUHX3ZwSLR7h4jVoWy6RP1cybWYWOg
|
||||
CFX/L/7JVYZsBu414q2+75buzi55Ja8GUTjq3T2oyxtVtnC6zr8oLZM9TFwEe+QF
|
||||
C6pXdbLOx2ToGpqbk2Ps4vTqIo0pTBbzDohycFQCiGIyOS/ZDjmJ8pMmCxPxZRjS
|
||||
XgEwhkNmirBPhGn+6DjeWJDB3p3vVy2BY7ftfGB8R+fxk4EqhhcnrZNhPvylTNqD
|
||||
A/UavumwRWNHFi0lCt9/OHON1bnrjTAUbcajaGq6D7vtSzyZcW2xL9nlJ04mOO4=
|
||||
=pcZc
|
||||
hQIMA7uy4qQr71wiAQ/9HzeTVqelbvPtluYa5xGvoYNeEEXg43CwrwZ1/z5yFWvx
|
||||
DoOCeyro5wFsNC6td7n2HVhtK0ULkfrMHH8OC+7L3bXbnlEnQzITmDggAUvfegCv
|
||||
b/7ohPkOdLvi6qXbr8bgqCZYFnPq+gUs3UOPh5Tl6wgzRSFXw2Hsb4YmQkvZJUNb
|
||||
PhPpLIUe/ECE4hmEjO5v9o3X0o7qZ3bahf9mZZlnJnvXT7R/DM8eeWTis/q0WSHE
|
||||
XnclhOX4GlMwXxa65sRrShuPcsV3qqX3VWOSWJFBhGx/FDtZTkhlHGQ9YhF2TzbB
|
||||
xxCrn87mH2W13NH6jQOQYPh1JTTJbgZZMZXgyPNmPDSYZE1kxTdrz4l4mcmCDND0
|
||||
hY3T8iR8ap2b3HhSNCqC1C0QN/bK217hTs8cJHWRRfa6jfh12imwk2XhJkB3zZxV
|
||||
O1oSb6eiP0ba0CgXu31shmfXuTAeVbTm6E50heYorjQKR5djjnOVwQUdmis1Awae
|
||||
AQTiWtBBbOgfX5WA5b6wInFr0WEsshG+YuqfB7FhJpo2SHyeFhgk47ssHWSeBpPv
|
||||
wa4OAGaMkdGoePQhApZFrBCZHslEhPE+XQlDdyOtXCmxBOcLwe59ikWLV75j0DzS
|
||||
NRUNOBYQ8Q1Y6Su/sJWW7TykQkmDirU+oIYxAngZyIyJSWvARPd6fJJvkqqg013S
|
||||
XgH1+LQJWNEJzIaLKCWbkZXnMstsOYrs4ynV4f/QZKU+Md5CgVbjy9KIC/trfNhj
|
||||
1t9kkyVVOEO7UmRhMyl8pK2gQDiOBrkhUJ5tSNFEfxM1llZ4GZRV+SUuMC3UzVA=
|
||||
=l7Wo
|
||||
-----END PGP MESSAGE-----
|
||||
fp: DC6910268E657FF70BA7EC289974494E76938DDC
|
||||
encrypted_regex: ^(password|value|ssh-key|api-key|user|username|privateKey|clientSecret|clientId|apiKey|extraArgs.*|.*Secret.*|extraEnvVars|.*SECRET.*|.*secret.*|key|.*Password|.*\.ya?ml)$
|
||||
|
||||
Reference in New Issue
Block a user