Files
familienarchiv/CLAUDE.md
Marcel 97e5255d7f refactor: move createPerson logic into PersonService
Controller was directly calling personRepository.save() for person creation.
Extracted into PersonService.createPerson() to enforce Controller → Service → Repository layering.
Also documented the layering rules in CLAUDE.md.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-03-17 08:28:30 +01:00

6.5 KiB

CLAUDE.md

This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.

Project Overview

Familienarchiv is a family document archival system — a full-stack web app for digitizing, organizing, and searching family documents. Key features: file uploads (stored in MinIO/S3), metadata management, Excel batch import, full-text search, conversation threads between family members, and role-based access control.

Collaboration Principles

Be honest and objective: Evaluate all suggestions, ideas, and feedback on their technical merits. Don't be overly complimentary or sycophantic. If something doesn't make sense, doesn't align with best practices, or could be improved, say so directly and constructively. Technical accuracy and project quality take precedence over being agreeable.

Core Workflow: Research → Plan → Implement → Validate

Start every feature with: "Let me research the codebase and create a plan before implementing."

  1. Research - Understand existing patterns and architecture
  2. Plan - Propose approach and verify with you
  3. Implement - Build with tests and error handling
  4. Validate - ALWAYS run formatters, linters, and tests after implementation
  • Whenever working on a feature or issue, let's always come up with a plan first, then save it to a file called /.agent/current-plan.md, before getting started with code changes. Update this file as the work progresses.
  • Let's use pure functions where possible to improve readability and testing.

Stack

  • Backend: Spring Boot 4.0 (Java 21, Maven, Jetty, JPA/Hibernate, Flyway, Spring Security, Spring Session JDBC)
  • Frontend: SvelteKit 2 with Svelte 5, TypeScript, Tailwind CSS 4, Paraglide.js (i18n: de/en/es)
  • Database: PostgreSQL 16
  • Object Storage: MinIO (S3-compatible)
  • Infrastructure: Docker Compose

Common Commands

Running the Full Stack

# From repo root — starts PostgreSQL, MinIO, and Spring Boot backend
docker-compose up -d

Backend (Spring Boot)

cd backend

./mvnw spring-boot:run          # Run locally
./mvnw clean package            # Build JAR (with tests)
./mvnw clean package -DskipTests
./mvnw test                     # Run all tests
./mvnw test -Dtest=ClassName    # Run a single test class

Frontend (SvelteKit)

cd frontend

npm install
npm run dev         # Dev server (port 3000)
npm run build       # Production build
npm run preview     # Preview production build

npm run lint        # Prettier + ESLint check
npm run format      # Auto-fix formatting
npm run check       # svelte-check (type checking)
npm run test        # Vitest unit tests

Architecture

Backend (backend/src/main/java/org/raddatz/familienarchiv/)

Layered architecture:

  • model/ — JPA entities: Document, Person, AppUser, UserGroup, Tag, DocumentStatus (enum: PLACEHOLDER → UPLOADED → TRANSCRIBED → REVIEWED → ARCHIVED)
  • repository/ — Spring Data repositories + DocumentSpecifications for complex filtered queries
  • service/ — Core business logic: DocumentService (uploads, search, Excel import), FileService (MinIO/S3), ExcelService, MassImportService, UserService
  • controller/ — REST endpoints: DocumentController, PersonController, UserController, AdminController, GroupController, TagController
  • security/SecurityConfig (HTTP Basic + form login, CSRF disabled), PermissionAspect (AOP enforcement of @RequirePermission), CustomUserDetailsService
  • config/MinioConfig (creates S3Client, validates connectivity on startup), AsyncConfig

Database migrations live in src/main/resources/db/migration/ (Flyway). Configuration in src/main/resources/application.properties — most values injected from environment variables (DB credentials, MinIO endpoint/credentials/bucket, upload limits, Excel column mappings).

Frontend (backend/workspaces/frontend/src/)

  • hooks.server.ts — Central middleware: reads auth_token cookie, injects it into all API calls to the backend, loads current user context
  • routes/ — File-based routing. Main pages: / (search/home), /documents/[id], /documents/[id]/edit, /persons, /persons/[id], /conversations, /admin, /login
  • routes/api/ — SvelteKit API endpoints for typeahead (persons, tags) — these call the Spring Boot backend
  • lib/components/PersonTypeahead.svelte, TagInput.svelte
  • messages/ — Paraglide.js translation files (de.json, en.json, es.json)

Authentication: form login → backend sets session → auth_token cookie → hooks.server.ts injects into all backend requests.

Backend Layering Rules

Strict layering must be respected at all times:

Controller → Service → Repository → DB
  • Controllers must never inject or call repositories directly. All business logic goes through a service.
  • Services must never reach into another domain's repository directly. If Service A needs data owned by domain B, it calls Service B — not Repository B.
    • DocumentServicePersonService.findById()PersonRepository
    • DocumentServicePersonRepository (bypasses the service layer)
  • This keeps domain boundaries clear and business logic testable in isolation.

Key Design Patterns

  • Search: DocumentSpecifications (Spring Data JPA Specification pattern) enables composable, dynamic query building for the document search endpoint
  • Permissions: @RequirePermission annotation processed by PermissionAspect (AOP) — checks user's UserGroup permissions at the method level
  • Excel Import: Configurable column index mapping in application.properties; ExcelService parses → MassImportService upserts documents
  • File Storage: FileService wraps AWS SDK v2 S3Client with path-style access for MinIO compatibility

Infrastructure

The docker-compose.yml at the repo root orchestrates everything. A MinIO MC helper container runs at startup to create the archive-documents bucket and set permissions. The backend container depends on both db and minio being healthy before starting.

API Testing

HTTP test files are in backend/api_tests/ (Document.http, User.http) for use with the VS Code REST Client extension.

Dev Container

A .devcontainer/ config is available (Java 21 + Node 24, with ports 8080 and 3000 forwarded). Use VS Code's "Reopen in Container" to get a pre-configured environment with Spring Boot Tools, Lombok support, and database/MinIO services running.