wip
This commit is contained in:
parent
0dac270e53
commit
7649edba32
4 changed files with 375 additions and 132 deletions
7
.claude/settings.json
Normal file
7
.claude/settings.json
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"permissions": {
|
||||
"allow": [
|
||||
"Read(//home/samantha/private/Knowledge/**)"
|
||||
]
|
||||
}
|
||||
}
|
||||
337
k3s/ejabberd/ejabberd.yaml
Normal file
337
k3s/ejabberd/ejabberd.yaml
Normal file
|
|
@ -0,0 +1,337 @@
|
|||
# ejabberd — XMPP server
|
||||
# Vhost: xmpp.the-fulfillment.org
|
||||
# Unpinned — scheduler places freely, local-path PVC for Mnesia data
|
||||
# TLS terminated externally by Caddy at venture ingress VPS
|
||||
# (HTTP admin/BOSH/websocket on 5280 is served plain; Caddy fronts it)
|
||||
# (c2s/s2s use ejabberd's auto-generated self-signed cert for STARTTLS
|
||||
# until real certs are mounted — see "TLS notes" below)
|
||||
# No STUN/TURN — add later when available
|
||||
# No MQTT — skipped
|
||||
#
|
||||
# Storage:
|
||||
# Mnesia (on-disk, via PVC) — default backend for most modules
|
||||
# PostgreSQL (cluster-local `postgres` service) — only mod_mam (archive + archive_prefs)
|
||||
# DB schema loaded from /home/ejabberd/sql/pg.new.sql into ejabberd_db.
|
||||
# SQL password lives in ejabberd-secret and is injected into the rendered
|
||||
# config at pod start by the `render-config` init container (sed).
|
||||
#
|
||||
# NodePorts:
|
||||
# 32378 — XMPP c2s (5222)
|
||||
# 32381 — XMPP s2s federation (5269)
|
||||
# 32382 — HTTP admin / BOSH / websocket / HTTP upload (5280)
|
||||
#
|
||||
# Deploy:
|
||||
# kubectl create secret generic ejabberd-secret \
|
||||
# --from-literal=admin-password='<password>' \
|
||||
# --from-literal=erlang-cookie='<random-long-string>' \
|
||||
# --from-literal=db-password='<postgres-password-for-ejabberd_user>'
|
||||
#
|
||||
# # Create DB + user + schema (one-shot, from a host with kubectl):
|
||||
# kubectl exec -i deploy/postgres -- psql -U postgres <<SQL
|
||||
# CREATE USER ejabberd_user WITH PASSWORD '<db-password>';
|
||||
# CREATE DATABASE ejabberd_db ENCODING 'UTF8' LC_COLLATE 'C' LC_CTYPE 'C'
|
||||
# TEMPLATE template0 OWNER ejabberd_user;
|
||||
# SQL
|
||||
# kubectl exec deploy/ejabberd -- cat /home/ejabberd/sql/pg.new.sql \
|
||||
# | kubectl exec -i deploy/postgres -- psql -U ejabberd_user -d ejabberd_db
|
||||
#
|
||||
# kubectl apply -f ejabberd.yaml -n <ns>
|
||||
#
|
||||
# First startup does NOT auto-register the admin (CTL_ON_CREATE entrypoint hook
|
||||
# doesn't expand shell vars). Register manually:
|
||||
# kubectl exec deploy/ejabberd -- ejabberdctl register admin xmpp.the-fulfillment.org <admin-password>
|
||||
#
|
||||
# Admin web UI: http://<any-node-wg-ip>:32382/admin
|
||||
# (login: admin@xmpp.the-fulfillment.org / <admin-password>)
|
||||
#
|
||||
# TLS notes:
|
||||
# For production federation, mount real certs for xmpp.the-fulfillment.org
|
||||
# at /home/ejabberd/conf/server.pem (PEM with privkey + fullchain) and
|
||||
# set certfiles in the ConfigMap to point at it. Many federating servers
|
||||
# reject self-signed s2s peers.
|
||||
#
|
||||
# User registration is CLOSED by default — admin must create accounts via:
|
||||
# kubectl exec deploy/ejabberd -- ejabberdctl register <user> xmpp.the-fulfillment.org <password>
|
||||
|
||||
---
|
||||
apiVersion: v1
|
||||
kind: PersistentVolumeClaim
|
||||
metadata:
|
||||
name: ejabberd-data-pvc
|
||||
spec:
|
||||
accessModes:
|
||||
- ReadWriteOnce
|
||||
storageClassName: local-path
|
||||
resources:
|
||||
requests:
|
||||
storage: 10Gi
|
||||
|
||||
---
|
||||
apiVersion: v1
|
||||
kind: ConfigMap
|
||||
metadata:
|
||||
name: ejabberd-config
|
||||
data:
|
||||
ejabberd.yml: |
|
||||
hosts:
|
||||
- "xmpp.the-fulfillment.org"
|
||||
|
||||
loglevel: info
|
||||
|
||||
## ejabberd will auto-generate a self-signed cert on first run.
|
||||
## Replace with real certs for production federation.
|
||||
certfiles: []
|
||||
|
||||
## PostgreSQL — used only by mod_mam (see modules section).
|
||||
## Password is substituted into a rendered copy of this file at pod
|
||||
## start by the `render-config` init container.
|
||||
sql_type: pgsql
|
||||
sql_server: postgres
|
||||
sql_port: 5432
|
||||
sql_database: ejabberd_db
|
||||
sql_username: ejabberd_user
|
||||
sql_password: "__SQL_PASSWORD__"
|
||||
|
||||
listen:
|
||||
-
|
||||
port: 5222
|
||||
ip: "::"
|
||||
module: ejabberd_c2s
|
||||
max_stanza_size: 262144
|
||||
shaper: c2s_shaper
|
||||
access: c2s
|
||||
starttls: true
|
||||
-
|
||||
port: 5269
|
||||
ip: "::"
|
||||
module: ejabberd_s2s_in
|
||||
max_stanza_size: 524288
|
||||
-
|
||||
port: 5280
|
||||
ip: "::"
|
||||
module: ejabberd_http
|
||||
request_handlers:
|
||||
"/admin": ejabberd_web_admin
|
||||
"/api": mod_http_api
|
||||
"/bosh": mod_bosh
|
||||
"/ws": ejabberd_http_ws
|
||||
"/upload": mod_http_upload
|
||||
|
||||
s2s_use_starttls: optional
|
||||
|
||||
acl:
|
||||
admin:
|
||||
user:
|
||||
- "admin@xmpp.the-fulfillment.org"
|
||||
local:
|
||||
user_regexp: ""
|
||||
|
||||
access_rules:
|
||||
local:
|
||||
allow: local
|
||||
c2s:
|
||||
deny: blocked
|
||||
allow: all
|
||||
announce:
|
||||
allow: admin
|
||||
configure:
|
||||
allow: admin
|
||||
muc_create:
|
||||
allow: local
|
||||
pubsub_createnode:
|
||||
allow: local
|
||||
register:
|
||||
deny: all
|
||||
trusted_network:
|
||||
allow: loopback
|
||||
|
||||
api_permissions:
|
||||
"console commands":
|
||||
from: ejabberd_ctl
|
||||
who: all
|
||||
what: "*"
|
||||
"admin access":
|
||||
who:
|
||||
access:
|
||||
allow:
|
||||
acl: admin
|
||||
what:
|
||||
- "*"
|
||||
- "!stop"
|
||||
- "!start"
|
||||
|
||||
shaper:
|
||||
normal:
|
||||
rate: 3000
|
||||
burst_size: 20000
|
||||
fast: 100000
|
||||
|
||||
shaper_rules:
|
||||
max_user_sessions: 10
|
||||
max_user_offline_messages:
|
||||
5000: admin
|
||||
100: all
|
||||
c2s_shaper:
|
||||
none: admin
|
||||
normal: all
|
||||
s2s_shaper: fast
|
||||
|
||||
modules:
|
||||
mod_adhoc: {}
|
||||
mod_admin_extra: {}
|
||||
mod_announce:
|
||||
access: announce
|
||||
mod_avatar: {}
|
||||
mod_blocking: {}
|
||||
mod_bosh: {}
|
||||
mod_caps: {}
|
||||
mod_carboncopy: {}
|
||||
mod_client_state: {}
|
||||
mod_configure: {}
|
||||
mod_disco: {}
|
||||
mod_http_api: {}
|
||||
mod_http_upload:
|
||||
put_url: "http://@HOST@:5280/upload"
|
||||
max_size: 104857600 # 100 MB
|
||||
mod_last: {}
|
||||
mod_mam:
|
||||
db_type: sql
|
||||
assume_mam_usage: true
|
||||
default: always
|
||||
mod_muc:
|
||||
access:
|
||||
- allow
|
||||
access_admin:
|
||||
- allow: admin
|
||||
access_create: muc_create
|
||||
access_persistent: muc_create
|
||||
default_room_options:
|
||||
mam: true
|
||||
mod_offline:
|
||||
access_max_user_messages: max_user_offline_messages
|
||||
mod_ping: {}
|
||||
mod_privacy: {}
|
||||
mod_private: {}
|
||||
mod_pubsub:
|
||||
access_createnode: pubsub_createnode
|
||||
plugins:
|
||||
- flat
|
||||
- pep
|
||||
mod_push: {}
|
||||
mod_push_keepalive: {}
|
||||
mod_roster:
|
||||
versioning: true
|
||||
mod_sic: {}
|
||||
mod_stream_mgmt:
|
||||
resend_on_timeout: if_offline
|
||||
mod_vcard: {}
|
||||
mod_vcard_xupdate: {}
|
||||
mod_version:
|
||||
show_os: false
|
||||
|
||||
---
|
||||
apiVersion: apps/v1
|
||||
kind: Deployment
|
||||
metadata:
|
||||
name: ejabberd
|
||||
spec:
|
||||
replicas: 1
|
||||
strategy:
|
||||
type: Recreate
|
||||
selector:
|
||||
matchLabels:
|
||||
app: ejabberd
|
||||
template:
|
||||
metadata:
|
||||
labels:
|
||||
app: ejabberd
|
||||
spec:
|
||||
securityContext:
|
||||
fsGroup: 9000
|
||||
initContainers:
|
||||
## Render ejabberd.yml from template, substituting the SQL password
|
||||
## from the ejabberd-secret. Avoids baking the password into the ConfigMap.
|
||||
- name: render-config
|
||||
image: busybox:1.37
|
||||
env:
|
||||
- name: SQL_PASSWORD
|
||||
valueFrom:
|
||||
secretKeyRef:
|
||||
name: ejabberd-secret
|
||||
key: db-password
|
||||
command:
|
||||
- /bin/sh
|
||||
- -c
|
||||
- |
|
||||
sed "s|__SQL_PASSWORD__|${SQL_PASSWORD}|" /template/ejabberd.yml > /rendered/ejabberd.yml
|
||||
volumeMounts:
|
||||
- name: config-template
|
||||
mountPath: /template
|
||||
- name: config-rendered
|
||||
mountPath: /rendered
|
||||
containers:
|
||||
- name: ejabberd
|
||||
image: ejabberd/ecs:latest
|
||||
env:
|
||||
- name: ERLANG_NODE
|
||||
value: ejabberd@localhost
|
||||
- name: ERLANG_COOKIE
|
||||
valueFrom:
|
||||
secretKeyRef:
|
||||
name: ejabberd-secret
|
||||
key: erlang-cookie
|
||||
ports:
|
||||
- name: c2s
|
||||
containerPort: 5222
|
||||
- name: s2s
|
||||
containerPort: 5269
|
||||
- name: http
|
||||
containerPort: 5280
|
||||
volumeMounts:
|
||||
- name: config-rendered
|
||||
mountPath: /home/ejabberd/conf/ejabberd.yml
|
||||
subPath: ejabberd.yml
|
||||
- name: data
|
||||
mountPath: /home/ejabberd/database
|
||||
readinessProbe:
|
||||
tcpSocket:
|
||||
port: 5222
|
||||
initialDelaySeconds: 20
|
||||
periodSeconds: 10
|
||||
livenessProbe:
|
||||
tcpSocket:
|
||||
port: 5222
|
||||
initialDelaySeconds: 60
|
||||
periodSeconds: 30
|
||||
volumes:
|
||||
- name: config-template
|
||||
configMap:
|
||||
name: ejabberd-config
|
||||
- name: config-rendered
|
||||
emptyDir: {}
|
||||
- name: data
|
||||
persistentVolumeClaim:
|
||||
claimName: ejabberd-data-pvc
|
||||
|
||||
---
|
||||
apiVersion: v1
|
||||
kind: Service
|
||||
metadata:
|
||||
name: ejabberd
|
||||
spec:
|
||||
selector:
|
||||
app: ejabberd
|
||||
ports:
|
||||
- name: c2s
|
||||
port: 5222
|
||||
targetPort: 5222
|
||||
nodePort: 32378
|
||||
- name: s2s
|
||||
port: 5269
|
||||
targetPort: 5269
|
||||
nodePort: 32381
|
||||
- name: http
|
||||
port: 5280
|
||||
targetPort: 5280
|
||||
nodePort: 32382
|
||||
type: NodePort
|
||||
|
|
@ -1,29 +1,48 @@
|
|||
# Monerod — Monero full node (pruned)
|
||||
# NAS-backed PVC for blockchain data — unpinned, free to migrate across nodes
|
||||
# Ban list stored on NAS alongside blockchain data
|
||||
# Pinned to game-worker-hdd — blockchain data lives on local disk at
|
||||
# /home/samantha/.bitmonero (LMDB/mmap is NFS-hostile, must stay local)
|
||||
# Ban list stored alongside blockchain data
|
||||
# NodePorts: 32379 (P2P), 32380 (restricted RPC)
|
||||
#
|
||||
# Prerequisites:
|
||||
# NAS share /volume1/samantha-private/.bitmonero must exist on Synology
|
||||
# Copy ban list to NAS: /volume1/samantha-private/.bitmonero/ban_list.txt
|
||||
# nas-pv.yaml must be applied first
|
||||
# nfs-common installed on all worker VMs
|
||||
# /home/samantha/.bitmonero must exist on game-worker-hdd with blockchain data
|
||||
# ban_list.txt must exist in that directory
|
||||
#
|
||||
# Deploy:
|
||||
# kubectl apply -f ../storage/nas-pv.yaml # once, if not already applied
|
||||
# kubectl apply -f monerod.yaml -n <ns>
|
||||
|
||||
---
|
||||
apiVersion: v1
|
||||
kind: PersistentVolume
|
||||
metadata:
|
||||
name: monerod-pv
|
||||
spec:
|
||||
capacity:
|
||||
storage: 200Gi
|
||||
accessModes:
|
||||
- ReadWriteOnce
|
||||
persistentVolumeReclaimPolicy: Retain
|
||||
storageClassName: local-storage
|
||||
local:
|
||||
path: /home/samantha/.bitmonero
|
||||
nodeAffinity:
|
||||
required:
|
||||
nodeSelectorTerms:
|
||||
- matchExpressions:
|
||||
- key: kubernetes.io/hostname
|
||||
operator: In
|
||||
values:
|
||||
- game-worker-hdd
|
||||
|
||||
---
|
||||
apiVersion: v1
|
||||
kind: PersistentVolumeClaim
|
||||
metadata:
|
||||
name: monerod-pvc
|
||||
annotations:
|
||||
nfs.io/storage-path: ".bitmonero"
|
||||
spec:
|
||||
accessModes:
|
||||
- ReadWriteMany
|
||||
storageClassName: nas-nfs
|
||||
- ReadWriteOnce
|
||||
storageClassName: local-storage
|
||||
resources:
|
||||
requests:
|
||||
storage: 200Gi
|
||||
|
|
@ -43,6 +62,7 @@ spec:
|
|||
labels:
|
||||
app: monerod
|
||||
spec:
|
||||
nodeName: game-worker-hdd
|
||||
containers:
|
||||
- name: monerod
|
||||
image: ghcr.io/sethforprivacy/simple-monerod:latest
|
||||
|
|
|
|||
|
|
@ -1,121 +0,0 @@
|
|||
# Snikket — XMPP server (Prosody-based)
|
||||
# Unpinned — scheduler places freely, local-path PVC
|
||||
# TLS terminated externally by Caddy at venture ingress VPS
|
||||
# NodePorts: 32381 (web/admin), 32382 (XMPP client), 32383 (XMPP federation), 32384 (file transfer proxy)
|
||||
#
|
||||
# Deploy:
|
||||
# kubectl apply -f snikket.yaml -n <ns>
|
||||
#
|
||||
# Caddy must proxy port 80 traffic (invites/admin portal) via NodePort 32381
|
||||
# XMPP client connections on 32382 must be reachable directly (not HTTP — raw TCP)
|
||||
# XMPP federation on 32383 must be reachable directly (raw TCP)
|
||||
|
||||
---
|
||||
apiVersion: v1
|
||||
kind: PersistentVolumeClaim
|
||||
metadata:
|
||||
name: snikket-pvc
|
||||
spec:
|
||||
accessModes:
|
||||
- ReadWriteOnce
|
||||
storageClassName: local-path
|
||||
resources:
|
||||
requests:
|
||||
storage: 10Gi
|
||||
|
||||
---
|
||||
apiVersion: apps/v1
|
||||
kind: Deployment
|
||||
metadata:
|
||||
name: snikket-web
|
||||
spec:
|
||||
replicas: 1
|
||||
selector:
|
||||
matchLabels:
|
||||
app: snikket-web
|
||||
template:
|
||||
metadata:
|
||||
labels:
|
||||
app: snikket-web
|
||||
spec:
|
||||
containers:
|
||||
- name: snikket-web
|
||||
image: snikket/snikket-server:latest
|
||||
command: ["web"]
|
||||
ports:
|
||||
- containerPort: 80
|
||||
volumeMounts:
|
||||
- name: snikket-data
|
||||
mountPath: /snikket
|
||||
volumes:
|
||||
- name: snikket-data
|
||||
persistentVolumeClaim:
|
||||
claimName: snikket-pvc
|
||||
|
||||
---
|
||||
apiVersion: apps/v1
|
||||
kind: Deployment
|
||||
metadata:
|
||||
name: snikket-server
|
||||
spec:
|
||||
replicas: 1
|
||||
selector:
|
||||
matchLabels:
|
||||
app: snikket-server
|
||||
template:
|
||||
metadata:
|
||||
labels:
|
||||
app: snikket-server
|
||||
spec:
|
||||
containers:
|
||||
- name: snikket-server
|
||||
image: snikket/snikket-server:latest
|
||||
command: ["server"]
|
||||
ports:
|
||||
- containerPort: 5222
|
||||
- containerPort: 5269
|
||||
- containerPort: 5000
|
||||
volumeMounts:
|
||||
- name: snikket-data
|
||||
mountPath: /snikket
|
||||
volumes:
|
||||
- name: snikket-data
|
||||
persistentVolumeClaim:
|
||||
claimName: snikket-pvc
|
||||
|
||||
---
|
||||
apiVersion: v1
|
||||
kind: Service
|
||||
metadata:
|
||||
name: snikket-web
|
||||
spec:
|
||||
selector:
|
||||
app: snikket-web
|
||||
ports:
|
||||
- port: 80
|
||||
targetPort: 80
|
||||
nodePort: 32381
|
||||
type: NodePort
|
||||
|
||||
---
|
||||
apiVersion: v1
|
||||
kind: Service
|
||||
metadata:
|
||||
name: snikket
|
||||
spec:
|
||||
selector:
|
||||
app: snikket-server
|
||||
ports:
|
||||
- name: xmpp-client
|
||||
port: 5222
|
||||
targetPort: 5222
|
||||
nodePort: 32382
|
||||
- name: xmpp-federation
|
||||
port: 5269
|
||||
targetPort: 5269
|
||||
nodePort: 32383
|
||||
- name: file-transfer
|
||||
port: 5000
|
||||
targetPort: 5000
|
||||
nodePort: 32384
|
||||
type: NodePort
|
||||
Loading…
Reference in a new issue