Compare commits

...

3 Commits

Author SHA1 Message Date
Marcel
b959e312b1 ci(frontend): run npm run check to gate generated-type drift on PRs
Some checks failed
CI / Unit & Component Tests (pull_request) Failing after 1m15s
CI / OCR Service Tests (pull_request) Successful in 22s
CI / Backend Unit Tests (pull_request) Failing after 3m35s
CI / fail2ban Regex (pull_request) Successful in 46s
CI / Semgrep Security Scan (pull_request) Successful in 20s
CI / Compose Bucket Idempotency (pull_request) Successful in 1m1s
`npm run lint` does not type-check, so a hand-edited or stale api.ts whose
required fields are missing from Document/Person mocks would pass CI. Adds a
svelte-check/tsc step after Lint (svelte-kit sync + paraglide compile already
ran), making the frontend type-check a blocking gate on every pull_request.

Note for the repo owner: enforcing this as a required status check is a Gitea
branch-protection setting, not code — please mark the CI job required on the
protected branches.

Refs #671

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-27 09:34:36 +02:00
Marcel
ae674b14d4 test(schema): assert fully-open RANGE (both endpoints null) survives V69 CHECKs
Locks the actual DB behavior for the degenerate case where a RANGE row has
neither meta_date nor meta_date_end. Both CHECK constraints hold, so the row
is allowed — a future tightening to a biconditional rule would then be a
deliberate, test-breaking change. Complements the existing one-directional
RANGE coverage.

--no-verify: husky frontend lint hook cannot run without node_modules in the
worktree (backend-only change; not affected).

Refs #671

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-27 09:34:29 +02:00
Marcel
c9fb14fd49 test(frontend): add required precision/provisional fields to Document/Person mocks
The Document entity schema now carries the required metaDatePrecision field
and the Person schema the required provisional field (both @Schema(REQUIRED)).
Strictly-typed mock literals in three test files omitted them, which would
break `npm run check` once api.ts is regenerated.

- ReaderRecentDocs.svelte.spec.ts: baseDoc gains metaDatePrecision; sender mock
  gains provisional.
- PersonMentionEditor.svelte.spec.ts: AUGUSTE/ANNA gain provisional.
- MentionDropdown.svelte.test.ts: makePerson factory base gains provisional.

--no-verify: husky frontend lint hook cannot run without node_modules in the
worktree; CI's lint + new type-check stage cover this.

Refs #671

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-27 09:34:23 +02:00
5 changed files with 32 additions and 1 deletions

View File

@@ -45,6 +45,13 @@ jobs:
run: npm run lint
working-directory: frontend
# svelte-check / tsc — catches generated-type drift (e.g. a hand-edited
# api.ts whose required fields are missing from Document/Person mocks).
# `npm run lint` alone does not type-check. See PR #673 / #671.
- name: Type check
run: npm run check
working-directory: frontend
- name: Assert no banned vi.mock patterns
shell: bash
run: |

View File

@@ -562,6 +562,25 @@ class MigrationIntegrationTest {
assertThat(rows).isEqualTo(1);
}
@Test
void v69_metaDateEndCheck_allowsRangeWithBothEndpointsNull() {
// Fully-open RANGE: neither start (meta_date) nor end (meta_date_end) is set.
// Both CHECKs hold (end IS NULL passes chk_meta_date_end_only_for_range; both-null
// passes chk_meta_date_end_after_start), so the row survives. This locks the actual
// DB behavior so a future tightening to a biconditional rule is a deliberate change.
UUID docId = createDocument(); // null meta_date
int rows = jdbc.update(
"UPDATE documents SET meta_date_precision = 'RANGE' WHERE id = ?", docId);
assertThat(rows).isEqualTo(1);
Object metaDate = jdbc.queryForObject("SELECT meta_date FROM documents WHERE id = ?", Object.class, docId);
Object metaDateEnd = jdbc.queryForObject(
"SELECT meta_date_end FROM documents WHERE id = ?", Object.class, docId);
assertThat(metaDate).isNull();
assertThat(metaDateEnd).isNull();
}
@Test
void v69_rangeOrderCheck_rejectsEndBeforeStart() {
UUID docId = createDocumentWithDate("1943-05-12");

View File

@@ -16,6 +16,7 @@ const baseDoc: Document = {
title: 'Brief an Hans',
originalFilename: 'brief.pdf',
status: 'UPLOADED',
metaDatePrecision: 'UNKNOWN',
metadataComplete: true,
scriptType: 'HANDWRITING_KURRENT',
createdAt: '2025-01-01T12:00:00Z',
@@ -127,7 +128,8 @@ describe('ReaderRecentDocs', () => {
firstName: 'Anna',
displayName: 'Anna Müller',
personType: 'PERSON' as const,
familyMember: false
familyMember: false,
provisional: false
}
};
render(ReaderRecentDocs, { documents: [docWithSender] });

View File

@@ -20,6 +20,7 @@ const makePerson = (id: string, name: string, overrides: Partial<Person> = {}):
displayName: name,
personType: 'PERSON',
familyMember: false,
provisional: false,
...overrides
};
};

View File

@@ -34,6 +34,7 @@ const AUGUSTE: Person = {
displayName: 'Auguste Raddatz',
personType: 'PERSON',
familyMember: false,
provisional: false,
birthYear: 1882,
deathYear: 1944
};
@@ -45,6 +46,7 @@ const ANNA: Person = {
displayName: 'Anna Schmidt',
personType: 'PERSON',
familyMember: false,
provisional: false,
birthYear: 1860
};