feat(members): implement /members page — Kachel-Ansicht (E2, issue #48) #58
Reference in New Issue
Block a user
Delete Branch "feat/issue-48-members-kachel"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Summary
GET /v1/households/mine/invites,DELETE /v1/households/mine/members/{userId},PATCH /v1/households/mine/members/{userId}endpoints; inviteshareUrlbase URL now configurable viaapp.base-url/APP_BASE_URLenv var/membersKachel grid — member cards with avatar (role colour), role badge, join date, Du-badge, kebab menu with inline role control and remove dialog; invite card + invite panel; optimistic updates with toast rollbackgreen-dark/blueby role, role badge colours,seit DD.MM.YYYYjoin date,⋯kebab with icons/divider,Mitglied einladeninvite card with hover states,Einladelink teilenpanel with mono link box + yellow expiry pill + text-link regenerateTest plan
./mvnw test— 329 tests greennpm run test— 771 tests green/membersas planer — grid shows all members, own card has green border + Du badge, other cards have⋯kebab⋯→ dropdown shows Rolle ändern + EntfernenAPP_BASE_URL=https://yourdomain.comin docker env → invite shareUrl uses that domainCloses #48
- Add V006 migration: invalidated_at column + partial unique index on household_invite - Add findByHouseholdIdAndInvalidatedAtIsNull, findByHouseholdIdAndUserId, countByHouseholdIdAndRole - Add ChangeRoleRequest DTO - HouseholdService: getActiveInvite, createInvite (regenerate), removeMember, changeMemberRole - HouseholdController: GET /v1/households/mine/invites, DELETE/PATCH /v1/households/mine/members/{userId} Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>- MemberCard: white bg, 1px border + shadow-card, centered column layout, avatar color by role (green-dark/blue), role badge with role-specific colors, join date "seit DD.MM.YYYY", Du-badge below join date, ⋯ kebab with icons and divider, inline role-control with Abbrechen, blue editing border #B5D4F4 - InviteCard: white bg, 1.5px dashed border, min-height 180px, plus circle, label "Mitglied einladen", full hover state (green border/bg/icon/label) - InvitePanel: white bg, title "Einladelink teilen", description, mono link box, yellow expiry pill when ≤ 24h, text-link "Neuen Link generieren" - RemoveDialog: white bg, padding 28px 32px, "?" in title, updated body text - +page.server.ts: expose householdName from locals.haushalt - +page.svelte: subtitle "{n} Mitglieder · {householdName}" - Tests: add join date format test, Abbrechen test, InvitePanel title test Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>removeMember now checks the planner count before deleting a planner member. Throws ConflictException("Cannot remove the last planner") when only one planner remains, matching the spec requirement in S4. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>Review concerns addressed
All four concerns identified during the self-review have been resolved:
9d3be84—feat(members): guard removeMember against removing the last plannerHouseholdService.removeMember()using the existingcountByHouseholdIdAndRolerepository method — same pattern aschangeMemberRole. ThrowsConflictExceptionwhen the target is the sole remaining planner.removeMemberShouldThrow409WhenRemovingLastPlanner60d84c0—feat(members): add error toasts for invite failures and Content-Type header on role PATCHhandleInviteClicknow shows a toast and returns early when the invite POST fails (previously silently dropped the error)handleRegeneratenow shows a toast when the regenerate POST fails (previously silently ignored errors)handleRoleChangenow sendsContent-Type: application/jsonon the PATCH request (previously missing, causing the Spring backend to reject the body)MemberCard.test.tsandInvitePanel.test.tsAll tests green: 330 backend ✅ · 772 frontend ✅