Beute L3 Runden 2+3 und Review-Fixes:
- Glas-Holo ohne warmes Leuchten, Wanderboden-Fuss, Fokusflug mit
Geist-Ansicht, Inhalte im Fokus, Rähmchen mit Art-Farbe beim Anheben
- Hinweis-Geometrie je Zarge nur einmal je Layout gebaut; Drehen mit
Pointer-Capture, endet auch bei Loslassen ausserhalb (rig-pointer.ts)
- Tiefenunschärfe ab 55 fps, Leistungsprobe bei jeder Bewegungsstufe,
Context-Loss-Listener aufgeräumt, Trefferboxen als skalierte Einheitsbox
Beute L4 Umbauen (/colonies/[id]/hive): Entwurf mit Basis-Schnappschuss
beim ersten Schritt, Rückgängig/Wiederholen, Hinweis bei Serverstand-
Änderung, Konfliktblatt.
Beute L5:
- Durchsicht-Abschnitt „Beute“: Aufbau-Änderungen in der Durchsicht,
Blatt-Formulare stoppen das Submit-Bubbling durch Portale (sonst
speicherte „Speichern“ im Blatt die ganze Durchsicht), Fokus nach
Rückgängig, Folgevorschläge beim Speichern
- Offline: Beute im Offline-Paket, Warteschlange pending-hive-changes
(DB v5), Abarbeiten in Reihenfolge, keine Online-Änderung überholt
wartende, Hinweis bei abgelehnter Änderung mit „Warteschlange öffnen“
T7 L1 Diktat: Spracherkennungs-Kapsel (Web Speech API), Einwilligung
standardmässig aus, Diktat-Knopf an Freitextfeldern, Seite
„Sprache & Datenschutz“; axe-core als exakte devDependency.
Backend: NotificationsService liest Empfänger und schreibt in einer
Transaktion mit FOR KEY SHARE (paralleles Löschen eines Benutzers
führte zu P2003 und verzögerten Vorschlägen; Ursache der wackeligen
Endtests). Zwei e2e-Prüfungen gegen geteilten DB-Zustand entschärft.
Gates: Frontend lint, typecheck, 2740 Tests, build; Backend lint,
typecheck, 4266 Unit-Tests, build; parallele e2e 3x grün (978).
Browser-Prüfung 1280/390 px, Tastatur, offline, reduced motion.
Refs #19#20#21#22#27#32
Co-Authored-By: Claude Opus 5.5 (1M context) <[email protected]>
- Veterinary medicine catalogue, lots and append-only movement ledger
(rest always computed; corrections as counter-bookings; inactive
medicines take no new stock; unit must match on lot moves).
- Documents of medicine lots, authority notices and restrictions need the
domain right on top of documents:* (403 before any lookup).
- Label particulars: pure checkLabel with six mandatory gaps and four
warnings, AFM font metrics, Berlin-day dates, geometric reading order
for split addresses, new master-data fields with row-locked updates.
- Herd events ColonyCreated, ColonyMoved, ApiaryChanged and
TskReferenceDayReached (ids only, never forwarded to webhooks); CSV
import emits ColonyCreated with audit.
- ARCHITECTURE.md §12 Compliance (T6), Annahmen 59–70.
Co-Authored-By: Claude Opus 5.5 (1M context) <[email protected]>
- Colony end releases the queen in the same transaction; open
suggestions become obsolete and a CLEANUP suggestion lists open
tasks and the queen; apply-cleanup validates evidence and blocks
reactivated colonies
- Withdrawal chain: plausibility warnings on harvest and bottling,
conflict notifications also when a treatment is entered or corrected
after the harvest (naming bottled lots), withdrawal spans in the
calendar and M365 sync, Berlin-day end events
- Next 3 steps per colony and the "Heute" endpoint with ranking and an
explicit merge table by intent
- Inspection-triggered rule suggestions follow the colony's latest
inspection (resolve when the finding is gone, refresh when it stays)
- Frontend: colony card takeover in the inspection form, feed status as
condition, occupied frames 0-40; legacy offline entries keep syncing
- Notifications and preferences are deleted with their user
Co-Authored-By: Claude Opus 5.5 (1M context) <[email protected]>
Platform backbone (plan 2026-10-13-plattform-rueckgrat), reviewed tasks:
- run roles api/worker/job/all with shared startup checks (Task 1)
- schema and migration for DomainEvent, deliveries, JobRun, ThrottlerHit (Task 2)
- audit, notifications and domain events written in the same transaction (Task 3)
- dispatcher with SKIP LOCKED claims, retries and stale release (Task 4)
- worker building blocks: tick, LISTEN/NOTIFY wake-up, health (Task 5)
- worker process and entry points (Task 6)
- throttler counters in Postgres (Task 19)
- separate keys per purpose with key ring (Task 20)
- public origin page without exact location (Task 22)
- shop keys split into read and write (Task 23)
- Kustomize base, components, overlay encry, CI validation (Task 26)
Field capture T3 (plan 2026-10-13-t3-erfassung-am-stand), reviewed tasks:
- brood frames, read endpoints, apiary overview and offline pack
- network basics, offline queue v3, navigation sheets, form building blocks
- new inspection with last-time hints and weather, varroa per day,
treatment prefill, apiary page with round
- inspection photo (Task 10) is implemented, review pending
Not rolled out. Remaining tasks follow in later commits.
Co-Authored-By: Claude Opus 5.5 (1M context) <[email protected]>
Backend
- Backup covers every Prisma model (bundle v3); a guard test fails for any
new model that is neither backed up nor explicitly excluded. Unsealed
bundles may only add rows to 27 legacy master/field tables and never
overwrite; counters, ledgers, settings, roles etc. need a sealed file.
Shared import limit BACKUP_MAX_IMPORT_BYTES (default 50 MB, max 256 MB)
with warnings in log and UI; replaced document files are removed after
commit.
- Post-commit side effects (automation, calendar sync, webhooks) run via
runAfterCommit and never turn a committed write into a 500, so retries
with the same Idempotency-Key no longer create duplicates.
- Calendar outbox is multi-replica safe: per-entry claims with stale
takeover, revision-based settle, new Graph event only on 404/410,
transactionId on create, 30 s Graph timeout, URL-encoded ids, GUID
validation for groupId, "run now" in background and resets FAILED.
- Automation tasks are deduplicated under a row lock on the rule.
- Update DTOs follow one null rule: omitted = unchanged, null clears a
nullable field, null on a required field is a 400.
- Varroa mites/day is recomputed on correction; withdrawal status is
checked against the harvest date (?at=), bounded colonyIds; inspection
create is audited; updates re-enqueue calendar entries.
- Dashboard, statistics and apiary/colony guards treat WEAK, CONSPICUOUS
and QUEENLESS colonies as living.
- Prisma errors and body-parser errors are logged without query values or
request bodies.
- Migration 20261012100000_calendar_sync_claims; schema index name aligned
with the existing database object.
Frontend
- Sticky save bar sticks again (no scroll container ancestors, card uses
overflow-clip), safe-area insets, scroll-padding, FAB hidden on forms,
sticky desktop sidebar.
- Inspections record yes / no / not checked instead of silent defaults.
- All living colonies are selectable; shared RecordSelect, EnumSelect,
ChoiceGroup and TriStateField replace per-page copies; selects show
names instead of ids; labels point at real controls.
- Emptied optional fields are sent as null (emptyToNull) so every field
can be cleared; dates default to the local day and are sent via
toApiDate.
- Harvest withdrawal warning uses the harvest date; backup page warns when
a backup outgrows the import limit and lists skipped tables.
Build and docs
- Docker builds fail unless lint, typecheck and unit tests pass.
- ARCHITECTURE.md updated (assumptions 9-12, 19-21, section 8) and spec
docs/superpowers/specs/2026-10-12-plattform-rueckgrat-und-fahrplan-design.md
for the backbone (api/worker/job roles, domain event outbox) and the
feature roadmap T3-T7.
Co-Authored-By: Claude Opus 5.5 (1M context) <[email protected]>
Letzte Phase des RBAC-Umbaus: die transitionale Rollen-Infrastruktur,
die seit Phase 1 parallel zum neuen Role/Permission-System mitlief,
ist jetzt komplett weg.
- Prisma-Migration: User.legacyRole-Spalte und LegacyRole-Enum
gedroppt (nichts liest die Spalte mehr, seit Phase 2 jeder Controller
auf @RequirePermission laeuft).
- roles.guard.ts, roles.guard.spec.ts, roles.decorator.ts geloescht;
RolesGuard aus den APP_GUARD-Providern entfernt.
- AuthenticatedUser/JWT-Payload verlieren das role-Feld (permissions
werden ohnehin frisch pro Request aus der DB aufgeloest, nicht aus
dem Claim).
- Users-API: CreateUserDto/UpdateUserDto akzeptieren jetzt roleId
(eine echte Role.id) statt der alten role-Enum-Werte; UsersService
validiert, dass die Rolle existiert und aktiv ist, bevor sie
zugewiesen wird.
- Alle 34 e2e-Fixtures und der Seed-Script folgen dem neuen Schema.
Verifiziert: tsc, lint, build, unit (220/220), volle e2e-Suite
159/159 gruen - keine uebersprungenen Tests.
Co-Authored-By: Claude Sonnet 5 <[email protected]>
Replaces the fixed 5-value Role enum with a database-driven Role/Permission
model: admins can create custom roles with a precise per-resource/action
permission set (83-key code-owned catalog), instead of being locked to
ADMIN/BEEKEEPER/STAFF/READONLY/API_CLIENT.
- New Role/Permission/RolePermission tables; legacy Role enum renamed to
LegacyRole and kept as User.legacyRole so all existing @Roles() call
sites keep working unchanged during the migration.
- New RolesController/RolesService (CRUD, permission-set editing,
deactivate/reactivate) with lockout-prevention invariants: system roles
(ADMIN) can't be edited or deactivated, and a role still assigned to
users can't be deactivated.
- New PermissionResolverService (30s-cached, DB-fresh per user) and
PermissionsGuard + @RequirePermission(), registered as an additional
APP_GUARD alongside the legacy RolesGuard so both systems run
side-by-side until controllers are migrated in Phase 2.
- PermissionCatalogSyncService seeds any new catalog entries into the DB
on boot, so future features only touch the TS catalog.
- New GET /auth/me returns the caller's role and effective permissions.
- Migration hand-written (destructive column rename) with grants derived
from a fresh grep of every existing @Roles() call site, verified
against 5 controllers read in full for STAFF's exact write boundary.
- test/roles.e2e-spec.ts covers the new endpoints and invariants end to
end; test/authorization-coverage.e2e-spec.ts added but skipped until
Phase 2 gives every controller a @RequirePermission.
Co-Authored-By: Claude Sonnet 5 <[email protected]>
Da fachliche Objekte nie hart geloescht werden (nur status +
deactivatedAt), fehlte bisher ein Weg, ein versehentlich aufgeloestes
Volk oder deaktivierten Bienenstand wieder zu aktivieren. Neue
POST :id/reactivate-Endpunkte setzen status zurueck auf ACTIVE und
loeschen deactivatedAt; ConflictException wenn bereits aktiv.