refactor(person): fold year range into section headings, remove standalone stats bar
Some checks are pending
CI / Unit & Component Tests (push) Successful in 1m39s
CI / Backend Unit Tests (push) Successful in 2m8s
CI / E2E Tests (push) Has started running

The floating stats bar was visually disconnected and showed a combined document
count already visible from the per-section badges. Replaced it with a year range
shown inline next to each section heading (e.g. "Gesendete Dokumente · 12 · 1921–1945"),
making the range contextually relevant per direction.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
Marcel
2026-03-20 11:16:22 +01:00
parent 203b7d2b08
commit 3f717e3266
2 changed files with 41 additions and 24 deletions

View File

@@ -125,6 +125,29 @@ test.describe('Person detail — sent and received documents', () => {
await expect(page.getByRole('heading', { name: /Empfangene Dokumente/i })).toBeVisible();
await page.screenshot({ path: 'test-results/e2e/person-sent-received.png' });
});
test('shows year range next to document count when documents have dates', async ({ page }) => {
// Navigate to the first person who has documents with dates
await page.goto('/persons');
const personLinks = page.locator('a[href^="/persons/"]:not([href="/persons/new"])');
const count = await personLinks.count();
for (let i = 0; i < count; i++) {
await page.goto('/persons');
await personLinks.nth(i).click();
await page.waitForSelector('[data-hydrated]');
// Check if either section heading has a year range (4 digits)
const sentHeading = page.getByRole('heading', { name: /Gesendete Dokumente/i }).locator('..');
const hasYearRange = await sentHeading.locator('span').filter({ hasText: /\d{4}/ }).count();
if (hasYearRange > 0) {
await expect(sentHeading.locator('span').filter({ hasText: /\d{4}/ }).first()).toBeVisible();
await page.screenshot({ path: 'test-results/e2e/person-year-range.png' });
return;
}
}
// If no person has dated documents, the test is a no-op (year range is optional)
});
});
test.describe('Person detail — conversations link', () => {

View File

@@ -24,15 +24,18 @@
const allDocuments = $derived([...sentDocuments, ...receivedDocuments]);
const docStats = $derived(() => {
const dated = allDocuments.filter(d => d.documentDate);
const years = dated.map(d => parseInt(d.documentDate!.substring(0, 4)));
return {
total: allDocuments.length,
minYear: years.length ? Math.min(...years) : null,
maxYear: years.length ? Math.max(...years) : null,
};
});
function yearRange(docs: typeof sentDocuments) {
const years = docs
.filter(d => d.documentDate)
.map(d => parseInt(d.documentDate!.substring(0, 4)));
if (!years.length) return null;
const min = Math.min(...years);
const max = Math.max(...years);
return min === max ? `${min}` : `${min} ${max}`;
}
const sentYearRange = $derived(yearRange(sentDocuments));
const receivedYearRange = $derived(yearRange(receivedDocuments));
const coCorrespondents = $derived(() => {
const freq = new Map<string, { id: string; name: string; count: number }>();
@@ -327,21 +330,6 @@
</div>
{/if}
<!-- Document Statistics Bar -->
{#if docStats().total > 0}
<div class="mb-8 px-4 py-3 bg-brand-sand/30 rounded-sm flex items-center gap-2 font-sans text-sm text-brand-navy/70">
<span>{docStats().total} Dokumente</span>
{#if docStats().minYear !== null}
<span class="text-brand-mint">·</span>
{#if docStats().minYear === docStats().maxYear}
<span>{docStats().minYear}</span>
{:else}
<span>{docStats().minYear} {docStats().maxYear}</span>
{/if}
{/if}
</div>
{/if}
<!-- Sort control -->
{#if allDocuments.length > 0}
<div class="flex justify-end mb-4">
@@ -362,6 +350,9 @@
<span class="bg-brand-navy text-white text-xs font-bold px-2 py-1 rounded-full">
{sentDocuments.length}
</span>
{#if sentYearRange}
<span class="text-xs font-sans text-gray-400">{sentYearRange}</span>
{/if}
</div>
{#if sentDocuments.length === 0}
@@ -423,6 +414,9 @@
<span class="bg-brand-navy text-white text-xs font-bold px-2 py-1 rounded-full">
{receivedDocuments.length}
</span>
{#if receivedYearRange}
<span class="text-xs font-sans text-gray-400">{receivedYearRange}</span>
{/if}
</div>
{#if receivedDocuments.length === 0}