Compare commits

..
Author SHA1 Message Date
claude-botandClaude Opus 5.5 286564a0d7 fix(kuma-sync): create when the previous monitor ID belongs to another owner
ci/woodpecker/pr/ci-scripts-test Pipeline was successful
review-bot reviewed: comment
After a Kuma database loss or restore, IDs restart and a resource's
status.monitorID can point at a monitor that now carries another
resource's ownership tag. That proves our monitor is gone, so the
controller creates a new one instead of parking at NotOwned forever.
Only an untagged monitor at the previous ID still blocks the create
(tag removed by hand), as before.

Residual Important finding from the kuma-sync final review.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-19 08:12:45 +02:00
k.renner 1dc5ae7816 Merge pull request 'test(kuma-sync): remove smoke-test KumaMonitor' (#1353) from chore/kuma-sync-smoke-remove into master
Reviewed-on: k.renner/homelab#1353
2026-10-19 06:04:39 +00:00
claude-botandClaude Opus 5.5 ada5b7ea4d test(kuma-sync): remove smoke-test KumaMonitor
ci/woodpecker/pr/ci-scripts-test Pipeline was successful
ci/woodpecker/pr/ci-manifests-test Pipeline was successful
review-bot skipped: closed
Last smoke-test step: Flux prunes the KumaMonitor and the controller's
finalizer deletes Kuma monitor 9.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-19 08:02:48 +02:00
k.renner 38c186d424 Merge pull request 'test(kuma-sync): live smoke-test KumaMonitor' (#1351) from feat/kuma-sync-smoke into master
ci/woodpecker/cron/alert-monitor Pipeline was successful
Reviewed-on: k.renner/homelab#1351
2026-10-19 06:00:17 +00:00
security-bot d659097b8f chore(image-automation): bump gitea.renner.uno/gitea_admin/ci-backup-verify:2026-10-19
Updates managed by image-automation-controller.
2026-10-19 06:00:13 +00:00
security-bot 4baf5aa8be chore(image-automation): bump gitea.renner.uno/gitea_admin/authentik-gate-sync:2026-10-19-0544
Updates managed by image-automation-controller.
2026-10-19 05:58:07 +00:00
claude-botandClaude Opus 5.5 fafc73cb3f test(kuma-sync): live smoke-test KumaMonitor for www.renner.uno
ci/woodpecker/pr/ci-scripts-test Pipeline was successful
review-bot reviewed: comment
ci/woodpecker/pr/ci-manifests-test Pipeline was successful
Keyword check on https://www.renner.uno/ (page title "Familie Renner")
with certificate-expiry notification. Exercises create, tagging,
restart adoption and deletion against the live Kuma; removed from git
again as the last smoke-test step.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-19 07:58:00 +02:00
k.renner ab876a1231 Merge pull request 'feat(kuma-sync): deploy controller (Task 7)' (#1350) from feat/kuma-sync-deploy into master
Reviewed-on: k.renner/homelab#1350
2026-10-19 05:56:20 +00:00
security-bot d8d676b711 chore(image-automation): bump gitea.renner.uno/k.renner/shelly-manager:build.1792387459
Updates managed by image-automation-controller.
2026-10-19 05:48:49 +00:00
security-bot 3f43d5fa17 chore(image-automation): bump gitea.renner.uno/gitea_admin/review-bot:2026-10-19-0540
ci/woodpecker/cron/alert-monitor Pipeline was successful
Updates managed by image-automation-controller.
2026-10-19 05:45:09 +00:00
security-bot 142a21883d chore(image-automation): bump gitea.renner.uno/gitea_admin/authentik-gate-sync:2026-10-19-0518 docker.gitea.com/gitea-mcp-server:1.10.0
ci/woodpecker/cron/alert-monitor Pipeline was successful
ci/woodpecker/cron/issue-fix Pipeline was successful
Updates managed by image-automation-controller.
2026-10-19 05:28:07 +00:00
k.renner dc3a299cf6 Merge pull request 'chore(ci): bump ci-claude image to 2.1.303' (#1349) from ci-image/claude-2.1.303 into master
Reviewed-on: k.renner/homelab#1349
2026-10-19 05:24:52 +00:00
k.renner b73e1b5636 Merge pull request 'chore(deps): update helm release openbao to >=0.30.4 <0.31.0' (#1348) from renovate/openbao into master
Reviewed-on: k.renner/homelab#1348
2026-10-19 05:19:50 +00:00
k.renner c8d2d073a5 Merge pull request 'chore(deps): pin dependencies' (#1343) from renovate/pin-image-digests into master
Reviewed-on: k.renner/homelab#1343
2026-10-19 05:19:20 +00:00
claude-bot 8d3b3c4324 chore(ci): bump ci-claude image to 2.1.303
ci/woodpecker/pr/ci-scripts-test Pipeline was successful
review-bot reviewed: comment
ci/woodpecker/pr/ci-manifests-test Pipeline was successful
2026-10-19 05:18:31 +00:00
k.renner 7b1041c188 Merge pull request 'chore(deps): update home-assistant non-major' (#1346) from renovate/home-assistant-minor-patch into master
Reviewed-on: k.renner/homelab#1346
2026-10-19 05:18:13 +00:00
k.renner 9e62fadcb1 Merge pull request 'chore(deps): update ci non-major' (#1345) from renovate/ci-minor-patch into master
ci/woodpecker/push/ci-claude-refresh Pipeline was successful
ci/woodpecker/push/build-ci-images Pipeline was successful
Reviewed-on: k.renner/homelab#1345
2026-10-19 05:17:04 +00:00
renovate-bot 94090c68c3 chore(deps): update helm release openbao to >=0.30.4 <0.31.0
review-bot reviewed: comment
ci/woodpecker/pr/ci-scripts-test Pipeline was successful
ci/woodpecker/pr/ci-manifests-test Pipeline was successful
2026-10-19 02:02:09 +00:00
renovate-bot b555277634 chore(deps): update home-assistant non-major
review-bot reviewed: comment
ci/woodpecker/pr/ci-scripts-test Pipeline was successful
ci/woodpecker/pr/ci-manifests-test Pipeline was successful
2026-10-19 02:02:00 +00:00
renovate-bot f8b98907e8 chore(deps): update ci non-major
ci/woodpecker/pr/ci-scripts-test Pipeline was successful
review-bot reviewed: comment
ci/woodpecker/pr/ci-manifests-test Pipeline was successful
2026-10-19 02:01:57 +00:00
renovate-bot d7d99365e8 chore(deps): pin dependencies
ci/woodpecker/pr/ci-scripts-test Pipeline was successful
ci/woodpecker/pr/ci-manifests-test Pipeline was successful
review-bot reviewed: request changes
2026-10-19 02:01:50 +00:00
20 changed files with 38 additions and 34 deletions
+1 -1
View File
@@ -101,7 +101,7 @@ steps:
bash scripts/ci/make-diag-kubeconfig.sh
- name: alert-triage-agent
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.302
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.303
environment:
CLAUDE_CODE_OAUTH_TOKEN:
from_secret: claude_code_oauth_token
+4 -4
View File
@@ -35,25 +35,25 @@ when:
steps:
- name: model-selection-tests
depends_on: []
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.302
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.303
commands:
- sh scripts/ci/test-model-selection.sh
- name: pr-review-mistral-tests
depends_on: []
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.302
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.303
commands:
- sh scripts/ci/test-pr-review-mistral.sh
- name: promtool-rules-guard-tests
depends_on: []
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.302
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.303
commands:
- sh scripts/ci/test-promtool-rules.sh
- name: yaml-citations-guard-tests
depends_on: []
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.302
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.303
commands:
- sh scripts/ci/test-yaml-citations.sh
+1 -1
View File
@@ -26,7 +26,7 @@ steps:
# fetch-models.sh response mapping. No cluster, no secrets, no network — the
# ci-claude image just provides sh + jq. Keeps the flag-injection regression
# test from rotting (it exercises the exact injection shapes).
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.302
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.303
commands:
- sh scripts/ci/test-model-selection.sh
+1 -1
View File
@@ -62,7 +62,7 @@ steps:
- bash scripts/ci/make-diag-kubeconfig.sh
- name: issue-fix-agent
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.302
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.303
environment:
CLAUDE_CODE_OAUTH_TOKEN:
from_secret: claude_code_oauth_token
+3 -3
View File
@@ -18,12 +18,12 @@ when:
steps:
- name: iac-scan
image: aquasec/trivy:latest@sha256:af6acf9a6b85dfe389a1941505c0ce9efef52a4719635e1a962f022a3d855daa
image: aquasec/trivy:latest@sha256:2416d1f74045b57274df1a340eee6b510cacd73c66a6ccb8da092b117eb7d222
commands:
- trivy fs --format json -o trivy-iac.json --severity CRITICAL,HIGH --ignore-unfixed .
- name: image-scans
image: aquasec/trivy:latest@sha256:af6acf9a6b85dfe389a1941505c0ce9efef52a4719635e1a962f022a3d855daa
image: aquasec/trivy:latest@sha256:2416d1f74045b57274df1a340eee6b510cacd73c66a6ccb8da092b117eb7d222
commands:
- trivy image --download-db-only
- |
@@ -70,7 +70,7 @@ steps:
# this step is skipped — otherwise we'd fork-bomb PRs.
when:
- branch: master
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.302
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.303
environment:
CLAUDE_CODE_OAUTH_TOKEN:
from_secret: claude_code_oauth_token
+1 -1
View File
@@ -30,7 +30,7 @@ when:
steps:
- name: update-audit-agent
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.302
image: gitea.renner.uno/gitea_admin/ci-claude:2.1.303
environment:
CLAUDE_CODE_OAUTH_TOKEN:
from_secret: claude_code_oauth_token
+2 -2
View File
@@ -5,12 +5,12 @@
# The unit tests gate the image: the final stage copies the controller out of
# this stage, so a failing test fails the build.
FROM python:3.14-slim@sha256:a2b82f3c48559aa0a8446d9af49826b6e2b2016f4cd2afabfe6013ec53729170 AS test
FROM python:3.15-slim@sha256:2da676046630d7bf14c6764ae1143dc7fa0377a53f94bf5a642f0b214aca5bce AS test
WORKDIR /src
COPY controller.py test_controller.py ./
RUN python3 -B -m unittest -v
FROM python:3.14-slim@sha256:a2b82f3c48559aa0a8446d9af49826b6e2b2016f4cd2afabfe6013ec53729170
FROM python:3.15-slim@sha256:2da676046630d7bf14c6764ae1143dc7fa0377a53f94bf5a642f0b214aca5bce
RUN useradd --system --no-create-home --shell /usr/sbin/nologin controller
COPY --from=test /src/controller.py /opt/controller.py
+1 -1
View File
@@ -1,4 +1,4 @@
FROM node:24-alpine@sha256:ebfe2f90462722a7a4de65e91990e97fe0d401c70e0e762c5b53302f905ec1c1
FROM node:24-alpine@sha256:44fce696f38ba8c987c4db89954051000bbd05ffd8d8659ba15ed4a8602e937f
# Default to the latest Claude Code. Pinning a fixed version is the wrong
# default here: old releases eventually stop working against the API, so a
+2 -2
View File
@@ -23,7 +23,7 @@
# namespace, so can0 is only reachable with network_mode: host. That is also
# how the local MQTT broker on 127.0.0.1:1883 is reached. CAN_RAW sockets need
# no capabilities, so both run unprivileged.
FROM python:3.14-slim@sha256:a2b82f3c48559aa0a8446d9af49826b6e2b2016f4cd2afabfe6013ec53729170 AS build
FROM python:3.15-slim@sha256:2da676046630d7bf14c6764ae1143dc7fa0377a53f94bf5a642f0b214aca5bce AS build
# Pins live here, in the artifact, rather than in Ansible variables.
#
@@ -56,7 +56,7 @@ RUN git clone --quiet https://github.com/MyHomeMyData/E3onCAN.git /opt/e3oncan \
&& rm -rf /opt/e3oncan/.git
FROM python:3.14-slim@sha256:a2b82f3c48559aa0a8446d9af49826b6e2b2016f4cd2afabfe6013ec53729170
FROM python:3.15-slim@sha256:2da676046630d7bf14c6764ae1143dc7fa0377a53f94bf5a642f0b214aca5bce
ARG OPEN3E_REF=6553c10453a6bae1210908f38a5af2481a46a3e5
ARG E3ONCAN_REF=461dcbdf97e8d72d2edb9929c63b39382af6c3a1
@@ -133,18 +133,19 @@ func (r *Reconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl.Resu
var id int64
if res.mon == nil {
// The monitor this resource synced before may have lost its tag; a
// second one would then sit beside it.
// second one would then sit beside it. An ID now carrying another
// owner's key was reused by Kuma, so ours is gone.
if prev := km.Status.MonitorID; prev != 0 {
found, key, err := r.Kuma.Probe(ctx, prev)
switch {
case err != nil:
return r.fail(ctx, km, &failure{ReasonKumaUnavailable, msgKumaUnavailable, err})
case found && key != desired.OwnerKey:
case found && key == "":
log.FromContext(ctx).Error(nil, "previous monitor exists without our ownership tag, not creating another",
"ownerKey", desired.OwnerKey, "monitorID", prev, "tagValue", key)
err := r.setReady(ctx, km, metav1.ConditionFalse, ReasonNotOwned, msgNotOwned, nil)
return ctrl.Result{RequeueAfter: r.resync()}, err
case found:
case found && key == desired.OwnerKey:
return r.fail(ctx, km, &failure{ReasonKumaUnavailable, msgKumaUnavailable,
fmt.Errorf("monitor %d carries our key but is missing from the owned list", prev)})
}
@@ -428,7 +428,7 @@ func TestReconcileRefusesCreateBesideUntaggedPrevious(t *testing.T) {
}
}
func TestReconcileRefusesCreateBesideOtherOwnersMonitor(t *testing.T) {
func TestReconcileCreatesWhenPreviousIDReusedByOtherOwner(t *testing.T) {
e := newEnv(t, withPreviousMonitor(1))
if _, err := e.kuma.Create(t.Context(), kumaclient.Monitor{Name: "x", OwnerKey: "default/other"}); err != nil {
t.Fatal(err)
@@ -436,12 +436,15 @@ func TestReconcileRefusesCreateBesideOtherOwnersMonitor(t *testing.T) {
if _, err := e.reconcile(t, "a"); err != nil {
t.Fatal(err)
}
if e.cnt.creates != 0 {
t.Errorf("creates = %d, want 0", e.cnt.creates)
if e.cnt.creates != 1 {
t.Errorf("creates = %d, want 1", e.cnt.creates)
}
if c := ready(t, e.get(t, "a")); c.Reason != ReasonNotOwned {
if c := ready(t, e.get(t, "a")); c.Reason != ReasonSynced {
t.Errorf("Ready = %+v", c)
}
if m := e.kuma.Get(1); m == nil || m.OwnerKey != "default/other" {
t.Errorf("other owner's monitor 1 = %+v, want untouched", m)
}
}
func TestReconcileCreatesWhenPreviousMonitorIsGone(t *testing.T) {
+1 -1
View File
@@ -2,7 +2,7 @@
# domains -> TLS passthrough -> Traefik ClusterIP) from Ingresses carrying the
# public label. Standard library only, so the image is the interpreter plus one
# file; runs unprivileged as its own user.
FROM python:3.14-slim@sha256:a2b82f3c48559aa0a8446d9af49826b6e2b2016f4cd2afabfe6013ec53729170
FROM python:3.15-slim@sha256:2da676046630d7bf14c6764ae1143dc7fa0377a53f94bf5a642f0b214aca5bce
RUN useradd --system --no-create-home --shell /usr/sbin/nologin controller
COPY controller.py /opt/controller.py
+1 -1
View File
@@ -114,7 +114,7 @@ spec:
type: RuntimeDefault
containers:
- name: controller
image: gitea.renner.uno/gitea_admin/authentik-gate-sync:2026-10-15-0857 # {"$imagepolicy": "flux-system:authentik-gate-sync"}
image: gitea.renner.uno/gitea_admin/authentik-gate-sync:2026-10-19-0544 # {"$imagepolicy": "flux-system:authentik-gate-sync"}
securityContext:
allowPrivilegeEscalation: false
readOnlyRootFilesystem: true
@@ -61,7 +61,7 @@ spec:
type: RuntimeDefault
containers:
- name: shelly-manager
image: gitea.renner.uno/k.renner/shelly-manager:build.1791777553 # {"$imagepolicy": "flux-system:shelly-manager"}
image: gitea.renner.uno/k.renner/shelly-manager:build.1792387459 # {"$imagepolicy": "flux-system:shelly-manager"}
imagePullPolicy: IfNotPresent
ports:
- name: http
@@ -159,7 +159,7 @@ spec:
# substitution to POD_IP so nginx-runtime variables like $host
# / $http_x_forwarded_for in the template stay intact.
- name: proxy
image: nginxinc/nginx-unprivileged:1.31-alpine@sha256:b9241c6e7b8e9a862f129d8d4199ab64b10390949a78bdd5603379b32c844083
image: nginxinc/nginx-unprivileged:1.31-alpine@sha256:378d0c32f6562f7fd9629170797f57d2b953aa09be983b3daaf4809bb039ca00
env:
- name: POD_IP
valueFrom:
@@ -203,7 +203,7 @@ spec:
# readiness probe on purpose: a broker outage must not take HA out of
# its Service endpoints.
- name: mqtt-tls
image: ghostunnel/ghostunnel:v1.11.3@sha256:2599b8a04bae16d70a4209495618dea61b46a00a9a05fcf74da282688ad3517f
image: ghostunnel/ghostunnel:v1.11.4@sha256:e5248233863aadd36383a11c92360f2981141881ef05e38360a6ada8630d36b1
args:
- client
- --listen=127.0.0.1:11883
@@ -304,7 +304,7 @@ spec:
# dedicated long-lived token.
# Runs as root to match HA's root-owned /config files. See config-sync.sh.
- name: config-sync
image: alpine/git:2.54.0@sha256:ce84fd6a057b4dc5cf5009da2dd832f1c6d096c1984bf50496cf3c256402264d
image: alpine/git:2.54.0@sha256:03228d7ded483b0b3e55e1de7fa660d70d3e1bb432fa7021d29e192640de11aa
command: ["/bin/sh", "/scripts/sync.sh"]
env:
- name: SYNC_BRANCH
+1 -1
View File
@@ -32,7 +32,7 @@ spec:
type: RuntimeDefault
containers:
- name: review-bot
image: gitea.renner.uno/gitea_admin/review-bot:2026-10-18-0706 # {"$imagepolicy": "flux-system:review-bot"}
image: gitea.renner.uno/gitea_admin/review-bot:2026-10-19-0540 # {"$imagepolicy": "flux-system:review-bot"}
env:
- name: REPOS
value: k.renner/homelab,konairius/homeassistant,konairius/authentik-samba-bridge,konairius/shelly-manager
@@ -4,7 +4,7 @@ metadata:
name: gitea-mcp
namespace: flux-system
spec:
image: docker.gitea.com/gitea-mcp-server
image: docker.gitea.com/gitea-mcp-server@sha256:20701c3dcf3b71df384417d04f9f6382205b7f362380b258fb8e4dcf9599091f
interval: 1h
---
apiVersion: image.toolkit.fluxcd.io/v1
@@ -24,7 +24,7 @@ spec:
# window. The StatefulSet rolls one pod at a time (updateStrategyType
# below). Undo after a pod has run the new server = restore the
# snapshot, not a git revert.
version: ">=0.30.3 <0.31.0"
version: ">=0.30.4 <0.31.0"
sourceRef:
kind: HelmRepository
name: openbao
@@ -32,7 +32,7 @@ spec:
type: RuntimeDefault
containers:
- name: backup-verify
image: gitea.renner.uno/gitea_admin/ci-backup-verify:2026-10-15 # {"$imagepolicy": "flux-system:backup-verify"}
image: gitea.renner.uno/gitea_admin/ci-backup-verify:2026-10-19 # {"$imagepolicy": "flux-system:backup-verify"}
command: ["bash", "/script/backup-verify.sh"]
env:
- name: HOME
+1 -1
View File
@@ -11,7 +11,7 @@ spec:
restartPolicy: Never
containers:
- name: check
image: docker.io/nicolaka/netshoot:v0.13
image: docker.io/nicolaka/netshoot:v0.13@sha256:a20c2531bf35436ed3766cd6cfe89d352b050ccc4d7005ce6400adf97503da1b
command:
- /bin/bash
- -c