2479 lines
110 KiB
YAML
2479 lines
110 KiB
YAML
schema_version: 1
|
||
project: VacatureRadar
|
||
updated_at: '2026-08-12'
|
||
execution_policy:
|
||
order: file-order, then first ready task whose dependencies are done
|
||
no_product_questions: true
|
||
external_block_rule: finish interface, fixtures, tests, error handling and docs; block only the credential/review
|
||
step; continue
|
||
completion_gate: ./scripts/codex_verify.sh
|
||
status_values:
|
||
- done
|
||
- ready
|
||
- blocked-external
|
||
- deferred
|
||
tasks:
|
||
- id: VR-000
|
||
title: Repository, keuzes en autonome overdracht
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- NFR-005
|
||
- NFR-006
|
||
- AC-001
|
||
- AC-051
|
||
- AC-054
|
||
depends_on: []
|
||
summary: Maak één self-contained repository met vaste productbeslissingen, documentnavigatie, Codex-instructies
|
||
en machineleesbare taakledger.
|
||
acceptance_criteria:
|
||
- README, CODEX_START_HERE en AGENTS bevatten één consistente startflow.
|
||
- Product-, architectuur-, UX-, security-, operations- en qualitydocumenten zijn aanwezig.
|
||
- Backlogvalidator detecteert ontbrekende velden, dubbele IDs, onbekende dependencies en cycli.
|
||
- Repo-eigen Codex-skill beschrijft dezelfde Definition of Done als AGENTS.md.
|
||
verification:
|
||
- python scripts/backlog.py validate
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- AGENTS.md
|
||
- CODEX_START_HERE.md
|
||
- docs/
|
||
- .agents/skills/
|
||
- scripts/backlog.py
|
||
result:
|
||
completed_at: '2026-07-20'
|
||
note: Volledige overdrachtsstructuur en documentatieset aangelegd.
|
||
- id: VR-001
|
||
title: Domeinmodellen en migraties
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-001
|
||
- PR-003
|
||
- PR-010
|
||
- PR-024
|
||
- PR-025
|
||
- PR-027
|
||
- PR-043
|
||
- PR-053
|
||
- PR-054
|
||
depends_on:
|
||
- VR-000
|
||
summary: Implementeer user-scoped profielen, bronnen/runs/raw documents, canonieke vacatures/aliassen/provenance/versies,
|
||
scores, feedback, sollicitaties en digest-outbox.
|
||
acceptance_criteria:
|
||
- Alle domeinobjecten hebben expliciete constraints, statussen en timestamps.
|
||
- Persoonsgebonden objecten zijn aan Django User gekoppeld.
|
||
- Migraties bouwen een lege database zonder handmatige stap.
|
||
verification:
|
||
- uv run python manage.py migrate --noinput
|
||
- uv run python manage.py makemigrations --check --dry-run
|
||
primary_paths:
|
||
- apps/*/models.py
|
||
- apps/*/migrations/
|
||
result:
|
||
completed_at: '2026-07-20'
|
||
note: Initiële modellen en migraties geïmplementeerd.
|
||
- id: VR-002
|
||
title: Strikt bronbeleid en veilige fetcher
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-011
|
||
- PR-012
|
||
- PR-013
|
||
- PR-014
|
||
- NFR-001
|
||
- AC-011
|
||
- AC-012
|
||
- AC-013
|
||
depends_on:
|
||
- VR-001
|
||
summary: Bouw fail-closed source policy, centrale platformdenylist, URL/host/IP-validatie, redirecthercontrole,
|
||
conditional requests en responsegrenzen.
|
||
acceptance_criteria:
|
||
- Private, loopback, link-local, credentialed en niet-toegestane URLs worden vóór request geblokkeerd.
|
||
- Iedere redirect wordt opnieuw gevalideerd.
|
||
- Denylistplatformen worden ook via redirect geweigerd.
|
||
- Fetcher heeft time-, byte-, type- en redirectlimieten en logt geen payload.
|
||
verification:
|
||
- uv run pytest tests/security/test_url_security.py tests/security/test_policy.py tests/unit/test_fetcher.py
|
||
primary_paths:
|
||
- apps/sources/services/policy.py
|
||
- apps/sources/services/url_security.py
|
||
- apps/sources/services/fetcher.py
|
||
result:
|
||
completed_at: '2026-07-20'
|
||
note: Veilige fetchboundary en negatieve tests geïmplementeerd.
|
||
- id: VR-003
|
||
title: Deterministische bronadapters
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-020
|
||
- PR-021
|
||
- PR-022
|
||
- PR-023
|
||
- AC-015
|
||
depends_on:
|
||
- VR-002
|
||
summary: Implementeer een gemeenschappelijk extractiecontract en adapters voor JSON-LD JobPosting, generieke HTML,
|
||
RSS/Atom en vacaturemail.
|
||
acceptance_criteria:
|
||
- Adapters schrijven niet naar de database en doen geen netwerkrequests.
|
||
- Iedere adapter levert parser key/version, confidence, warnings en veldbewijs.
|
||
- HTML wordt gesanitized en unsubscribe-/trackinglinks worden niet als vacature beschouwd.
|
||
- Gesaneerde offline fixtures dekken normale en malformed input.
|
||
verification:
|
||
- uv run pytest tests/unit/test_jsonld_adapter.py tests/unit/test_generic_html_adapter.py tests/unit/test_discovery_rss.py
|
||
tests/unit/test_email_adapter.py tests/security/test_sanitize.py
|
||
primary_paths:
|
||
- apps/sources/adapters/
|
||
- fixtures/
|
||
- apps/jobs/services/sanitize.py
|
||
result:
|
||
completed_at: '2026-07-20'
|
||
note: Vier adaptertypen, registry en fixtures geïmplementeerd.
|
||
- id: VR-004
|
||
title: Normalisatie, deduplicatie en provenancepipeline
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-024
|
||
- PR-025
|
||
- PR-027
|
||
- PR-030
|
||
- PR-031
|
||
- PR-032
|
||
- PR-033
|
||
- AC-010
|
||
- AC-020
|
||
- AC-021
|
||
depends_on:
|
||
- VR-001
|
||
- VR-003
|
||
summary: Bouw CanonicalJobDraft, URL/titel/contract/datum-normalisatie, exact-voor-fuzzy dedupe, werkgeverresolutie,
|
||
alias/provenance/versioning en transactionele persistence.
|
||
acceptance_criteria:
|
||
- Replay van hetzelfde document creëert geen tweede canonieke vacature.
|
||
- Een gewijzigde vacature bewaart een historisch snapshot.
|
||
- Rechtstreekse werkgever krijgt canonieke voorkeur zonder platformalias te verliezen.
|
||
- Field provenance en parserversie blijven auditbaar.
|
||
verification:
|
||
- uv run pytest tests/unit/test_normalization.py tests/unit/test_canonicalize.py tests/integration/test_pipeline.py
|
||
tests/integration/test_dedupe_lifecycle_feedback.py
|
||
primary_paths:
|
||
- apps/jobs/services/normalization.py
|
||
- apps/jobs/services/dedupe.py
|
||
- apps/jobs/services/pipeline.py
|
||
result:
|
||
completed_at: '2026-07-20'
|
||
note: Idempotente canonieke pipeline met aliassen en historiek geïmplementeerd.
|
||
- id: VR-005
|
||
title: Zoekprofielen en uitlegbare deterministische scoring
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-001
|
||
- PR-002
|
||
- PR-004
|
||
- PR-040
|
||
- PR-041
|
||
- PR-042
|
||
- PR-043
|
||
- PR-044
|
||
- AC-022
|
||
- AC-023
|
||
- AC-024
|
||
depends_on:
|
||
- VR-004
|
||
summary: Implementeer profieldefaults/revisies, harde uitsluitingen, features, gewogen score, recommendation en
|
||
positieve/negatieve evidence.
|
||
acceptance_criteria:
|
||
- Harde uitsluitingen lopen vóór zachte scoring en hebben stabiele codes.
|
||
- Onbekende afstand of voorwaarde wordt niet verzonnen.
|
||
- ScoreRun bewaart profiel/modelversie, componenten, concerns en evidence.
|
||
- Feedbackgewichten blijven binnen vaste grenzen.
|
||
verification:
|
||
- uv run pytest tests/unit/test_profiles.py tests/unit/test_features_distance.py tests/unit/test_scoring.py
|
||
primary_paths:
|
||
- apps/profiles/
|
||
- apps/jobs/services/features.py
|
||
- apps/jobs/services/scoring.py
|
||
- apps/jobs/services/feedback.py
|
||
result:
|
||
completed_at: '2026-07-20'
|
||
note: Deterministische score- en profielbasis geïmplementeerd.
|
||
- id: VR-006
|
||
title: Nederlandstalige kerninterface en gebruikersacties
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-050
|
||
- PR-051
|
||
- PR-052
|
||
- PR-053
|
||
- PR-056
|
||
- NFR-008
|
||
- AC-003
|
||
- AC-040
|
||
- AC-041
|
||
- AC-042
|
||
- AC-043
|
||
depends_on:
|
||
- VR-005
|
||
summary: Lever dashboard, vacaturelijst/detail, profiel-, bron- en sollicitatiepagina's plus CSRF-beschermde feedbackacties.
|
||
acceptance_criteria:
|
||
- Kernflows vereisen login en user-scopen mutaties.
|
||
- Interessant, bewaren, verbergen en gesolliciteerd zijn één duidelijke actie.
|
||
- Applied creëert/bijwerkt één dossier maar verzendt nooit extern.
|
||
- UI is responsive, semantisch en zonder externe assets bruikbaar.
|
||
verification:
|
||
- uv run pytest tests/integration/test_views.py tests/integration/test_tasks_and_more_views.py tests/integration/test_dedupe_lifecycle_feedback.py
|
||
primary_paths:
|
||
- apps/*/views.py
|
||
- templates/
|
||
- static/
|
||
result:
|
||
completed_at: '2026-07-20'
|
||
note: Server-rendered MVP-interface en feedback/applications geïmplementeerd.
|
||
- id: VR-007
|
||
title: Digest-outbox en vacaturelevenscyclus
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-054
|
||
- PR-055
|
||
- NFR-003
|
||
- AC-030
|
||
- AC-031
|
||
- AC-032
|
||
- AC-033
|
||
- AC-034
|
||
depends_on:
|
||
- VR-005
|
||
- VR-006
|
||
summary: Implementeer dagelijkse selectie, idempotente outbox/verzending en overgang active → uncertain/expired/removed.
|
||
acceptance_criteria:
|
||
- Maximaal één digest per profiel en lokale kalenderdag.
|
||
- Verborgen of hard uitgesloten vacatures verschijnen niet.
|
||
- Verzonden records worden niet dubbel verstuurd.
|
||
- Lifecycle gebruikt valid_through en last_seen met reproduceerbare drempels.
|
||
verification:
|
||
- uv run pytest tests/integration/test_email_import_notifications.py tests/integration/test_dedupe_lifecycle_feedback.py
|
||
primary_paths:
|
||
- apps/notifications/
|
||
- apps/jobs/services/lifecycle.py
|
||
- templates/emails/
|
||
result:
|
||
completed_at: '2026-07-20'
|
||
note: Outbox, digesttemplates en lifecycle geïmplementeerd.
|
||
- id: VR-008
|
||
title: Docker, Unraid, beheer en kwaliteitsbaseline
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-060
|
||
- PR-061
|
||
- PR-062
|
||
- PR-063
|
||
- PR-064
|
||
- NFR-006
|
||
- NFR-009
|
||
- NFR-010
|
||
- AC-050
|
||
- AC-051
|
||
- AC-052
|
||
- AC-053
|
||
- AC-055
|
||
depends_on:
|
||
- VR-001
|
||
- VR-007
|
||
summary: Lever settings, healthchecks, Celeryschema, Docker/Compose/Unraidbestanden, bootstrap/back-up/restore
|
||
en offline CI-testbasis.
|
||
acceptance_criteria:
|
||
- Lokale bootstrap maakt een bruikbare demo en draait de volledige gate.
|
||
- De kern werkt met AI en IMAP uit.
|
||
- Liveness en readiness hebben het gedocumenteerde contract.
|
||
- Back-up/restore en Unraidstappen zijn gedocumenteerd zonder secrets.
|
||
verification:
|
||
- ./scripts/codex_verify.sh
|
||
- python -c "import yaml; yaml.safe_load(open('docker-compose.yml')); yaml.safe_load(open('docker-compose.unraid.yml'))"
|
||
primary_paths:
|
||
- config/
|
||
- Dockerfile
|
||
- docker-compose*.yml
|
||
- scripts/
|
||
- docs/operations/
|
||
result:
|
||
completed_at: '2026-07-20'
|
||
note: Self-hosted deployment- en kwaliteitsbasis aangelegd; live Dockerbuild vereist een host met Docker.
|
||
- id: VR-009
|
||
title: Optionele lokale AI-boundary
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-045
|
||
- PR-046
|
||
- PR-063
|
||
- AC-025
|
||
depends_on:
|
||
- VR-005
|
||
summary: Lever een uitgeschakelde-by-default Ollama-client met vast JSON-schema, timeout, beperkte prompt, confidence
|
||
en foutfallback.
|
||
acceptance_criteria:
|
||
- Zonder model of bij fout blijft de deterministische pipeline volledig werken.
|
||
- Vacaturetekst wordt als onbetrouwbare data begrensd en modeloutput gevalideerd.
|
||
- AI-service heeft geen tools, databasewrite of netwerktoegang buiten de geconfigureerde Ollamahost.
|
||
verification:
|
||
- uv run pytest tests/unit/test_ai.py
|
||
primary_paths:
|
||
- apps/jobs/services/ai.py
|
||
- config/settings.py
|
||
result:
|
||
completed_at: '2026-07-20'
|
||
note: Ollama-serviceboundary en fallbacktests geïmplementeerd; nog niet in rankingpipeline geïntegreerd.
|
||
- id: VR-101
|
||
title: Automatische bronontdekking en kandidaatregister
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-017
|
||
- PR-020
|
||
- PR-021
|
||
- NFR-003
|
||
depends_on:
|
||
- VR-008
|
||
summary: 'Bouw veilige ontdekking uit bestaande toegestane documenten: same-domain carrièrelinks, sitemaplocaties,
|
||
JSON-LD job-URLs, feedlinks en werkgeversdomeinen uit e-mail. Ontdekking maakt uitsluitend candidate/review-records
|
||
en fetcht ze niet automatisch.'
|
||
acceptance_criteria:
|
||
- Discovery heeft pure functies plus persistente kandidaatservice met uniqueness en provenance.
|
||
- Alle URL's worden gecanonicaliseerd; off-domain, denylist en private doelen worden verworpen.
|
||
- Een confidence/reason bepaalt prioriteit maar nooit policy=allow.
|
||
- Management command en bron-UI tonen candidates, bewijs en bulk-safe dismiss/approve-to-trial acties.
|
||
- Fixtures dekken HTML, sitemapindex/urlset, feed en e-mail discovery plus replay.
|
||
verification:
|
||
- uv run pytest tests/unit tests/integration -k 'discover or candidate or sitemap'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/services/discovery.py
|
||
- apps/sources/models.py
|
||
- apps/sources/views.py
|
||
- templates/sources/
|
||
- tests/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: 'Implemented discovery from HTML/JSON-LD/feed/sitemap/email into candidate-only source records, added
|
||
provenance persistence with idempotency, added discover_sources command, candidate bulk UI actions, fixtures,
|
||
and integration/unit tests. Verification: python -m pytest subset blocked by missing django in this runtime;
|
||
./scripts/codex_verify.sh passed.'
|
||
- id: VR-102
|
||
title: Bronpolicyreview, robotscache en vervaldatum
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-011
|
||
- PR-017
|
||
- PR-018
|
||
- NFR-001
|
||
- NFR-010
|
||
depends_on:
|
||
- VR-101
|
||
summary: Maak policybeslissingen expliciet en auditbaar. Robots mag geautomatiseerd worden gelezen; voorwaardenreview
|
||
blijft een beheerattest met datum, bewijslink/notitie en expiry. Een verlopen of conflicterende review schakelt
|
||
automatische fetch fail-closed uit.
|
||
acceptance_criteria:
|
||
- SourcePolicyReview/versiehistoriek registreert actor, beslissing, scope, reden en expiry.
|
||
- Robotsregels worden per origin gecachet met timeout/size/SSRF-beveiliging en user-agentmatching.
|
||
- Terms review wordt nooit door AI of heuristiek als juridisch toegestaan verklaard.
|
||
- UI toont ontbrekende/verlopen review en maakt veilige allow/trial/pause/deny-overgangen.
|
||
- Fetcher/task weigert policy-conflict of verlopen allow en tests bewijzen fail-closed gedrag.
|
||
verification:
|
||
- uv run pytest tests/security tests/integration -k 'policy or robots or review'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/models.py
|
||
- apps/sources/services/policy.py
|
||
- apps/sources/services/robots.py
|
||
- apps/sources/views.py
|
||
- docs/operations/SOURCE_ONBOARDING.md
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: 'VR-102 afgerond: bronpolicyreview-historie met actor/beslissing/scope/reden/expiry toegevoegd; robotscache
|
||
per origin met TTL/size/SSRF en user-agent matching; fetcher/task faalveilig op review-conflict/verval; bronlijst
|
||
toont reviewstatus en bulkacties allow/trial/pause/deny.'
|
||
- id: VR-103
|
||
title: Databaseleases, per-domein rate limiting en adaptieve planning
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-015
|
||
- PR-018
|
||
- NFR-003
|
||
- NFR-007
|
||
- NFR-010
|
||
depends_on:
|
||
- VR-102
|
||
summary: Voorkom dubbele/concurrerende fetches over workers met databaseleases en per-origin minimumintervallen.
|
||
Gebruik PostgreSQL als waarheid; Redis mag alleen als optimalisatie dienen.
|
||
acceptance_criteria:
|
||
- Een SourceLease of equivalente atomische claim heeft token, expiry en crash recovery.
|
||
- Max concurrency en minimum interval gelden installatiebreed per origin.
|
||
- 429/Retry-After, timeouts en opeenvolgende fouten vergroten gecontroleerd de backoff.
|
||
- Succes reset alleen toepasselijke foutstate en plant volgende run met begrensde jitter.
|
||
- Tests simuleren twee workers, verlopen lease, 304, 429 en retry zonder dubbel request.
|
||
verification:
|
||
- uv run pytest tests/integration tests/unit -k 'lease or rate or schedule or retry'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/models.py
|
||
- apps/sources/tasks.py
|
||
- apps/sources/services/scheduling.py
|
||
- tests/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Implemented DB-lease claims per-origin interval/backoff, concurrency guard, Retry-After/timeouts, regression
|
||
tests, and docs traceability updates.
|
||
- id: VR-104
|
||
title: Geocodingcontract, cache en importeerbare Belgische postcodegegevens
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-002
|
||
- PR-024
|
||
- PR-041
|
||
- PR-042
|
||
depends_on:
|
||
- VR-005
|
||
summary: 'Implementeer provider-onafhankelijke geocoding zonder verplichte externe API: Location/GeoPoint-cache,
|
||
conservatieve locatieparser en CLI-import voor een door de beheerder aangeleverde gelicenseerde Belgische postcode/municipality-CSV.
|
||
Commit alleen fictieve/minimale testdata.'
|
||
acceptance_criteria:
|
||
- Providerprotocol en offline CSV-provider hebben versie, confidence en bronmetadata.
|
||
- Parser ondersteunt Belgische postcode/gemeente en laat ambiguïteit onbekend.
|
||
- Cache voorkomt herhaalde lookups en kan opnieuw worden opgebouwd.
|
||
- Importcommand valideert kolommen, ranges, duplicates en licentiemetadata zonder gedeeltelijke writes.
|
||
- Zonder dataset blijft scoring werken met unknown distance; UI meldt dat duidelijk.
|
||
verification:
|
||
- uv run pytest tests/unit tests/integration -k 'geocode or location or postcode'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/jobs/services/geocoding.py
|
||
- apps/jobs/models.py
|
||
- apps/jobs/management/commands/
|
||
- config-data/geodata/
|
||
- docs/operations/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Implemented offline CSV geocode provider/import contract with validation, ambiguity semantics (unknown
|
||
on ambiguous), atomic import with metadata checks, and command+docs. Added unit/integration tests.
|
||
- id: VR-105
|
||
title: Afstands- en reistijdschatting in ranking
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-002
|
||
- PR-040
|
||
- PR-041
|
||
- PR-042
|
||
- AC-022
|
||
- AC-024
|
||
- NFR-004
|
||
depends_on:
|
||
- VR-104
|
||
summary: Gebruik profielorigin en gecachte jobcoördinaten voor haversineafstand en een expliciet gelabelde, conservatieve
|
||
reistijdschatting. Voeg een optioneel providercontract toe voor later OSRM/routergebruik; geen externe route-API
|
||
is vereist.
|
||
acceptance_criteria:
|
||
- Exacte afstand is alleen beschikbaar wanneer beide punten voldoende confidence hebben.
|
||
- Geschatte reistijd is herkenbaar als schatting en beïnvloedt geen harde filter tenzij profiel dat expliciet
|
||
kiest.
|
||
- Onbekend blijft unknown en veroorzaakt geen automatische uitsluiting.
|
||
- Rescore wordt gericht getriggerd wanneer locatiecache verandert.
|
||
- Tests dekken grensafstand, remote/hybrid, ontbrekende data en tijdzone-onafhankelijkheid.
|
||
verification:
|
||
- uv run pytest tests/unit tests/integration -k 'distance or commute or geocode or score'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/jobs/services/distance.py
|
||
- apps/jobs/services/scoring.py
|
||
- apps/profiles/models.py
|
||
- templates/jobs/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Implemented distance exactness via cache confidence, conservative commute estimate, explicit commute labels,
|
||
no automatic exclusion for unknown distance, cache-triggered rescore, and scoring/coverage updates.
|
||
- id: VR-106
|
||
title: Gespecialiseerde publieke ATS-adapters
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-020
|
||
- PR-021
|
||
- PR-022
|
||
- PR-024
|
||
- NFR-005
|
||
depends_on:
|
||
- VR-003
|
||
summary: Voeg adapters toe voor publieke vacatureformaten van Greenhouse, Lever, Recruitee, SmartRecruiters en
|
||
Workable, in die volgorde. Gebruik alleen openbare, bedoelde jobpagina's/feeds of officieel gedocumenteerde
|
||
publieke endpoints; geen login of reverse-engineered private API.
|
||
acceptance_criteria:
|
||
- Elke provideradapter detecteert alleen eigen host/markup en valt veilig terug.
|
||
- Paginatie/listing en detail worden gescheiden; listings ontdekken kandidaten, details leveren vacaturedata.
|
||
- Providerfixtures bevatten meerdere jobs, gesloten job, ontbrekende velden en gewijzigde markup.
|
||
- External ID, canonical URL, location, dates en employment type krijgen veldbewijs/confidence.
|
||
- Source onboardingdocument noemt providerbeperkingen en rate limits zonder ongeverifieerde juridische claim.
|
||
verification:
|
||
- uv run pytest tests/unit tests/integration -k 'greenhouse or lever or recruitee or smartrecruiters or workable
|
||
or ats'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/adapters/
|
||
- fixtures/ats/
|
||
- docs/architecture/SOURCE_ADAPTERS.md
|
||
- tests/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Added specialist ATS adapters voor Greenhouse, Lever, Recruitee, SmartRecruiters en Workable met host-gedreven
|
||
listing/detail scheiding, evidencevelddekking en fixture/tests voor gesloten job, multi-job en markup-variatie.
|
||
- id: VR-107
|
||
title: Handmatige URL-import en bookmarklet
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-017
|
||
- PR-021
|
||
- PR-052
|
||
- NFR-001
|
||
- NFR-008
|
||
depends_on:
|
||
- VR-102
|
||
summary: Lever een authenticated form en minimale bookmarklet die alleen een URL naar VacatureRadar opent/invult.
|
||
De server importeert pas na expliciete gebruikersactie en volledige policy/SSRF-check; gebruikers kunnen ook
|
||
gesaneerde tekst plakken wanneer fetch niet is toegestaan.
|
||
acceptance_criteria:
|
||
- GET-prefill verandert geen state; import is POST+CSRF en user-auditbaar.
|
||
- URL-import respecteert dezelfde denylist/policy/redirectlimieten als scheduler.
|
||
- Paste-import heeft bytegrens, sanitization en source_type=manual zonder externe fetch.
|
||
- Resultaat toont gecreëerd/duplicate/warnings en biedt direct vacaturedetail.
|
||
- Bookmarklet bevat geen secret, sessietoken of broninhoud en is in UX-doc gedocumenteerd.
|
||
verification:
|
||
- uv run pytest tests/integration tests/security -k 'manual or bookmark or import'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/views.py
|
||
- apps/sources/forms.py
|
||
- apps/sources/services/manual_import.py
|
||
- templates/sources/
|
||
- static/js/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Handmatige URL/paste import toegevoegd (CSRF-post + GET-prefill, policy/SSRF-check op URL-flow, paste
|
||
zonder extern fetch), bookmarklet en importresultaat in bronlijst; tests en documentation bijgewerkt.
|
||
- id: VR-108
|
||
title: Resolutie naar oorspronkelijke werkgever
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-032
|
||
- PR-051
|
||
- NFR-004
|
||
depends_on:
|
||
- VR-101
|
||
- VR-106
|
||
summary: Bouw een deterministische resolver die recruiter/platform/e-mailaliassen koppelt aan bestaande of nieuw
|
||
ontdekte rechtstreekse werkgeversbronnen via external ID, titel/locatie, employer domain en publieke canonical
|
||
metadata. Geen algemene websearch is verplicht.
|
||
acceptance_criteria:
|
||
- Resolver maakt evidence-rich kandidaatlinks en auto-merge alleen boven conservatieve drempel.
|
||
- Directe bron vervangt canonical URL maar alle aliassen/provenance blijven zichtbaar.
|
||
- Conflicterende werkgever of locatie resulteert in review, niet merge.
|
||
- UI toont waarom een bron als rechtstreeks/recruiter/onbekend is geclassificeerd en laat herstel toe.
|
||
- Benchmarkfixtures meten false merge en missed direct source.
|
||
verification:
|
||
- uv run pytest tests/unit tests/integration -k 'employer or resolver or alias or canonical'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/jobs/services/employer_resolution.py
|
||
- apps/jobs/services/dedupe.py
|
||
- apps/jobs/models.py
|
||
- templates/jobs/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Implemented deterministic direct-employer resolver (apps/jobs/services/employer_resolution.py) with evidence-rich
|
||
decisions, conflict review path, and conservative threshold; wired resolver into dedupe/pipeline so ATS/recruiter
|
||
source merges resolve to direct employer canonical URL while preserving aliases/provenance; added unit tests
|
||
for merge/review/no-resolve and integration pipeline coverage for ATS-to-direct canonical canonicalization.
|
||
Added employer_resolution details in alias payload for UI-consumable auditability.
|
||
- id: VR-109
|
||
title: AI-analyse integreren met schema, cache en evaluaties
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-042
|
||
- PR-043
|
||
- PR-044
|
||
- PR-045
|
||
- PR-046
|
||
- NFR-004
|
||
depends_on:
|
||
- VR-009
|
||
- VR-005
|
||
summary: Integreer optionele Ollama-analyse na deterministische features. Bewaar model/prompt/schema/hash, valideer
|
||
evidence tegen tekst en laat AI alleen zachte kenmerken/confidence/samenvatting toevoegen. Bij iedere fout volgt
|
||
deterministische output.
|
||
acceptance_criteria:
|
||
- AI-run is gecachet op contenthash+model+promptversie en heeft status/foutcategorie zonder volledige promptlog.
|
||
- JSON-schema weigert extra velden, out-of-range waarden en evidence die niet uit brontekst komt.
|
||
- AI kan hard_exclusions, source policy, URL fetch, feedback of application niet muteren.
|
||
- Een golden evaluation-set vergelijkt disabled, valid, malformed, timeout en prompt-injectionoutput.
|
||
- Rankingimpact is opt-in per profiel, begrensd en uitlegbaar in ScoreRun/UI.
|
||
verification:
|
||
- uv run pytest tests/unit tests/integration tests/security -k 'ai or ollama or prompt or evidence'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/jobs/models.py
|
||
- apps/jobs/services/ai.py
|
||
- apps/jobs/services/scoring.py
|
||
- fixtures/ai/
|
||
- docs/architecture/SCORING_ENGINE.md
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: AI-analyse met schema, cache, foutcategorieën en opt-in weging voltooid; AI-waarden gevalideerd op tekst,
|
||
deterministische fallback en score-evidence opgeslagen. Geen UI-explainability aanpassingen hier, die kan
|
||
extern in Stitch worden opgepakt.
|
||
- id: VR-110
|
||
title: Gecontroleerd leren uit feedback
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-004
|
||
- PR-040
|
||
- PR-042
|
||
- NFR-004
|
||
depends_on:
|
||
- VR-005
|
||
summary: Maak feedbackleren expliciet, begrensd en resetbaar. Gebruik alleen zachte featuregewichten, minimale
|
||
sampledrempels en versieer iedere aanpassing; harde regels en bronpolicy blijven immutable.
|
||
acceptance_criteria:
|
||
- Learning staat standaard uit totdat de gebruiker het in het profiel activeert.
|
||
- Gewichten blijven binnen per-feature min/max en hebben een terugkeer-naar-default actie.
|
||
- Verborgen feedback met reden wordt onderscheiden van niet-relevante titel/afstand/werkvorm.
|
||
- Een offline evaluator toont scoreverschuiving, top-N churn en mogelijke false negatives vóór activatie.
|
||
- UI maakt geleerd versus handmatig gewicht en laatste update duidelijk.
|
||
verification:
|
||
- uv run pytest tests/unit tests/integration -k 'feedback or learn or weight or revision'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/jobs/services/feedback.py
|
||
- apps/profiles/models.py
|
||
- apps/profiles/services.py
|
||
- templates/profiles/
|
||
- docs/architecture/SCORING_ENGINE.md
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: 'Feedbackleren geïmplementeerd: leren blijft standaard uit, feedback-signalen met minimumsample-drempel,
|
||
hidden/niet-learn-categorisering via reason_code, feedbackmetadata logging en een offline evaluatierapport-script.
|
||
UI-explainability/resetflow voor learned-vs-manual achterwege gelaten per verzoek.'
|
||
- id: VR-111
|
||
title: Herinneringen en uitzonderingsmeldingen
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-053
|
||
- PR-054
|
||
- PR-055
|
||
- NFR-003
|
||
depends_on:
|
||
- VR-007
|
||
summary: Voeg idempotente reminder-outbox toe voor sluitingsdatum, opvolgdatum en uitzonderlijk sterke nieuwe
|
||
match. Respecteer quiet hours, lokale tijdzone en dagelijkse frequentie; geen externe sollicitatieactie.
|
||
acceptance_criteria:
|
||
- Reminderregels hebben stabiele event keys zodat retries niet dubbel sturen.
|
||
- Topmatchmelding vereist score/confidence/drempel en kan per profiel uit.
|
||
- Sluitingsreminders worden niet verzonden voor hidden/expired/applied wanneer niet relevant.
|
||
- Follow-up gebruikt applicationstatus en user-configured werkdagen, niet alleen kalenderdagen.
|
||
- Consolemail- en locmemtests dekken DST, retries, quiet hours en lege recipient.
|
||
verification:
|
||
- uv run pytest tests/unit tests/integration -k 'reminder or notification or digest or outbox'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/notifications/models.py
|
||
- apps/notifications/services.py
|
||
- apps/notifications/tasks.py
|
||
- apps/profiles/models.py
|
||
- templates/emails/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Implemented reminder outbox (closing/follow-up/top-match), idempotent scheduler integration, reminders
|
||
templates, and integration coverage for quiet hours/weekdays/DST/skips.
|
||
- id: VR-112
|
||
title: Bronhealth, quarantaine en observability
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-018
|
||
- PR-026
|
||
- PR-060
|
||
- PR-061
|
||
- NFR-010
|
||
depends_on:
|
||
- VR-103
|
||
summary: 'Maak source health operationeel: rolling metrics, parserdrift, velddichtheid, nulresultaat-anomalie,
|
||
automatische quarantaine/herstel en statusdashboard. Logs blijven gestructureerd en payloadvrij.'
|
||
acceptance_criteria:
|
||
- Per bron zijn succesratio, latency, HTTP/foutcategorie, extract/duplicate counts en laatste goede parseroutput
|
||
zichtbaar.
|
||
- Drempels onderscheiden tijdelijke fout, policy/securityfout en parserdrift.
|
||
- Automatische quarantaine is fail-closed; herstel gaat altijd via trial en begrensde canaryrun.
|
||
- Raw cleanup draait periodiek en behoudt gequarantaineerd bewijs.
|
||
- Readiness blijft alleen kritieke dependencies meten; detailhealth staat authenticated op systempagina.
|
||
verification:
|
||
- uv run pytest tests/unit tests/integration tests/security -k 'health or quarantine or metrics or cleanup or
|
||
drift'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/models.py
|
||
- apps/sources/services/health.py
|
||
- apps/sources/tasks.py
|
||
- apps/core/views.py
|
||
- templates/system/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Implemented source health metrics, quarantining logic, parser drift detection and bounded canary recovery
|
||
path; scheduled periodic health enforcement and recovery tasks.
|
||
- id: VR-113
|
||
title: Uitgebreid sollicitatiedossier en veilige export
|
||
status: done
|
||
priority: P2
|
||
requirement_ids:
|
||
- PR-051
|
||
- PR-053
|
||
- PR-056
|
||
- NFR-002
|
||
- NFR-008
|
||
depends_on:
|
||
- VR-006
|
||
summary: Breid applications uit met tijdlijn, contactmetadata, notities, vacature-HTMLsnapshot en export naar
|
||
ZIP met JSON/CSV/printbare HTML. Voeg geen automatische formulierverzending toe. Bestandsuploads blijven buiten
|
||
scope tenzij een aparte threat review en contentvalidatie worden toegevoegd.
|
||
acceptance_criteria:
|
||
- Applied bevriest een gesaniteerde vacature- en scoresnapshot met bronlinks en tijdstip.
|
||
- Statuswijzigingen en notities vormen een user-scoped audit timeline.
|
||
- Export bevat alleen het gekozen dossier, veilige filenames en geen secrets/raw mailboxbody.
|
||
- Printbare HTML werkt zonder externe assets en is bruikbaar als PDF via browserprint.
|
||
- Data-export en dossierverwijdering zijn idempotent en getest op cross-user access.
|
||
verification:
|
||
- uv run pytest tests/integration tests/security -k 'application or export or timeline or snapshot'
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/jobs/models.py
|
||
- apps/jobs/services/applications.py
|
||
- apps/jobs/views.py
|
||
- templates/applications/
|
||
- docs/operations/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Implemented application timeline/audit events, contact metadata persistence, snapshot freeze in applied
|
||
flow, ZIP+CSV+print export and idempotent user-scoped delete; added integration tests for snapshot, timeline,
|
||
export/print and cross-user scope.
|
||
- id: VR-114
|
||
title: Browser-e2e, accessibility en visuele regressiebasis
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-006
|
||
- NFR-008
|
||
- AC-002
|
||
- AC-003
|
||
- AC-051
|
||
depends_on:
|
||
- VR-107
|
||
- VR-111
|
||
- VR-113
|
||
summary: Voeg een lokale Playwright-suite toe voor de volledige gebruikersflow en een dependency-arme accessibilitycontrole.
|
||
Tests gebruiken seeded data, locmem mail en geen internet.
|
||
acceptance_criteria:
|
||
- E2E dekt login, dashboard, filter/detail, profielupdate, vier feedbackacties, application en manual import.
|
||
- Tests lopen op desktop en 360px viewport en gebruiken stabiele role/label-selectors.
|
||
- Keyboardtabvolgorde, zichtbare focus, form labels, headings en reduced motion worden gecontroleerd.
|
||
- Screenshots bij falen worden als CI-artifact bewaard maar niet in Git gecommit.
|
||
- Een snelle HTML/unit-a11ycheck blijft beschikbaar wanneer browsers niet geïnstalleerd zijn; browserjob mag apart
|
||
zijn.
|
||
verification:
|
||
- uv sync --extra browser
|
||
- uv run playwright install chromium
|
||
- uv run pytest tests/e2e
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- tests/e2e/
|
||
- pyproject.toml
|
||
- .github/workflows/ci.yml
|
||
- docs/design/ACCESSIBILITY.md
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Added VR-114 e2e accessibility and browser-flow coverage; updated traceability and project state.
|
||
- id: VR-115
|
||
title: Security- en supply-chainhardening
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- NFR-001
|
||
- NFR-002
|
||
- NFR-003
|
||
- NFR-009
|
||
- PR-013
|
||
- PR-023
|
||
- PR-046
|
||
- PR-064
|
||
depends_on:
|
||
- VR-102
|
||
- VR-109
|
||
summary: 'Hardening voor productie: non-root read-only container waar haalbaar, pinned image digests/releasebeleid,
|
||
secret scan, dependency audit, secure proxysettings, uploadverbod, DNS/transportreview en abuse-limieten op
|
||
authenticated mutaties.'
|
||
acceptance_criteria:
|
||
- Container draait als vaste niet-root UID/GID en schrijft alleen naar bedoelde volumes/tmp.
|
||
- CI scant repository op secrets en dependencies/images op bekende kwetsbaarheden met een gedocumenteerd severitybeleid.
|
||
- Security settings valideren DEBUG/hosts/origins/cookies/secret bij productie-start fail-fast.
|
||
- Rate limiting beschermt login en handmatige import zonder normale lokale bediening te breken.
|
||
- DNS rebinding-restgevaar is verminderd met transport-level connectcontrole of expliciet geteste mitigatie; threat
|
||
model vermeldt restscope.
|
||
- Geen gevoelige payload verschijnt in exceptions, admin list displays of exports.
|
||
verification:
|
||
- uv run pytest tests/security
|
||
- ./scripts/codex_verify.sh
|
||
- docker build -t vacatureradar:verify .
|
||
primary_paths:
|
||
- Dockerfile
|
||
- config/settings.py
|
||
- apps/core/
|
||
- apps/sources/services/fetcher.py
|
||
- .github/workflows/
|
||
- docs/quality/THREAT_MODEL.md
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Security hardening afgerond (production-safe instellingenvalidering, non-root/read-only containers, supply-chain
|
||
scans, DNS-rebindcontrole, login/manual import rate limiting, tests en docs).
|
||
- id: VR-116
|
||
title: Kwaliteits-, dedupe- en performancebenchmark
|
||
status: done
|
||
priority: P2
|
||
requirement_ids:
|
||
- NFR-004
|
||
- NFR-007
|
||
- PR-031
|
||
- PR-040
|
||
- PR-042
|
||
depends_on:
|
||
- VR-105
|
||
- VR-108
|
||
- VR-109
|
||
- VR-110
|
||
- VR-112
|
||
summary: Maak reproduceerbare offline benchmarksets en commands voor parservelddekking, dedupe precision/recall,
|
||
hard-filter false positives, ranking top-N en dashboard/pipelineperformance op 25.000 jobs.
|
||
acceptance_criteria:
|
||
- Datasets zijn synthetisch of geanonimiseerd en hebben expected labels/version.
|
||
- Rapport toont precision, recall, false merges, missed merges, top-N churn en onbekende-data-aandeel.
|
||
- Performancecommand rapporteert hardware/context, p50/p95, querycount en peak memory.
|
||
- NFR-007 wordt alleen als gehaald gemarkeerd bij gemeten p95 <1s op het gedocumenteerde referentieprofiel.
|
||
- Regressiedrempels zijn conservatief en blokkeren CI alleen wanneer baseline betrouwbaar stabiel is.
|
||
verification:
|
||
- uv run python scripts/benchmark.py --quick
|
||
- uv run pytest tests/benchmark
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- scripts/benchmark.py
|
||
- fixtures/benchmark/
|
||
- tests/benchmark/
|
||
- docs/quality/BENCHMARKS.md
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Added offline benchmark script, fixture coverage, benchmark tests, and benchmark docs. Updated traceability/projectstate.
|
||
Requires verification result pending.
|
||
- id: VR-117
|
||
title: Productierelease en Unraid acceptance
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-060
|
||
- PR-062
|
||
- PR-063
|
||
- PR-064
|
||
- NFR-003
|
||
- NFR-009
|
||
- NFR-010
|
||
- AC-001
|
||
- AC-051
|
||
- AC-055
|
||
depends_on:
|
||
- VR-106
|
||
- VR-107
|
||
- VR-111
|
||
- VR-112
|
||
- VR-114
|
||
- VR-115
|
||
- VR-116
|
||
summary: 'Maak release 1.0 kandidaat: production Compose, immutable image metadata, migratie-/rollbackcheck, clean-install
|
||
smoke, fixture-import, digest, back-up/restore en Unraid runbookvalidatie. Externe domein/mailbox/registrystappen
|
||
blijven aparte blocked tasks.'
|
||
acceptance_criteria:
|
||
- Een schone Dockerstack start, migreert en passeert healthchecks zonder handmatige databaseactie.
|
||
- Release-smoke importeert fixture tweemaal, maakt één job/aliascluster, score, feedback, application en digest.
|
||
- PostgreSQL-back-up wordt naar tijdelijke nieuwe stack hersteld en modelcounts/smoke blijven correct.
|
||
- Release artifact bevat SBOM/checksums, changelog, configdiff en exact upgrade/rollbackpad.
|
||
- README en PROJECT_STATE maken eerlijk onderscheid tussen productieklare code en resterende externe configuratie.
|
||
verification:
|
||
- ./scripts/release_verify.sh
|
||
- ./scripts/codex_verify.sh
|
||
- python scripts/backlog.py validate
|
||
primary_paths:
|
||
- scripts/release_verify.sh
|
||
- docker-compose.yml
|
||
- docker-compose.unraid.yml
|
||
- docs/operations/
|
||
- CHANGELOG.md
|
||
- docs/ai/PROJECT_STATE.md
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Release script, smoke-run, backup/restore and artifact bundle for VR-117 toegevoegd; release artefacten
|
||
en Unraid-runbook geactualiseerd; traceability en projectstate bijgewerkt.
|
||
- id: VR-118
|
||
title: Stitch Intelligence Cockpit production-grade integreren
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-006
|
||
- NFR-008
|
||
- AC-002
|
||
- AC-003
|
||
- AC-051
|
||
depends_on:
|
||
- VR-107
|
||
- VR-114
|
||
summary: Vertaal de negen aangeleverde Stitch-schermen naar de bestaande server-rendered Django-interface zonder
|
||
domeinlogica, securitygrenzen of gebruikersscope te vervangen en zonder fictieve productdata te introduceren.
|
||
acceptance_criteria:
|
||
- Een consistente responsive cockpit-shell en dark/light tokens bedienen alle kernroutes.
|
||
- Dashboard, vacatures, detail, pipeline, profiel, bronnen, systeem en login gebruiken echte backenddata en acties.
|
||
- Externe auto-apply, nepmetrics, onbewezen werkgeverinzichten en onbetrouwbare activiteitenfeeds zijn niet overgenomen.
|
||
- Zes doelviewports hebben één h1, geen horizontale overflow en werkende mobiele navigatie.
|
||
- Stitch-bronnen, integratieplan, screenshots en verificatierapport zijn traceerbaar maar niet onderdeel van de
|
||
productiecontainer.
|
||
verification:
|
||
- uv run pytest tests/e2e tests/integration/test_views.py tests/integration/test_tasks_and_more_views.py
|
||
- ./scripts/codex_verify.sh
|
||
- Browsercontrole op 1440x900, 1280x800, 1024x768, 768x1024, 390x844 en 360x800
|
||
primary_paths:
|
||
- templates/
|
||
- static/css/app.css
|
||
- static/js/app.js
|
||
- docs/design/STITCH_INTEGRATION_PLAN.md
|
||
- docs/design/stitch-reference/
|
||
- docs/design/validation/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Stitch-visuele taal geïntegreerd in CSP-veilige Django-templates; dark/light, responsive shell, pipeline,
|
||
broninteracties en browservalidatie toegevoegd zonder functionele scope-uitbreiding of fictieve data.
|
||
- id: VR-119
|
||
title: Stitch-schermcompositie dominant doorvoeren
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-050
|
||
- PR-051
|
||
- NFR-008
|
||
depends_on:
|
||
- VR-118
|
||
summary: Herwerk de cockpit na productfeedback zodat de aangeleverde Stitch-frontend niet alleen de visuele tokens
|
||
maar ook de schermcompositie, informatiedichtheid en interactiehiërarchie bepaalt, met behoud van echte Django-data,
|
||
toegankelijke server-rendered flows en alle bestaande veiligheidsgrenzen.
|
||
acceptance_criteria:
|
||
- De gedeelde shell, utilitybar en navigatie volgen aantoonbaar de Stitch-compositie op desktop en mobiel.
|
||
- Dashboard, vacatureoverzicht en detail nemen de primaire Stitch-layouts vrijwel volledig over met uitsluitend
|
||
aantoonbare databasevelden en bestaande veilige acties.
|
||
- Pipeline, profiel, bronnen, systeem en login gebruiken dezelfde dichte cockpit-hiërarchie en componentvormen.
|
||
- Lege, fout- en een-itemtoestanden behouden de bedoelde compositie zonder grote onverklaarde lege vlakken.
|
||
- Zes doelviewports hebben één h1, geen pagina-brede horizontale overflow en werkende toetsenbordnavigatie.
|
||
- Geen auto-apply, externe assets, fictieve metrics of onbewezen intelligence wordt toegevoegd.
|
||
verification:
|
||
- uv run pytest tests/e2e tests/integration/test_views.py tests/integration/test_tasks_and_more_views.py
|
||
- ./scripts/codex_verify.sh
|
||
- Browsercontrole op 1440x900, 1280x800, 1024x768, 768x1024, 390x844 en 360x800
|
||
primary_paths:
|
||
- apps/core/context_processors.py
|
||
- apps/core/views.py
|
||
- apps/jobs/views.py
|
||
- templates/
|
||
- static/css/app.css
|
||
- static/js/app.js
|
||
- docs/design/STITCH_INTEGRATION_PLAN.md
|
||
- docs/design/validation/
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Stitch-schermcompositie dominant doorgevoerd in shell, dashboard, vacaturefeed/detail, pipeline, profieleditor,
|
||
bronnen en systeem; geverifieerd met 146 tests, 82,02% coverage en browsermatrix op zes viewports, dark/light
|
||
en mobiele navigatie.
|
||
- id: VR-120
|
||
title: Begeleid zoekprofiel en functionele livebronnen opleveren
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-001
|
||
- PR-002
|
||
- PR-005
|
||
- PR-011
|
||
- PR-017
|
||
- PR-018
|
||
- PR-022
|
||
depends_on:
|
||
- VR-119
|
||
summary: Verwerk de functionele productfeedback door thuislocatie tot postcode te vereenvoudigen, technische JSON-invoer
|
||
door selectielijsten en checkboxes te vervangen en minimaal twee actuele publieke werkgeversfeeds end-to-end
|
||
te valideren.
|
||
acceptance_criteria:
|
||
- Het profiel vraagt alleen een viercijferige thuispostcode en leidt gemeente/coördinaten af wanneer lokale geodata
|
||
eenduidig beschikbaar is.
|
||
- Functietitels, skills, contractvormen, werkmodellen en regio's zijn begeleide keuzevelden die bestaande waarden
|
||
veilig behouden.
|
||
- Minimaal twee echte werkgeverfeeds hebben een actuele policyreview, parserfixtures en twee succesvolle livecycli.
|
||
- Demobronnen zijn niet zichtbaar in het normale bronoverzicht en actuele vacatures stromen door naar ranking.
|
||
- Profiel-, adapter-, pipeline-, view- en browsertests plus de volledige verificatiegate slagen.
|
||
verification:
|
||
- uv run pytest tests/integration/test_profile_preferences.py tests/integration/test_seed_sources.py tests/integration/test_pipeline.py
|
||
tests/unit/test_ats_adapters.py
|
||
- Volg docs/operations/SOURCE_ONBOARDING.md en controleer twee livecycli per geactiveerde bron
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/profiles/
|
||
- templates/profiles/
|
||
- apps/sources/
|
||
- config-data/seed_sources.yaml
|
||
- docs/operations/SOURCE_ONBOARDING.md
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Postcode-only profiel, begeleide checkboxkeuzes, gereviewde VITO- en Deliverect-feeds met twee livecycli,
|
||
employeridentiteit, broninventaris en robotsredirecthardening; 155 tests geslaagd, 2 optioneel overgeslagen,
|
||
82,94% coverage en volledige codex_verify-gate groen.
|
||
- id: VR-121
|
||
title: Regionale werkgevers- en platformalertdekking uitbreiden
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-011
|
||
- PR-012
|
||
- PR-017
|
||
- PR-018
|
||
- PR-032
|
||
depends_on:
|
||
- VR-120
|
||
summary: Breid de livebroncatalogus uit met publieke werkgeversfeeds in Limburg en aangrenzende Belgische werkregio's,
|
||
maak gedeelde ATS-hosts first-class en documenteer de veilige alertingress voor VDAB en Indeed.
|
||
acceptance_criteria:
|
||
- Minimaal acht bijkomende publieke bronnen hebben een actuele policyreview, parserdekking en twee succesvolle
|
||
livecycli voordat ze actief worden.
|
||
- De catalogus bevat aantoonbaar regionale dekking voor Hasselt/Genk en aanvullende IT-werkgevers in Brussel,
|
||
Gent of Leuven.
|
||
- Meerdere werkgevers op één publieke ATS-host kunnen naast elkaar bestaan zonder bronrecords te overschrijven.
|
||
- Corda Campus-vacaturekaarten worden deterministisch uitgelezen en off-domain links worden verworpen.
|
||
- Indeed en VDAB worden uitsluitend via officiële vacaturealerts/mailimport of handmatige import gebruikt en blijven
|
||
op de directe-fetchdenylist.
|
||
verification:
|
||
- uv run pytest tests/unit/test_regional_adapters.py tests/unit/test_ats_adapters.py tests/unit/test_source_models.py
|
||
tests/integration/test_seed_sources.py
|
||
- Voer twee livecycli uit voor iedere nieuwe bron en controleer source health, parserwarnings en inventaristelling
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/
|
||
- config-data/seed_sources.yaml
|
||
- fixtures/pages/corda-campus-jobs.html
|
||
- fixtures/ats/smartrecruiters-public-postings.json
|
||
- docs/operations/LIVE_SOURCE_CATALOG.md
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Acht extra gereviewde livebronnen, gedeelde ATS-hostidentiteit, Corda-adapter en veilige VDAB/Indeed-alertingress
|
||
toegevoegd; twee livecycli per bron, 159 tests, 82,91% coverage en in-app-browsercontrole geslaagd.
|
||
- id: VR-122
|
||
title: Dagelijkse officiële VDAB-ingang operationaliseren
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-012
|
||
- PR-016
|
||
- PR-018
|
||
- PR-064
|
||
depends_on:
|
||
- VR-121
|
||
summary: Verwerk officiële VDAB-jobalerts eenmaal per dag via de bestaande dedicated mailbox, met herkenbare provenance,
|
||
begrensde verwerking en een duidelijke route naar de contractueel toegankelijke VDAB Vacature API.
|
||
acceptance_criteria:
|
||
- De IMAP-ingang draait standaard eenmaal per dag op een configureerbaar tijdstip en blijft idempotent bij replay.
|
||
- VDAB-alertmails worden als VDAB-provenance herkend en vacatures stromen zonder automatische linkfetch door de
|
||
bestaande normalisatie-, dedupe- en rankingpipeline.
|
||
- De mailboxpoll is begrensd op aantal en berichtgrootte; oversized of onleesbare berichten stoppen de batch niet.
|
||
- De bronpagina toont de dagelijkse planning, configuratiestatus, laatste VDAB-import en het onderscheid tussen
|
||
jobalertingang en de officiële API waarvoor VDAB-goedkeuring vereist is.
|
||
- Directe VDAB-scraping, platformlogin en niet-goedgekeurde API-toegang blijven geblokkeerd en dit is getest en
|
||
operationeel gedocumenteerd.
|
||
verification:
|
||
- uv run pytest tests/unit/test_email_adapter.py tests/integration/test_email_import_notifications.py tests/integration/test_tasks_and_more_views.py
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/adapters/email_alert.py
|
||
- apps/sources/services/email_import.py
|
||
- apps/sources/services/imap_import.py
|
||
- apps/sources/tasks.py
|
||
- config/settings.py
|
||
- templates/sources/list.html
|
||
- docs/architecture/adrs/0005-email-alerts-as-platform-ingress.md
|
||
result:
|
||
completed_at: '2026-07-21'
|
||
note: Dagelijkse configureerbare VDAB-jobalertimport met expliciete provenance, begrensde foutgeisoleerde IMAP-poll,
|
||
beveiligde handmatige inplanning en heldere officiele API-route; 164 tests, 2 optioneel overgeslagen, 83,55%
|
||
coverage en desktop/390px Codex-browsercontrole groen.
|
||
- id: VR-123
|
||
title: Platformmailboxen veilig in de UI koppelen en frequent synchroniseren
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-012
|
||
- PR-016
|
||
- PR-018
|
||
- PR-064
|
||
depends_on:
|
||
- VR-122
|
||
summary: Vervang de globale dagelijkse IMAP-configuratie door gebruikersgescopeerde mailboxkoppelingen per vacatureplatform,
|
||
met versleutelde app-wachtwoorden en een eigen frequent synchronisatie-interval.
|
||
acceptance_criteria:
|
||
- Een ingelogde gebruiker kan voor VDAB en Indeed afzonderlijk een Gmail-, Outlook- of aangepaste IMAP-mailbox
|
||
koppelen, wijzigen, pauzeren en direct laten synchroniseren.
|
||
- App-wachtwoorden worden met een afzonderlijke roteerbare sleutel versleuteld opgeslagen, nooit teruggetoond
|
||
en nooit in logs of taakresultaten opgenomen.
|
||
- Iedere mailbox heeft een interval van 5 tot 360 minuten; de scheduler plant alleen verschuldigde actieve mailboxen
|
||
en is concurrency- en replayveilig.
|
||
- Mailimport bewaart mailbox- en platformprovenance, is per mailbox idempotent en laat een fout in één mailbox
|
||
de andere mailboxen niet blokkeren.
|
||
- Alle mutaties zijn login-, user-scope- en CSRF-beveiligd; negatieve tests dekken cross-user toegang, ontbrekende
|
||
encryptiesleutel, ongeldige host/poort en secretlekken.
|
||
- Bronpagina, runbook, threat model, configuratie en migratiedocumentatie zijn bijgewerkt; directe platformfetch
|
||
en platformlogin blijven uitgesloten.
|
||
verification:
|
||
- uv run pytest tests/unit/test_mailbox_credentials.py tests/integration/test_mailbox_connections.py tests/integration/test_email_import_notifications.py
|
||
- uv run python manage.py makemigrations --check --dry-run
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/models.py
|
||
- apps/sources/forms.py
|
||
- apps/sources/services/mailbox_connections.py
|
||
- apps/sources/services/imap_import.py
|
||
- apps/sources/tasks.py
|
||
- apps/sources/views.py
|
||
- templates/sources/list.html
|
||
- config/settings.py
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: 'Per-platform VDAB/Indeed-mailboxen met versleutelde app-wachtwoorden, intervallen van 5-360 minuten,
|
||
leases, user-scoped UI, securitytests en documentatie; volledige gate: 178 passed, 2 skipped, 83.56%.'
|
||
- id: VR-124
|
||
title: LinkedIn en Belgische jobboards via veilige jobalertmail toevoegen
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-012
|
||
- PR-016
|
||
- PR-021
|
||
- NFR-001
|
||
- NFR-003
|
||
depends_on:
|
||
- VR-123
|
||
summary: Breid de platformmailboxingang uit met LinkedIn, ictjob.be, Jobat, StepStone, EuroBrussels en BrusselsJobs
|
||
en beperk iedere parserrun tot vacaturelinks van het expliciet gekozen jobboard.
|
||
acceptance_criteria:
|
||
- De mailbox-UI biedt naast VDAB en Indeed ook LinkedIn, ictjob.be, Jobat, StepStone, EuroBrussels en BrusselsJobs
|
||
met een actuele officiele jobalertlink en dezelfde afzonderlijke mailbox-, interval-, pauze- en syncflow.
|
||
- Gesaneerde fixtures en adaptertests bewijzen per nieuw platform titel-, link- en provenance-extractie zonder
|
||
live netwerkcall.
|
||
- Een platformgebonden mail importeert alleen HTTPS-vacaturelinks op het verwachte jobboarddomein; externe, tracking-,
|
||
account-, privacy- en uitschrijflinks worden genegeerd.
|
||
- Mailboxrecords, bronprovenance, idempotentie, user scoping, encryptie, leases en foutisolatie blijven voor alle
|
||
platformkeuzes behouden.
|
||
- Bronbeleid, catalogus, threat model, onboarding, traceability en UI-copy vermelden dat directe platformlogin
|
||
en jobboardscraping uitgesloten blijven.
|
||
verification:
|
||
- uv run pytest tests/unit/test_email_adapter.py tests/integration/test_email_import_notifications.py tests/integration/test_mailbox_connections.py
|
||
- uv run python manage.py makemigrations --check --dry-run
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/models.py
|
||
- apps/sources/adapters/email_alert.py
|
||
- apps/sources/services/email_import.py
|
||
- templates/sources/list.html
|
||
- fixtures/emails/
|
||
- docs/operations/LIVE_SOURCE_CATALOG.md
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: LinkedIn, ictjob.be, Jobat, StepStone, EuroBrussels en BrusselsJobs toegevoegd aan platformmailboxen;
|
||
domeingebonden HTTPS-parser, zes fixtures, denylist, UI en docs; 192 passed, 2 skipped, 83.61%, desktop/390px
|
||
browser groen.
|
||
- id: VR-125
|
||
title: Brusselse dekking vervangen door regionale werkgevers en Belgische jobplatformen
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-011
|
||
- PR-012
|
||
- PR-017
|
||
- PR-018
|
||
- PR-021
|
||
- NFR-001
|
||
- NFR-003
|
||
depends_on:
|
||
- VR-124
|
||
summary: Verwijder de expliciete Brusselse jobboards en werkgevers uit de actieve radar, voeg brede Belgische
|
||
jobalertplatformen toe en activeer veilige publieke vacaturelijsten van werkgevers rond Hasselt-Genk.
|
||
acceptance_criteria:
|
||
- EuroBrussels en BrusselsJobs zijn niet meer configureerbaar of actief; bestaande koppelingen worden veilig uitgeschakeld
|
||
en verborgen zonder historische provenance te verwijderen.
|
||
- Careerjet, Randstad en Robert Half zijn beschikbaar via hun officiele e-mailalerts en blijven op de directe-fetchdenylist.
|
||
- Werkgeversbronnen buiten de regionale scope worden gedeactiveerd en verborgen; bestaande vacaturehistoriek blijft
|
||
bewaard.
|
||
- Minstens vier lokale werkgeverspagina's uit de kern Hasselt-Genk worden met host- en padgebonden adapters, gesaneerde
|
||
fixtures, actuele bronreview en twee succesvolle livecycli toegevoegd.
|
||
- Tot een thuispostcode is ingevuld, vermeldt de catalogus expliciet dat Hasselt-Genk als omkeerbaar centrum voor
|
||
de 40-km-selectie is gebruikt; ranking blijft de exacte profielafstand toepassen zodra die bekend is.
|
||
- Bronbeleid, threat model, onboarding, traceability en gebruikerscopy blijven duidelijk over e-mailingress, robots,
|
||
SSRF, off-domain afwijzing en het verbod op platformlogin en scraping.
|
||
verification:
|
||
- .venv/Scripts/python.exe -m pytest tests/unit/test_regional_adapters.py tests/unit/test_email_adapter.py tests/integration/test_seed_sources.py
|
||
tests/integration/test_email_import_notifications.py
|
||
- .venv/Scripts/python.exe manage.py makemigrations --check --dry-run
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/adapters/regional.py
|
||
- apps/sources/platforms.py
|
||
- apps/sources/management/commands/seed_sources.py
|
||
- config-data/seed_sources.yaml
|
||
- fixtures/pages/
|
||
- fixtures/emails/
|
||
- docs/operations/LIVE_SOURCE_CATALOG.md
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: Brusselse mailboxen en zeven buitenregionale bronnen veilig geretired; Careerjet, Randstad en Robert Half
|
||
toegevoegd; ACA, Xplore, UHasselt, PXL en ZOL na host/padreview en twee livecycli actief; 200 passed, 2 skipped,
|
||
83.90%, browser desktop/390px groen.
|
||
- id: VR-126
|
||
title: Werkgeversradar herankeren op postcode 2400 Mol
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-002
|
||
- PR-011
|
||
- PR-017
|
||
- PR-018
|
||
- PR-021
|
||
- NFR-001
|
||
- NFR-003
|
||
depends_on:
|
||
- VR-125
|
||
summary: Vervang de tijdelijke Hasselt-Genk-aanname door postcode 2400 Mol en voeg veilige publieke vacaturelijsten
|
||
toe van relevante werkgevers binnen ongeveer 40 km, met nadruk op infrastructuur-, systeem- en netwerkfuncties.
|
||
acceptance_criteria:
|
||
- De actieve profielruntime bewaart postcode 2400 en een maximale afstand van 40 km; ontbrekende gelicenseerde
|
||
coördinatendata blijft expliciet zichtbaar als extern restpunt en wordt niet stil ingevuld.
|
||
- De broncatalogus en UI noemen Mol als centrum en maken onderscheid tussen geografisch gereviewde bronnen en
|
||
exacte vacatureafstand die pas na geocoding kan worden berekend.
|
||
- Minstens vijf werkgevers uit Mol, Geel, Westerlo of Turnhout met regelmatig gepubliceerde eigen vacatures worden
|
||
host- en padgebonden toegevoegd, inclusief relevante IT-/infrastructuurwerkgevers.
|
||
- Iedere nieuwe bron heeft een gesaneerde fixture, positieve adaptertest, off-domain/route-negatie en minstens
|
||
twee geslaagde livecycli zonder parserwarnings voor activering.
|
||
- Bestaande regionale bronnen blijven alleen actief wanneer hun primaire vestiging of vacaturelocatie indicatief
|
||
binnen 40 km van Mol valt; historische vacatures en provenance worden bij retirement behouden.
|
||
- Bronbeleid, threat model, livecatalogus, onboarding, traceability en gebruikerscopy documenteren robots-, SSRF-,
|
||
sanitization- en locatiegrenzen; login, sollicitatie-endpoints en platformscraping blijven uitgesloten.
|
||
verification:
|
||
- .venv/Scripts/python.exe -m pytest tests/unit/test_regional_adapters.py tests/integration/test_seed_sources.py
|
||
tests/integration/test_profile_preferences.py tests/security/test_policy.py
|
||
- .venv/Scripts/python.exe manage.py makemigrations --check --dry-run
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/sources/adapters/regional.py
|
||
- apps/sources/management/commands/seed_sources.py
|
||
- config-data/seed_sources.yaml
|
||
- fixtures/pages/
|
||
- templates/sources/list.html
|
||
- docs/operations/LIVE_SOURCE_CATALOG.md
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: Profielruntime op postcode 2400 en 40 km gezet; SCK CEN, Cipal Schaubroeck, VanRoey, NTX en Thomas More
|
||
met fail-closed Mol-regioadapter, fixtures, docs en twee livecycli geactiveerd; 206 passed, 2 skipped, 84.12%,
|
||
browser desktop/360px groen.
|
||
- id: VR-201
|
||
title: Concrete live-bronnen inventariseren en juridisch/operationeel reviewen
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-011
|
||
- PR-017
|
||
- PR-018
|
||
depends_on:
|
||
- VR-102
|
||
- VR-106
|
||
summary: Vul voor Jens de gewenste werkgevers/overheden/instellingen in, controleer per domein publieke toegankelijkheid,
|
||
robots, voorwaarden, toegestane paden en frequentie en activeer alleen goedgekeurde bronnen.
|
||
acceptance_criteria:
|
||
- Iedere actieve bron heeft een actuele review, bewijsnotitie, parserfixture en succesvolle trialruns.
|
||
- Geen platformdenylistbron wordt als directe fetchbron geactiveerd.
|
||
- Een dekkingsteekproef en gemiste-bronnenlijst zijn gedocumenteerd.
|
||
verification:
|
||
- Volg docs/operations/SOURCE_ONBOARDING.md per bron
|
||
- Controleer source health na minstens twee geplande cycli
|
||
primary_paths:
|
||
- config-data/seed_sources.local.yaml
|
||
- Source admin
|
||
- docs/operations/SOURCE_ONBOARDING.md
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: Gemeente Mol en zeven Kempen-werkgevers na actuele menselijke review, fail-closed fixtures/tests en twee
|
||
livecycli geactiveerd; twaalf interessante regionale werkgevers als niet-scanbare waaklijst toegevoegd; TLS
|
||
gebruikt strikt de gepinde certifi-bundel zonder bypass.
|
||
- id: VR-202
|
||
title: Live IMAP- en SMTP-credentials configureren
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-016
|
||
- PR-054
|
||
- NFR-002
|
||
- PR-064
|
||
depends_on:
|
||
- VR-111
|
||
- VR-115
|
||
- VR-123
|
||
- VR-124
|
||
summary: Configureer de gewenste afzonderlijke platformmailboxen via de beveiligde UI, de Fernet-secretkey en
|
||
digestrecipient; test read-only import en mailverzending zonder credentials in Git/logs.
|
||
acceptance_criteria:
|
||
- Iedere platformmailbox gebruikt TLS, een dedicated alias en read-only mailboxselectie; Microsoft 365 gebruikt
|
||
app-only OAuth/XOAUTH2 en geen Basic Auth of app-wachtwoord.
|
||
- Dezelfde live testmail importeert per mailbox idempotent en alle geconfigureerde intervallen worden door de
|
||
scheduler gerespecteerd.
|
||
- SMTP verstuurt één testdigest en outboxstatus klopt.
|
||
- OAuth-clientcredentials en de encryptiesleutel staan alleen in de productie-secretstore/.env; eventuele Gmail/custom-app-wachtwoorden
|
||
zijn als ciphertext opgeslagen en sleutelrotatie is live getest.
|
||
verification:
|
||
- Volg Unraid mailboxchecklist
|
||
- Inspecteer logs op afwezigheid van secret/payload
|
||
primary_paths:
|
||
- /mnt/user/appdata/VacatureRadar/.env
|
||
- Bronnen -> Platformmailboxen
|
||
result:
|
||
completed_at: '2026-07-30'
|
||
note: M365 app-only OAuth/XOAUTH2 live ingericht met dedicated alias/map en Exchange-regel; negen platformmailboxen
|
||
importeerden dezelfde live testmail idempotent, schedulerstatus was correct, testdigest stond sent en logs
|
||
bleven payload-/secretvrij.
|
||
- id: VR-203
|
||
title: Productiedomein, TLS en reverse proxy activeren
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- NFR-001
|
||
- NFR-009
|
||
- PR-064
|
||
depends_on:
|
||
- VR-115
|
||
- VR-117
|
||
summary: Koppel het gekozen interne/publieke domein aan een TLS-reverse proxy en vul exacte Django host/origin/securitysettings
|
||
in.
|
||
acceptance_criteria:
|
||
- Alle externe requests gaan via HTTPS en HTTP redirect correct.
|
||
- ALLOWED_HOSTS en CSRF origins zijn exact, secure cookies/redirect zijn aan.
|
||
- PostgreSQL, Redis, Ollama en adminpoorten zijn niet publiek.
|
||
- Login, logout, CSRF POST en health werken achter de proxy.
|
||
verification:
|
||
- Voer reverse-proxy smoke-test uit vanaf een externe browser
|
||
- Controleer headers en TLS-configuratie
|
||
primary_paths:
|
||
- Unraid reverse proxy
|
||
- /mnt/user/appdata/vacatureradar/config/.env
|
||
result:
|
||
completed_at: '2026-07-29'
|
||
note: Publiek domein, HTTP-naar-HTTPS, TLS/securityheaders, DEBUG=False, secure cookies, CSRF-gastlogin, kernroutes
|
||
en readiness live bewezen in docs/audit/FINAL_ACCEPTANCE.md op 2026-07-29; interne diensten zijn uitsluitend
|
||
containerintern bereikbaar.
|
||
- id: VR-204
|
||
title: Immutable containerimage publiceren
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-009
|
||
- PR-064
|
||
depends_on:
|
||
- VR-115
|
||
- VR-117
|
||
summary: Publiceer de geverifieerde releaseimage naar de gekozen private registry, pin Unraid op tag+digest en
|
||
test pull/rollback.
|
||
acceptance_criteria:
|
||
- Registrytoken heeft minimale push/pullscope en staat alleen in CI/Unraid secretstore.
|
||
- Image heeft semver-tag, commitlabel, digest, SBOM en checksum/release notes.
|
||
- Unraid gebruikt geen CHANGE_ME of ongecontroleerde latest-tag.
|
||
verification:
|
||
- Pull image op schone host
|
||
- Start smoke stack en rollback naar vorige digest
|
||
primary_paths:
|
||
- .gitea/workflows/release.yml
|
||
- docker-compose.unraid.yml
|
||
result:
|
||
completed_at: '2026-07-30'
|
||
note: Gitea private registry publiceerde v0.3.15 als immutable digest met commitlabel, SPDX-SBOM, checksums
|
||
en release notes; Unraid pull, digest-pin, healthy smoke en rollback naar 0.3.14 plus herstel zijn live geslaagd.
|
||
- id: VR-205
|
||
title: Gelicenseerde Belgische geodatabron laden
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- PR-002
|
||
- PR-041
|
||
- NFR-002
|
||
depends_on:
|
||
- VR-104
|
||
summary: Selecteer een actuele, voor lokaal gebruik en distributie geschikte postcode/municipality-dataset, leg
|
||
licentie/versie/checksum vast en laad ze met de reeds geïmplementeerde importer.
|
||
acceptance_criteria:
|
||
- Herkomst, licentie, versie, download-/reviewdatum en checksum zijn vastgelegd.
|
||
- Data bevat alleen noodzakelijke locatievelden en geen persoonsgegevens.
|
||
- Importvalidatie en een steekproef voor relevante Belgische regio's slagen.
|
||
verification:
|
||
- Draai geodata importcommand met --validate-only en daarna normale import
|
||
- Voer locatie- en scoretests tegen lokale dataset uit
|
||
primary_paths:
|
||
- lokale geodatafile
|
||
- config-data/geodata/README.local.md
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: GeoNames België postcodedataset 2026-04-03 onder CC BY 4.0 gereviewd, checksums vastgelegd, 2781 unieke
|
||
rijen gevalideerd en 5562 lookuprecords geïmporteerd; 2400 Mol opgelost naar 51.1919, 5.1166 en actieve profielscores
|
||
herberekend.
|
||
- id: VR-206
|
||
title: Premium Stitch-cockpit en deterministische IT-focus
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-040
|
||
- PR-050
|
||
- PR-051
|
||
- NFR-004
|
||
- NFR-008
|
||
depends_on:
|
||
- VR-119
|
||
- VR-120
|
||
- VR-205
|
||
summary: Audit de volledige gebruikersflow in code en browser, voorkom dat niet-IT-vacatures de dagelijkse radar
|
||
vervuilen en benut de Stitch-compositie veel dominanter op mobiel, desktop en widescreen.
|
||
acceptance_criteria:
|
||
- Een deterministische en uitlegbare IT-relevantieregel heeft voorrang op scoring en AI; niet-IT-vacatures zijn
|
||
standaard afwezig uit Vandaag en de vacaturefeed maar blijven via een expliciete archiefkeuze inspecteerbaar.
|
||
- De vacaturefeed gebruikt echte score-evidence, bruikbare relevantie-/match-/sorteerfilters en toont standaard
|
||
de meest relevante IT-kansen in plaats van louter de nieuwste bronrecords.
|
||
- Dashboard, vacaturelijst en vacaturedetail nemen de bruikbare Stitch-panelhiërarchie, informatiedichtheid en
|
||
actiepatronen over zonder fictieve metrics, quick-apply of externe frontendafhankelijkheden.
|
||
- De shell en kernlayouts schalen inhoudelijk tussen 320 en 2560 px; widescreen voegt bruikbare kolommen/panelen
|
||
toe en laat de inhoud niet op een smalle 1280px-strook staan.
|
||
- Focus, headings, labels, lege toestanden, dark/light contrast, mobiele navigatie en reduced motion blijven toegankelijk;
|
||
kernroutes hebben geen horizontale paginaoverflow of browserconsolefouten.
|
||
verification:
|
||
- uv run pytest tests/unit/test_relevance.py tests/unit/test_scoring.py tests/integration/test_views.py tests/e2e/test_vr114_browser_and_accessibility.py
|
||
- ./scripts/codex_verify.sh
|
||
- Browsermatrix op 2560x1440, 1920x1080, 1440x900, 1024x768, 390x844 en 320x800
|
||
primary_paths:
|
||
- apps/jobs/services/relevance.py
|
||
- apps/jobs/services/scoring.py
|
||
- apps/jobs/views.py
|
||
- templates/dashboard/today.html
|
||
- templates/jobs/list.html
|
||
- templates/jobs/detail.html
|
||
- static/css/app.css
|
||
- docs/design/STITCH_INTEGRATION_PLAN.md
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: 'Volledige code- en browseraudit: deterministische IT-focus, laatste gebruikersscore, premium Stitch-feed/detail
|
||
en adaptieve 320-2560px-layout; 225 tests groen en browsermatrix geslaagd.'
|
||
- id: VR-207
|
||
title: Cv-gestuurd field- en infrastructuurprofiel
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-002
|
||
- PR-040
|
||
- PR-041
|
||
- NFR-002
|
||
- NFR-004
|
||
depends_on:
|
||
- VR-206
|
||
summary: Breid de begeleide profielconfiguratie uit voor een ervaren IT field-/infrastructuurprofiel en voorkom
|
||
dat een brede, relevante skillset de matchscore kunstmatig verlaagt. Persoonlijke cv-data blijft uitsluitend
|
||
in de gebruikersdatabase en komt niet in repositoryfixtures of documentatie.
|
||
acceptance_criteria:
|
||
- Rollen en skills zijn in begrijpelijke categorieën selecteerbaar voor field service, infrastructuur, Microsoft
|
||
365/endpoint, netwerk/security, back-up/monitoring, virtualisatie, VoIP en automation.
|
||
- Relevante IT-ervaring is via een selectielijst configureerbaar en wordt deterministisch vergeleken met expliciet
|
||
gevraagde ervaringsjaren; onbekende ervaring leidt niet tot uitsluiting.
|
||
- Ambigue field-/implementatietitels gelden alleen als IT wanneer de vacaturetekst tevens een sterk technisch
|
||
contextsignaal bevat; niet-IT field service blijft gefilterd.
|
||
- Meer relevante cv-skills aanvinken verwatert de skillscore niet onbeperkt en niet-vermelde voorkeurskills worden
|
||
niet als bewezen tekort gepresenteerd.
|
||
- Bestaande vrije profielwaarden blijven selecteerbaar en persoonlijke gegevens uit cv's worden niet gecommit.
|
||
verification:
|
||
- uv run pytest tests/unit/test_relevance.py tests/unit/test_scoring.py tests/unit/test_profiles.py tests/integration/test_profile_preferences.py
|
||
- uv run python manage.py makemigrations --check --dry-run
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/profiles/forms.py
|
||
- apps/profiles/models.py
|
||
- apps/profiles/taxonomy.py
|
||
- apps/jobs/services/relevance.py
|
||
- apps/jobs/services/scoring.py
|
||
- templates/profiles/edit.html
|
||
- static/css/app.css
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: Cv-gestuurde gegroepeerde profielconfiguratie, ervaringsband, begrensde skill-evidence, contextgebonden
|
||
fieldrelevantie en lokale profielrescore geverifieerd; 232 tests groen en browsercontrole op ultrawide/390
|
||
px geslaagd.
|
||
- id: VR-208
|
||
title: Skillsvraag- en leerkansenradar zonder ervaringsscore
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-002
|
||
- PR-040
|
||
- PR-041
|
||
- PR-043
|
||
- PR-050
|
||
- NFR-004
|
||
depends_on:
|
||
- VR-207
|
||
summary: Maak ervaringsduur volledig informatief en bouw uit de actuele, relevante vacatures een uitlegbare marktvraaganalyse
|
||
met profieldekking, skillsfilters en concrete bijleerkansen.
|
||
acceptance_criteria:
|
||
- Ervaringsjaren en senioriteitslabels hebben geen invloed op score, aanbeveling of harde uitsluiting; de profielwaarde
|
||
is uitsluitend informatieve context en bestaande senioriteitsgewichten worden veilig genegeerd en opgeruimd.
|
||
- De analyse gebruikt alleen actieve IT-vacatures die voor het actieve profiel niet hard uitgesloten zijn en blijft
|
||
strikt gebruikersgescopeerd.
|
||
- Een deterministische, uitbreidbare skillcatalogus toont per technologie of capability in hoeveel vacatures een
|
||
expliciet tekstsignaal voorkomt en onderscheidt profieldekking van mogelijke leer-/bijscholingskansen.
|
||
- Het profiel biedt extra relevante skills als gegroepeerde checkboxes; de inzichtspagina biedt categorie- en
|
||
dekkingsfilters en links naar de onderliggende vacatures.
|
||
- Feiten, tekstinferenties en onbekende gegevens zijn in de Nederlandstalige UI duidelijk onderscheiden; lege
|
||
toestanden en layouts werken van 320 tot 2560 px zonder horizontale paginaoverflow.
|
||
verification:
|
||
- uv run pytest tests/unit/test_scoring.py tests/unit/test_skill_demand.py tests/integration/test_skill_insights.py
|
||
tests/integration/test_profile_preferences.py
|
||
- uv run python manage.py makemigrations --check --dry-run
|
||
- ./scripts/codex_verify.sh
|
||
- Browsercontrole op 2560x1440, 1440x900 en 390x844
|
||
primary_paths:
|
||
- apps/jobs/services/scoring.py
|
||
- apps/jobs/services/skill_demand.py
|
||
- apps/jobs/views.py
|
||
- apps/profiles/taxonomy.py
|
||
- templates/jobs/skill_insights.html
|
||
- static/css/app.css
|
||
- docs/architecture/SCORING_ENGINE.md
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: Ervarings- en senioriteitsinvloed uit score en learning verwijderd; gebruikersgescopeerde Skillsradar
|
||
met actuele bronselectie, vraagbewijs, profieldekking, leerkansen, uitgebreide skillfilters en 2560/1440/390-browsercontrole
|
||
voltooid.
|
||
- id: VR-209
|
||
title: Stitch frontendcontract, audit en cockpit-shell
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-040
|
||
- PR-050
|
||
- PR-051
|
||
- NFR-004
|
||
- NFR-008
|
||
depends_on:
|
||
- VR-208
|
||
summary: Leg de volledige negen-schermenaudit en fidelitymatrix vast en vervang het globale design system, de
|
||
shell, navigatie en generieke browserstates door de Stitch Intelligence Cockpit.
|
||
acceptance_criteria:
|
||
- Contract en integratieplan bevatten alle negen schermen, afmetingen, componenten, route/data-mapping, fidelitydoelen,
|
||
responsive/accessibilityrisico's en legacy-opruiming.
|
||
- De enige productieshell gebruikt de lokale Stitch-tokens, compacte navigatie, contextbar, mobile drawer, skiplink,
|
||
focusstaten en echte statusdata zonder externe runtimeassets.
|
||
- Login, meldingen, lege toestanden en generieke foutstates gebruiken dezelfde visuele taal en blijven zonder
|
||
JavaScript bruikbaar.
|
||
verification:
|
||
- uv run pytest tests/integration/test_views.py tests/e2e/test_vr114_browser_and_accessibility.py
|
||
- uv run ruff check .
|
||
primary_paths:
|
||
- docs/design/STITCH_FRONTEND_CONTRACT.md
|
||
- docs/design/STITCH_INTEGRATION_PLAN.md
|
||
- templates/base.html
|
||
- static/css/app.css
|
||
- static/js/app.js
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: Volledige negen-schermenaudit, fidelitymatrix, bindend frontendcontract en nieuwe lokale Stitch-cockpit-shell
|
||
met gesplitst design system, mobile navigatie en generieke foutstates; relevante tests groen.
|
||
- id: VR-210
|
||
title: Stitch dashboard en vacature-intelligence
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-040
|
||
- PR-041
|
||
- PR-050
|
||
- NFR-004
|
||
depends_on:
|
||
- VR-209
|
||
summary: Vervang dashboard, vacatureverkenner en detail door de echte Stitch-composities met database-aggregaties,
|
||
uitlegbare scores, provenance en veilige acties.
|
||
acceptance_criteria:
|
||
- Dashboard toont echte dag-, match-, filter-, duplicaat-, sollicitatie-, activiteit- en brongezondheidsdata met
|
||
beste matches als dominante feed.
|
||
- De explorer heeft serverfilters, actieve chips, paginering en een brede master/detailcompositie die querystring
|
||
en browser-back behoudt.
|
||
- Het detail toont scorebewijs, inhoud, provenance, versies, duplicaten, sollicitatiestatus en een responsive
|
||
actiedock; ervaring telt nergens als scorefactor en externe links blijven veilig.
|
||
verification:
|
||
- uv run pytest tests/integration/test_views.py tests/unit/test_scoring.py tests/unit/test_relevance.py
|
||
primary_paths:
|
||
- apps/core/views.py
|
||
- apps/jobs/views.py
|
||
- apps/jobs/services/cockpit.py
|
||
- templates/dashboard/today.html
|
||
- templates/jobs/list.html
|
||
- templates/jobs/detail.html
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: Dashboard, vacatureverkenner en detail volledig naar Stitch-composities vervangen met echte cockpitaggregaties,
|
||
laatste profielscore, master/detailselectie, provenance, versies, duplicaten en veilige acties; relevante
|
||
scoring/relevance/viewtests groen.
|
||
- id: VR-211
|
||
title: Stitch pipeline, radarprofiel en brongezondheid
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-002
|
||
- PR-050
|
||
- PR-051
|
||
- NFR-004
|
||
depends_on:
|
||
- VR-210
|
||
summary: Vervang sollicitaties, zoekprofiel en bronnen door de functionele Stitch-pipeline, radarconfigurator
|
||
en source-healthinterface.
|
||
acceptance_criteria:
|
||
- Sollicitaties bieden kanban en lijstfallback, gebruikersgescopeerde POST-statuswijziging, deadlines, contact-
|
||
en timelinecontext.
|
||
- Het zoekprofiel groepeert echte selecties, toont revisie-informatie en een server-rendered preview uit de laatste
|
||
echte match.
|
||
- Bronnen tonen policy, runs, fout/succes, volgende planning, parser, tellingen, retry en bestaande beveiligde
|
||
import-/mailboxflows.
|
||
verification:
|
||
- uv run pytest tests/integration/test_applications.py tests/integration/test_profile_preferences.py tests/integration/test_sources_manual_import.py
|
||
tests/integration/test_source_health.py
|
||
primary_paths:
|
||
- apps/jobs/views.py
|
||
- apps/profiles/views.py
|
||
- apps/sources/views.py
|
||
- templates/applications
|
||
- templates/profiles
|
||
- templates/sources/list.html
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: Stitch-kanban met gescopeerde auditbare status-POST, dossiereditor en tijdlijn; gegroepeerde radarconfigurator
|
||
met echte scorepreview/revisies; health-first bronnenconsole met policy/runbewijs, retry, mailbox- en importflows.
|
||
Relevante tests groen.
|
||
- id: VR-212
|
||
title: Stitch automation, activiteit en werkgeversintelligence
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- PR-040
|
||
- PR-050
|
||
- PR-051
|
||
- NFR-002
|
||
- NFR-004
|
||
depends_on:
|
||
- VR-211
|
||
summary: Bouw de ontbrekende activiteit- en werkgeversroutes en vervang systeemstatus door een echte afgeleide
|
||
automationcockpit.
|
||
acceptance_criteria:
|
||
- Automation toont echte pipeline-, run-, score-, notificatie-, scheduling-, database- en configuratiestatus en
|
||
labelt niet-beschikbare infrastructuur eerlijk.
|
||
- Activiteit combineert betrouwbare, gebruikersgescopeerde gebeurtenissen in een filterbare, gelinkte en gepagineerde
|
||
tijdlijn.
|
||
- Werkgevers index/detail aggregeren echte werkgever-, vacature-, score-, bron- en sollicitatiedata zonder CRM-
|
||
of marktclaims te verzinnen.
|
||
verification:
|
||
- uv run pytest tests/integration/test_intelligence_views.py tests/integration/test_views.py
|
||
primary_paths:
|
||
- apps/jobs/services/activity.py
|
||
- apps/jobs/services/employer_intelligence.py
|
||
- apps/jobs/views.py
|
||
- apps/jobs/urls.py
|
||
- apps/core/views.py
|
||
- templates/activity
|
||
- templates/employers
|
||
- templates/system/status.html
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: Echte automationcockpit met 24u-pipeline en eerlijke runtimeconfiguratie; gepagineerde/filterbare activiteitreadservice;
|
||
werkgeversindex/detail met vacature-, score-, bron- en dossieraggregaties. Nieuwe routes, templates en scope-tests
|
||
groen.
|
||
- id: VR-213
|
||
title: Stitch responsive validatie en legacyverwijdering
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- NFR-004
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-212
|
||
summary: Rond de high-fidelity replacement af met browsermatrix, accessibility, elf screenshots, legacy-audit,
|
||
documentatie en volledige regressiegate.
|
||
acceptance_criteria:
|
||
- Alle negen schermen en kernflows zijn visueel en functioneel gecontroleerd tussen 360 en 1440 px, met aanvullende
|
||
ultrawidecontrole en schone browserconsole.
|
||
- Elf verplichte validatiescreenshots bestaan; majeure afwijkingen, accessibility- en querybevindingen staan in
|
||
het eindrapport.
|
||
- Oude visuele selectors, dode partials/JS en parallelle shellmarkup zijn verwijderd; de Stitch-frontend is de
|
||
enige normale productiefrontend.
|
||
- De volledige verificatiegate slaagt en backlog, projectstatus, traceability, README en changelog zijn bijgewerkt.
|
||
verification:
|
||
- ./scripts/codex_verify.sh
|
||
- Browsermatrix 1440x900, 1280x800, 1024x768, 768x1024, 390x844 en 360x800
|
||
primary_paths:
|
||
- static/css/app.css
|
||
- static/js/app.js
|
||
- tests/e2e
|
||
- artifacts/visual-validation
|
||
- docs/design/STITCH_INTEGRATION_REPORT.md
|
||
result:
|
||
completed_at: '2026-07-22'
|
||
note: Alle negen Stitch-schermen zijn browsergevalideerd van 360 tot 2560 px; elf screenshots, accessibility-/legacy-/queryaudit
|
||
en documentatie afgerond. Volledige gate groen met 248 tests, 2 optionele skips en 84,40% coverage.
|
||
- id: VR-214
|
||
title: Herstel het Unraid Dockerman-containericoon
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-213
|
||
summary: Vervang de fragiele runtime-SVG voor de Dockerman-tegel door een lokale rasterasset en dek het volledige
|
||
Unraid-label- en packagingcontract af.
|
||
acceptance_criteria:
|
||
- Dockerman verwijst via de gepubliceerde webpoort naar een lokale PNG die door collectstatic in de image wordt
|
||
opgenomen.
|
||
- De browserfavicon blijft lokaal en ongewijzigd beschikbaar.
|
||
- Een regressietest controleert de exacte WebUI- en icoonlabels, PNG-signatuur en verwachte afmetingen.
|
||
- Het Unraid-runbook beschrijft het cachegedrag en de veilige refreshstap.
|
||
verification:
|
||
- uv run pytest tests/unit/test_deployment_configuration.py tests/integration/test_views.py
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- docker-compose.unraid.yml
|
||
- static/img/vacatureradar-docker.png
|
||
- tests/unit/test_deployment_configuration.py
|
||
- docs/operations/UNRAID_DEPLOYMENT.md
|
||
result:
|
||
completed_at: '2026-07-25'
|
||
note: Dockerman-icoon vervangen door lokale 256x256 PNG via exact Unraid-poortlabel; URL, PNG-signatuur en afmetingen
|
||
regressiegedekt. Volledige gate groen met 264 tests en 83,47% dekking. Live Unraid-image sha256:799825df1a343b6bee43695850454a5fdc977b5af3366077e6ac6aaeeb94f6f9
|
||
gebouwd en gerecreate; container healthy, readiness/liveness groen en PNG via LAN HTTP 200 (7111 bytes).
|
||
- id: VR-215
|
||
title: Corrigeer Dockermans server-side icoondownload
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-214
|
||
summary: Gebruik voor het Dockerman-icoon een concrete server-side URL omdat Unraid placeholders alleen voor WebUI-links
|
||
vervangt en niet voor icoondownloads.
|
||
acceptance_criteria:
|
||
- Het icoonlabel bevat geen IP- of poortplaceholder en is vanaf de Unraid-host bereikbaar.
|
||
- Dockerman maakt `VacatureRadar-icon.png` in zijn eigen icooncache aan.
|
||
- De Docker-tegel gebruikt de gecachte PNG terwijl WebUI-poortsubstitutie behouden blijft.
|
||
- De regressietest en het Unraid-runbook leggen dit onderscheid vast.
|
||
verification:
|
||
- uv run pytest tests/unit/test_deployment_configuration.py
|
||
- Live Unraid-recreate, cachecontrole en HTTP-smoke
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- docker-compose.unraid.yml
|
||
- tests/unit/test_deployment_configuration.py
|
||
- docs/operations/UNRAID_DEPLOYMENT.md
|
||
result:
|
||
completed_at: '2026-07-25'
|
||
note: Dockerman gebruikt nu concrete server-side loopback-URL zonder placeholders; live Unraid-container healthy,
|
||
HTTP-smoke groen, persistente en RAM-cache bevatten geldige 256x256 PNG en docker.json verwijst naar VacatureRadar-icon.png.
|
||
Gericht 5 tests en volledige gate groen met 264 tests en 83,44% dekking.
|
||
- id: VR-216
|
||
title: Premium UX-verfijning met rustige visuele hiërarchie
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-004
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-215
|
||
summary: Verfijn de bestaande Stitch-interface naar een premium, rustige cockpit met minder visuele ruis, selectiever
|
||
kleurgebruik en sterkere informatiehiërarchie zonder server-rendered flows te wijzigen.
|
||
acceptance_criteria:
|
||
- Donker en licht thema gebruiken gelaagde oppervlakken, zachtere scheidingen en cyan alleen voor primaire signalen
|
||
en acties; navigatie en labels gebruiken leesbare humane typografie.
|
||
- Dashboard, verkenner, detail, pipeline en profiel hebben een herkenbare eigen compositie met consistente componenten,
|
||
zonder nepdata of dode bediening.
|
||
- Mobiele KPI's staan compact boven de vouw, filters blijven bruikbaar en de pipeline scrolt intern zonder pagina-overflow
|
||
tussen 360 en 1440 px.
|
||
- Browsercontrole op 390 en 1280 px dekt donker en licht thema, kernflows en een schone console.
|
||
verification:
|
||
- uv run pytest tests/e2e/test_vr114_browser_and_accessibility.py tests/integration/test_views.py
|
||
- ./scripts/codex_verify.sh
|
||
- Browsermatrix 390x844 en 1280x800 in donker en licht thema
|
||
primary_paths:
|
||
- static/css
|
||
- templates/dashboard/today.html
|
||
- templates/jobs/list.html
|
||
- templates/applications/list.html
|
||
- templates/profiles/list.html
|
||
- docs/design/STITCH_INTEGRATION_REPORT.md
|
||
result:
|
||
completed_at: '2026-07-25'
|
||
note: Premium calm-intelligence-laag voor dark/light, compacte mobiele KPI's, responsieve filtercommandobar,
|
||
intern scrollende pipeline en breed profiel. Bestaande login-CSP-fout opgelost met lokale externe JS. Browsermatrix
|
||
390/1280 zonder overflow en schone console; volledige gate groen met 264 tests, 2 optionele skips en 83,44%
|
||
dekking.
|
||
- id: VR-217
|
||
title: Borg Unraid-authenticatie en voeg interactieve radarillustraties toe
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-216
|
||
summary: Maak het bestaande SSH-deploymentprofiel expliciet en voeg een lokale, toegankelijke interactieve radarillustratie
|
||
toe op inhoudelijk passende cockpitstates zonder echte data of kernflows te vervangen.
|
||
acceptance_criteria:
|
||
- Deploymentdocumentatie en helper valideren de geconfigureerde Unraid-hostalias en falen met een concrete herstelmelding
|
||
wanneer de verkeerde SSH-identiteit wordt gekozen.
|
||
- Een herbruikbare lokale radarillustratie versterkt profiel- en lege radarstates met pointer-/focusrespons en
|
||
bevat geen externe asset, fictieve metric of betekenisdragende informatie.
|
||
- De illustratie degradeert zonder JavaScript, respecteert prefers-reduced-motion en blijft verborgen voor hulptechnologie;
|
||
kernacties en tekst blijven zelfstandig bruikbaar.
|
||
- Browsercontrole op 390 en 1280 px in donker en licht thema toont geen overflow, consolefout of concurrerende
|
||
visuele hiërarchie; de live Unraid-container is na deployment healthy.
|
||
verification:
|
||
- uv run pytest tests/unit/test_deployment_configuration.py tests/e2e/test_vr114_browser_and_accessibility.py
|
||
- Browsermatrix 390x844 en 1280x800 in donker en licht thema
|
||
- Live SSH-, containerhealth- en HTTP-smoke via de geconfigureerde hostalias
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- scripts/deploy_unraid.ps1
|
||
- docs/operations/UNRAID_DEPLOYMENT.md
|
||
- templates/components/radar_illustration.html
|
||
- templates/profiles/list.html
|
||
- static/css/premium.css
|
||
- static/js/app.js
|
||
result:
|
||
completed_at: '2026-07-26'
|
||
note: Unraid-authenticatie hersteld via gevalideerde hostalias unraid-itworx met root en dedicated sleutel;
|
||
fail-fast deployhelper toegevoegd. Interactieve lokale SVG-radar met pointerparallax, dark/light en reduced-motionfallback
|
||
toegevoegd. Browsermatrix 390/1280 zonder overflow of consolefouten; 265 tests groen. Live image sha256:4d30e01e778777d5a2cde4339a9b2ad006edb25cae387293737420152d65069d
|
||
healthy en readiness/CSS/JS HTTP 200.
|
||
- id: VR-218
|
||
title: Personaliseer merkidentiteit en verfijn de globale UX
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-004
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-217
|
||
summary: Vervang het generieke favicon door een herkenbaar radarsymbool, voeg configureerbare eigenaarssignatuur
|
||
toe en verfijn shell, oriëntatie, navigatie en micro-interacties tot een coherente persoonlijke premiumervaring.
|
||
acceptance_criteria:
|
||
- Favicon en hoofdlogo delen één scherp, lokaal en op 16 px herkenbaar radarsymbool met passende light/dark browsermetadata
|
||
en zonder externe assets.
|
||
- De shell en authenticatieschermen tonen VacatureRadar als product en een configureerbare eigenaarssignatuur
|
||
met veilige standaardwaarde Jens; deze branding wordt niet uit gebruikersdata of nepdata afgeleid.
|
||
- De topbar geeft compacte paginaoriëntatie, navigatie-/zoekinteracties hebben duidelijkere focus- en hoverstates
|
||
en mobiele bruikbaarheid blijft intact zonder extra bediening of JavaScriptafhankelijkheid.
|
||
- Browsercontrole op dashboard, verkenner, profiel en login bij 390 en 1280 px in donker en licht thema toont
|
||
geen overflow, consolefout of onduidelijke hiërarchie; live container en assets zijn healthy na deployment.
|
||
verification:
|
||
- uv run pytest tests/e2e/test_vr114_browser_and_accessibility.py tests/integration/test_auth_login.py tests/integration/test_views.py
|
||
- Browsermatrix 390x844 en 1280x800 in donker en licht thema
|
||
- Live favicon-, logo-, readiness- en containerhealth-smoke
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/core/context_processors.py
|
||
- static/favicon.svg
|
||
- static/img/vacatureradar-logo.svg
|
||
- templates/base.html
|
||
- templates/registration
|
||
- static/css/premium.css
|
||
- static/css/auth.css
|
||
result:
|
||
completed_at: '2026-07-26'
|
||
note: Persoonlijke Jens-branding, vernieuwd radarbeeldmerk en favicon, contextuele bovenbalk en verfijnde navigatie/zoekfocus
|
||
zijn regressiegedekt, responsief in de browser gevalideerd en live uitgerold als healthy image sha256:5f25f00c9b7efb166587901ff39b02c56c98fb9946ddef0a4546a22f18dc0802.
|
||
- id: VR-219
|
||
title: Herstel ultrawide uitlijning en versterk persoonlijke merklock-up
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-004
|
||
- NFR-008
|
||
depends_on:
|
||
- VR-218
|
||
summary: Breng de cockpit op brede schermen terug naar één voorspelbaar horizontaal grid en maak de persoonlijke
|
||
Jens-signatuur tot een herkenbaar onderdeel van de productbranding in plaats van losse metadata.
|
||
acceptance_criteria:
|
||
- Header, filters, hoofdpanelen en onderliggende secties delen op desktop en ultrawide hetzelfde startpunt en
|
||
dezelfde contentbreedte; er ontstaat geen grote toevallige lege linkerkolom.
|
||
- Verkenner en automatisering benutten 1920- en 3840-pixelbreedtes evenwichtig zonder uitgerekte leesregels, losgekoppelde
|
||
panelen of documentoverflow.
|
||
- Sidebar en bovenbalk tonen één consistente VacatureRadar-by-Jens-merklock-up; authenticatie en mobiele shell
|
||
behouden dezelfde eigenaarssignatuur zonder gebruikersnaam als merk te presenteren.
|
||
- Browsercontrole op 390, 1280, 1920 en 3840 px bevestigt consistente ankers, bruikbare paneelverhoudingen, schone
|
||
console en intacte toetsenbord-/mobiele flows.
|
||
verification:
|
||
- Browsermatrix dashboard, verkenner, automatisering en login op 390/1280/1920/3840 px
|
||
- uv run pytest tests/integration/test_auth_login.py tests/integration/test_views.py
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- templates/base.html
|
||
- static/css/layout.css
|
||
- static/css/premium.css
|
||
- static/css/responsive.css
|
||
result:
|
||
completed_at: '2026-07-26'
|
||
note: Ultrawide hoofdsecties delen één links verankerd 2800px-grid; explorer- en automationverhoudingen zijn
|
||
begrensd en Personal intelligence by Jens is de consistente lock-up. Browsermatrix 390/1280/1920/3840 schoon;
|
||
267 tests groen; live image sha256:86836f82cc543a7adb414e47b9667e9123bb9ceba10d629a53086273aaaae03f healthy
|
||
met readiness en asset-smokes.
|
||
- id: VR-220
|
||
title: Integreer de officiële ITWorx-merkidentiteit
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-004
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-219
|
||
summary: Vervang de tijdelijke tekstuele Jens-branding door de door de eigenaar aangeleverde officiële ITWorx.tech-wordmark
|
||
en cloud-check-identiteit, met VacatureRadar herkenbaar als product binnen dat merk.
|
||
acceptance_criteria:
|
||
- Sidebar, login en herstelpagina's gebruiken de transparante officiële ITWorx.tech-wordmark uit het aangeleverde
|
||
asset pack; VacatureRadar blijft duidelijk als productnaam aanwezig.
|
||
- Browserfavicon en app-/Dockericoon gebruiken de officiële cloud-check-symboliek in een compacte transparante,
|
||
lokaal gehoste en voor klein formaat geoptimaliseerde variant.
|
||
- Merkassets hebben betekenisvolle alt-/toegankelijkheidslabels, laden zonder externe runtimebron en blijven scherp
|
||
en leesbaar in donker/licht thema en op mobiel.
|
||
- Browsercontrole op login, dashboard en verkenner bij 390, 1280 en 1920 px toont correcte assets, geen overflow
|
||
of consolefouten; de live container levert brandingassets en readiness met HTTP 200.
|
||
verification:
|
||
- Controleer afmetingen, transparantie en bestandsgrootte van de afgeleide merkassets
|
||
- uv run pytest tests/integration/test_auth_login.py tests/integration/test_views.py tests/unit/test_deployment_configuration.py
|
||
- Browsermatrix 390/1280/1920 voor login, dashboard en verkenner
|
||
- Live asset-, favicon-, readiness- en containerhealth-smoke
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- static/img/itworx-wordmark.png
|
||
- static/img/itworx-app-icon.png
|
||
- static/img/vacatureradar-docker.png
|
||
- templates/base.html
|
||
- templates/registration
|
||
- static/css/premium.css
|
||
- static/css/auth.css
|
||
result:
|
||
completed_at: '2026-07-26'
|
||
note: Officiële aangeleverde ITWorx.tech-wordmark geïntegreerd in sidebar, topbar, login en herstel; cloud-check
|
||
exact afgeleid voor 512px favicon/app-icon en 256px Dockermanicoon. Browsermatrix 390/1280/1920 schoon, 267
|
||
tests groen en live image sha256:daf34407813b37cdf2d0fc65a482ded65375f89eedd3f0144a8c0ce206d41565 healthy
|
||
met readiness/PNG-smokes.
|
||
- id: VR-221
|
||
title: Scheid appmerk van ontwikkelaarsbranding
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-004
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-220
|
||
summary: Herstel VacatureRadar als zelfstandig productmerk met een nieuw professioneel radarlogo en favicon, en
|
||
plaats de aangeleverde ITWorx.tech-identiteit uitsluitend als subtiele ontwikkelaarscredit.
|
||
acceptance_criteria:
|
||
- VacatureRadar gebruikt een zelfstandig, vectorvriendelijk beeldmerk dat radar, detectie en een gevonden kans
|
||
combineert, scherp blijft op 16 px en visueel niet met het ITWorx-cloud-check-logo concurreert.
|
||
- Sidebar, login, favicon en Dockerman tonen het VacatureRadar-productmerk; ITWorx.tech staat alleen op geschikte
|
||
secundaire plaatsen als `Ontwikkeld door ITWorx.tech`.
|
||
- De ontwikkelaarscredit gebruikt de officiële aangeleverde ITWorx-wordmark lokaal en blijft ondergeschikt, toegankelijk
|
||
en leesbaar in donker/licht thema en op mobiel.
|
||
- Browsercontrole op login, dashboard en verkenner bij 390, 1280 en 1920 px toont correcte merkhiërarchie, geladen
|
||
assets, geen overflow of consolefouten; live container en alle assets zijn healthy.
|
||
verification:
|
||
- Inspecteer VacatureRadar-SVG op viewBox, elementeenvoud en klein-formaat-signatuur
|
||
- uv run pytest tests/integration/test_auth_login.py tests/integration/test_views.py tests/unit/test_deployment_configuration.py
|
||
- Browsermatrix 390/1280/1920 voor login, dashboard en verkenner
|
||
- Live logo-, favicon-, ontwikkelaarswordmark-, readiness- en containerhealth-smoke
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- static/favicon.svg
|
||
- static/img/vacatureradar-logo.svg
|
||
- static/img/vacatureradar-docker.png
|
||
- static/img/itworx-wordmark.png
|
||
- templates/base.html
|
||
- templates/registration
|
||
- static/css/premium.css
|
||
- static/css/auth.css
|
||
result:
|
||
completed_at: '2026-07-26'
|
||
note: VacatureRadar heeft een zelfstandig professioneel open-radar-logo, SVG-favicon en 256px Dockermanicoon;
|
||
officiële ITWorx.tech-wordmark staat alleen als Ontwikkeld door-credit. Twee beeldconcepten verkend, finale
|
||
geometrie handmatig als vijf-elementen-SVG gebouwd. Browsermatrix 390/1280/1920 schoon, 267 tests groen en
|
||
live image sha256:4184aeff33759b7a205637b0a0333b751b599141fe691a61965d2f1c56ca984a healthy met alle asset-smokes.
|
||
- id: VR-222
|
||
title: Voer een integrale premium visuele audit en herstelroadmap uit
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-004
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-221
|
||
summary: Audit de volledige cockpit als één designsysteem en herstel merkhiërarchie, uitlijning, informatiedichtheid,
|
||
interactiedoelen, responsief gedrag en motion tot een consistente premium productervaring.
|
||
acceptance_criteria:
|
||
- Een gedateerd auditrapport bevat geprioriteerde bevindingen, concreet gevolg, herstelactie en volledige roadmap
|
||
voor alle hoofdschermen, login en herstel.
|
||
- Topbar en hoofdcontent delen voorspelbare horizontale ankers; dashboard en activiteit zijn aantoonbaar compacter
|
||
zonder echte informatie te verbergen of controles onbruikbaar te maken.
|
||
- VacatureRadar blijft het enige primaire appmerk; ITWorx.tech staat uitsluitend als subtiele ontwikkelaarscredit
|
||
en geen concept- of chroma-keybeeld wordt als productasset geleverd.
|
||
- Controls, focus, reduced motion, dark/light en 390/768/1280/1440/1920/3840 px zijn gecontroleerd zonder overflow,
|
||
consolefouten of regressie in de server-rendered kernflow.
|
||
- De live container is healthy en levert het finale logo, favicon en de relevante CSS met HTTP 200.
|
||
verification:
|
||
- Browsermatrix voor alle hoofdschermen plus login in dark/light en 390/768/1280/1440/1920/3840 px
|
||
- uv run pytest tests/integration/test_auth_login.py tests/integration/test_views.py
|
||
- ./scripts/codex_verify.sh
|
||
- Live readiness-, containerhealth- en assetsmokes
|
||
primary_paths:
|
||
- docs/design/VISUAL_AUDIT_2026-07-26.md
|
||
- templates/base.html
|
||
- templates/dashboard/today.html
|
||
- templates/activity/list.html
|
||
- static/css/premium.css
|
||
- static/css/pages.css
|
||
- static/css/responsive.css
|
||
result:
|
||
completed_at: '2026-07-26'
|
||
note: 'Integrale audit en roadmap uitgevoerd: gedeeld contentframe, vijf dashboardmatches, compacte activiteit,
|
||
subtiele ITWorx-credit, grotere klikdoelen, reduced-motion, CSS-cacheversies en herstelde mobiele login. Browsermatrix
|
||
50 checks plus light/login schoon; 268 tests groen, 2 skips, 83,45% dekking. Live image sha256:7e1688db80241813a04e27038ef5e4afb64748868b6a97e353346f077be50b70
|
||
healthy; readiness en assets HTTP 200.'
|
||
- id: VR-223
|
||
title: Verfijn transparant productlogo en professionele widescreenshell
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-004
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-222
|
||
summary: Herstel de resterende merk- en shellfrictie uit de gebruikersscreenshot met een transparant cleaner productlogo,
|
||
één rustige sidebarfooter zonder dubbele accountidentiteit en beter benutte widescreenruimte.
|
||
acceptance_criteria:
|
||
- Het VacatureRadar-logo heeft geen donkere tegelachtergrond en blijft als eenvoudige vector scherp en herkenbaar
|
||
op dark/light, login, sidebar en klein formaat; favicon en Dockerman blijven doelgeschikt.
|
||
- De sidebar toont onderaan één samenhangende status-/ontwikkelaarszone en herhaalt de demo- of accountidentiteit
|
||
niet; accountacties blijven bereikbaar via het bestaande topbarmenu.
|
||
- De cockpit benut 1920, 2560 en 3840 px evenwichtiger zonder uitgerekte leesregels, losstaande topbaracties of
|
||
horizontale documentoverflow; mobiel en laptop blijven intact.
|
||
- Een gerichte vervolgcheck identificeert en herstelt bijkomende zichtbare shellproblemen, inclusief light/dark,
|
||
korte viewport en toetsenbord-/interactiestates.
|
||
- De live container is healthy en levert logo, favicon, CSS en readiness met HTTP 200.
|
||
verification:
|
||
- Browsermatrix dashboard, verkenner, automatisering, login op 390/1280/1920/2560/3840 px en korte sidebarviewport
|
||
- uv run pytest tests/integration/test_auth_login.py tests/integration/test_views.py tests/unit/test_deployment_configuration.py
|
||
- ./scripts/codex_verify.sh
|
||
- Live readiness-, containerhealth- en assetsmokes
|
||
primary_paths:
|
||
- static/img/vacatureradar-logo.svg
|
||
- static/css/layout.css
|
||
- static/css/premium.css
|
||
- static/css/responsive.css
|
||
- templates/base.html
|
||
result:
|
||
completed_at: '2026-07-27'
|
||
note: Transparant vier-elementenlogo zonder donkere tegel; één compacte sidebarfooter zonder dubbele accountidentiteit;
|
||
monochrome dark-mode ITWorx-credit en widescreenframes van 2200/2480 px. Browsermatrix 18 shellchecks plus
|
||
dark/light/login schoon; volledige gate tweemaal groen met 268 tests, 2 skips en 83,45% dekking. Live image
|
||
sha256:ea9e61a1febca59eb906bfdebcd9fd2b2c2b000189a8772f4abf09012722e921 healthy; readiness en assets HTTP
|
||
200.
|
||
- id: VR-301
|
||
title: Multi-tenant SaaS, teams en billing
|
||
status: deferred
|
||
priority: P3
|
||
requirement_ids:
|
||
- NFR-005
|
||
depends_on:
|
||
- VR-117
|
||
summary: Niet nodig voor de persoonlijke installatie. Alleen heroverwegen bij een apart productbesluit met tenantisolatie,
|
||
privacy, support en billingarchitectuur.
|
||
acceptance_criteria:
|
||
- Nieuwe productbeslissing en ADR vereist vóór implementatie.
|
||
verification:
|
||
- Niet uitvoeren binnen huidige scope.
|
||
primary_paths:
|
||
- docs/product/SCOPE_AND_NON_GOALS.md
|
||
- id: VR-224
|
||
title: Maak de repository-README functioneel en user-first met actuele screenshots
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-223
|
||
summary: Herbouw de repository-ingang rond het gebruikersprobleem, de dagelijkse workflow en een veilige quickstart,
|
||
ondersteund door compacte actuele productbeelden uit de echte server-rendered cockpit.
|
||
acceptance_criteria:
|
||
- De README begint bij doel, doelgroep en dagelijkse gebruikersflow; installatie, beheer, architectuur en agentoverdracht
|
||
volgen in een duidelijke progressieve volgorde zonder bestaande essentiële informatie te verliezen.
|
||
- Minstens vier actuele screenshots tonen verschillende functionele hoofdschermen, desktop en mobiel en dark/light;
|
||
ze bevatten geen secrets of persoonlijke gegevens en zijn lokaal, geoptimaliseerd en correct gelinkt.
|
||
- Quickstarts, poorten, lokale credentials, veiligheidsgrenzen en operationele documentatielinks zijn aantoonbaar
|
||
correct en maken duidelijk wat demo-, ontwikkel- en productiegebruik betekent.
|
||
- README-links en repositorydocumentatie valideren, de beelden zijn visueel gecontroleerd zonder overflow of consolefouten
|
||
en de volledige kwaliteitsgate slaagt.
|
||
verification:
|
||
- Browsercontrole van de vastgelegde routes en viewports
|
||
- python scripts/validate_repository.py
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- README.md
|
||
- docs/screenshots/readme/
|
||
- docs/quality/TRACEABILITY_MATRIX.md
|
||
- docs/ai/PROJECT_STATE.md
|
||
result:
|
||
completed_at: '2026-07-27'
|
||
note: User-first README met gecontroleerde quickstarts en vier actuele dark/light desktop-/mobielscreenshots;
|
||
browsermatrix zonder overflow of consolewaarschuwingen, repositoryvalidatie groen en volledige gate met 268
|
||
tests, 2 skips en 83,48% dekking.
|
||
- id: VR-302
|
||
title: Automatisch sollicitaties invullen of versturen
|
||
status: deferred
|
||
priority: P3
|
||
requirement_ids:
|
||
- PR-056
|
||
- AC-043
|
||
depends_on:
|
||
- VR-117
|
||
summary: Expliciet niet bouwen. Menselijke eindcontrole en verzending via het oorspronkelijke kanaal blijven een
|
||
vaste veiligheidsgrens.
|
||
acceptance_criteria:
|
||
- Er bestaat geen submitendpoint, browserbot of taak die extern solliciteert.
|
||
verification:
|
||
- Codezoekreview op submit/auto-apply; ADR-0006 blijft accepted.
|
||
primary_paths:
|
||
- docs/architecture/adrs/0006-no-automatic-applications.md
|
||
- id: VR-303
|
||
title: Publieke mobiele app en algemene externe API
|
||
status: deferred
|
||
priority: P3
|
||
requirement_ids:
|
||
- NFR-005
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-117
|
||
summary: Server-rendered single-user UI voldoet. Alleen uitvoeren bij concrete integratiebehoefte, met auth/scopes/versioning
|
||
en een nieuwe ADR.
|
||
acceptance_criteria:
|
||
- Geen externe API-oppervlakte toevoegen zonder consumer en threat model.
|
||
verification:
|
||
- Niet uitvoeren binnen huidige scope.
|
||
primary_paths:
|
||
- docs/api/openapi.yaml
|
||
- docs/architecture/adrs/0008-server-rendered-design.md
|
||
- id: VR-225
|
||
title: Hard publieke reverse-proxydeployment en gasttoegang uit
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- NFR-001
|
||
- NFR-006
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-224
|
||
summary: Maak de bestaande persoonlijke installatie veilig en reproduceerbaar bereikbaar achter Nginx Proxy Manager,
|
||
herstel publieke host- en CSRF-configuratie en voorkom dat een gedeeld demoaccount persistente data wijzigt.
|
||
acceptance_criteria:
|
||
- Eén publieke HTTPS-URL configureert hostvalidatie, CSRF, secure cookies, SSL-detectie en redirect zonder de
|
||
interne containerpoort in de externe origin op te nemen.
|
||
- Productie start fail-fast bij debugmodusgerelateerde onveiligheid, een zwakke secret, onveilige cookies, ontbrekende
|
||
HTTPS-origin of een schrijfbare publieke demo.
|
||
- Login- en importlimieten gebruiken in productie een gedeelde cache; forwarded client-IP’s worden alleen vanaf
|
||
expliciet vertrouwde proxy-CIDR’s geaccepteerd.
|
||
- Het gastaccount is server-side alleen-lezen, heeft een begrensde sessie, kan afmelden en toont de beperking
|
||
zichtbaar.
|
||
- Unraid-envpad, Nginx Proxy Manager, healthchecks, noindex, heruitrol en terugdraaien zijn exact gedocumenteerd.
|
||
verification:
|
||
- PYTHONPATH=/mnt/data/vr_windows_site/site-packages pytest -q
|
||
- python manage.py check
|
||
- python manage.py makemigrations --check --dry-run
|
||
- python scripts/validate_repository.py
|
||
- bash -n scripts/deploy_docker.sh scripts/entrypoint.sh scripts/unraid_aio_entrypoint.sh
|
||
- Live Nginx-, TLS-, CSRF-, Dockerhealth- en restore-smoke op de doelserver
|
||
primary_paths:
|
||
- config/settings.py
|
||
- apps/core/middleware.py
|
||
- apps/core/network.py
|
||
- apps/core/health.py
|
||
- scripts/configure_public_url.py
|
||
- docker-compose.unraid.yml
|
||
- docs/operations/NGINX_PROXY_MANAGER.md
|
||
- docs/quality/PRODUCTION_AUDIT_2026-07-27.md
|
||
result:
|
||
completed_at: '2026-07-27'
|
||
note: Publieke host/CSRF/HTTPS-configuratie, gedeelde Redis-rate-limiting, proxy-IPvertrouwen, cache-readiness,
|
||
noindex en read-only gastdemo geïmplementeerd. 295 tests groen met 2 correcte Playwrightskips; Django check,
|
||
migratiecheck, repositoryvalidatie, YAML-, syntax- en packagechecks groen. Live servervalidatie blijft extern.
|
||
- id: VR-226
|
||
title: Verdiep de user-first README met een volledige productgalerij
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-006
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-225
|
||
summary: Maak de productpresentatie overtuigender met een logisch opgebouwde, actuele galerij die de volledige
|
||
gebruikersreis toont zonder de README traag, repetitief of marketingmatig te maken.
|
||
acceptance_criteria:
|
||
- De README bevat minstens acht actuele beelden die dashboard, zoeken/analyse, skills, sollicitatieopvolging,
|
||
profiel, bronnen, automatisering en mobiel gebruik als één samenhangende productreis tonen.
|
||
- Desktopbeelden gebruiken een consistente professionele viewport en rustige uitsnede; dark/light en mobiel zijn
|
||
doelbewust verdeeld, zonder overgangsoverlays, overflow, consolefouten, secrets of persoonlijke gegevens.
|
||
- De galerij heeft korte taakgerichte captions, een scanbare compositie en compacte lokale assets; duplicatieve
|
||
beelden of losse decoratieve screenshots worden verwijderd of vervangen.
|
||
- De eerder aangetroffen VR-225-baselinefouten in lint en platformafhankelijke bestandsmoduscontrole zijn hersteld;
|
||
repositoryvalidatie en de volledige kwaliteitsgate slagen.
|
||
verification:
|
||
- Browsercontrole van alle vastgelegde routes op desktop en mobiel in dark/light
|
||
- uv run pytest tests/unit/test_public_configuration.py
|
||
- python scripts/validate_repository.py
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- README.md
|
||
- docs/screenshots/readme/
|
||
- scripts/configure_public_url.py
|
||
- tests/unit/test_public_configuration.py
|
||
- docs/quality/TRACEABILITY_MATRIX.md
|
||
- docs/ai/PROJECT_STATE.md
|
||
result:
|
||
completed_at: '2026-07-28'
|
||
note: README verdiept tot een klikbare user-first productreis met negen actuele beelden op 1920x1080 en 390x844
|
||
in dark/light; alle routes zonder overflow of consolewaarschuwingen. VR-225-lint en Windows-modusassertie
|
||
hersteld; 296 tests groen, 2 skips en 83,44% dekking.
|
||
- id: VR-227
|
||
title: Professionaliseer VacatureRadar integraal voor release 0.3.13
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- NFR-001
|
||
- NFR-006
|
||
- NFR-007
|
||
- NFR-008
|
||
- NFR-009
|
||
- NFR-010
|
||
depends_on:
|
||
- VR-226
|
||
summary: Voer de integrale responsive, UX-, accessibility-, performance-, observability-, security- en operationsroadmap
|
||
uit en vervang optionele browsercontrole door een verplichte releasegate.
|
||
acceptance_criteria:
|
||
- Hoofdcontent en topbar delen een gecentreerd adaptief frame; gastbanner, sticky elementen en pipeline blijven
|
||
bruikbaar van 390 tot 3440 px zonder documentoverflow.
|
||
- De vacatureflow is begrensd gepagineerd, globale zoekcopy is eerlijk, mobiel pipelinegebruik is verticaal en
|
||
demomutaties veroorzaken geen controlmuur.
|
||
- Playwright Chromium draait verplicht in CI op zes viewports, faalt op console/page errors en controleert focus,
|
||
kernreis en documentoverflow zonder skips.
|
||
- Automatisering toont een echte worker/beat-heartbeat en markeert niet-meetbare queuediepte eerlijk; benchmarkparserdekking
|
||
is volledig en reproduceerbaar.
|
||
- Baseline, performance, architectuur, operations, testing, traceability, externe acties en finale acceptance
|
||
zijn actueel en de volledige repositorygate slaagt.
|
||
verification:
|
||
- python -m scripts.benchmark --quick --skip-performance --json
|
||
- python -m pytest tests/e2e/test_vr114_browser_and_accessibility.py
|
||
- python -m pytest tests/unit/test_runtime_observability.py tests/unit/test_generic_html_adapter.py
|
||
- docker compose config
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- static/css/
|
||
- static/js/app.js
|
||
- templates/base.html
|
||
- apps/core/services/automation.py
|
||
- apps/core/tasks.py
|
||
- tests/e2e/test_vr114_browser_and_accessibility.py
|
||
- docs/audit/
|
||
- USER_INPUT_REQUIRED.md
|
||
result:
|
||
completed_at: '2026-07-29'
|
||
note: Release 0.3.13 professionaliseert responsive layout, mobiele gastflow, begrensde vacature-UX, verplichte
|
||
zes-viewport-Playwrightgate zonder skips, echte runtimeheartbeat, parserbenchmark, authdekking, SBOM en integrale
|
||
documentatie; volledige gate 312 tests groen, 84,16% dekking.
|
||
- id: VR-228
|
||
title: Optimaliseer de importpipeline voor release 0.3.14
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- NFR-007
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-227
|
||
summary: Profileer de PostgreSQL-import reproduceerbaar, verwijder aantoonbare N+1- en overbodige writes en lever
|
||
de geverifieerde optimalisatie veilig op zonder wijziging aan deduplicatie, scoring of datakwaliteit.
|
||
acceptance_criteria:
|
||
- Een fail-closed runner meet een disposable PostgreSQL-database met vaste fixture, warm-up en drie herhalingen.
|
||
- De geoptimaliseerde import reduceert queryvolume en doorlooptijd aantoonbaar tegenover 0.3.13 en rapporteert
|
||
p50, p95, throughput, geheugen en queryfamilies.
|
||
- Parserdekking blijft 12/12, dedupeprecision en -recall blijven 1,0, rankingchurn blijft nul en historische ScoreRuns
|
||
plus veldprovenance blijven intact.
|
||
- Regressietests begrenzen het queryvolume; de volledige kwaliteitsgate slaagt tweemaal en productieacceptatie
|
||
bewijst health, beperkte importsmoke, publieke kernflows en rollbackgereedheid.
|
||
verification:
|
||
- python -m scripts.benchmark_import --jobs 250 --iterations 3
|
||
- uv run pytest tests/integration/test_pipeline.py tests/unit/test_import_benchmark.py
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/jobs/services/pipeline.py
|
||
- scripts/benchmark.py
|
||
- scripts/benchmark_import.py
|
||
- tests/integration/test_pipeline.py
|
||
- docs/audit/IMPORT_PERFORMANCE_FINAL.md
|
||
result:
|
||
completed_at: '2026-07-29'
|
||
note: 'Release 0.3.14: geïsoleerde PostgreSQL-benchmark reduceert importduur 44,74% en queries minstens 63,73%;
|
||
twee volledige gates met 318 tests groen; productie healthy op image sha256:1ee84241, transactionele importsmoke
|
||
teruggerold en rollbackimage 0.3.13 beschikbaar.'
|
||
- id: VR-229
|
||
title: Herstel de publieke demo na de visuele 0.3.15-audit
|
||
status: done
|
||
priority: P1
|
||
requirement_ids:
|
||
- NFR-008
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-228
|
||
summary: Maak de publieke demo opnieuw representatief en tijdsbestendig, scheid mailboxingress van URL-fetching
|
||
en laat operationele statussen exact zeggen wat ze meten.
|
||
acceptance_criteria:
|
||
- Iedere nieuwe demosessie herstelt zes fictieve actuele vacatures, scores en toekomstige opvolgdatums zonder
|
||
duplicaten of groeiende ScoreRun-historiek.
|
||
- De demo toont negen fictieve, actieve platformmailboxkoppelingen zonder secrets of echte persoonsgegevens.
|
||
- E-mailbronnen worden nooit door de generieke URL-fetchscheduler gepland en oude mailboxpolicyfouten vervuilen
|
||
dashboard en activiteit niet meer.
|
||
- Navigatie en dashboard noemen het zoekprofiel expliciet actief zonder brongezondheid te suggereren; het lege
|
||
loginwachtwoordveld lijkt niet vooraf ingevuld.
|
||
- De negen kernroutes blijven in dark/light en op mobiel, desktop en ultrawide zonder overflow, consolefouten
|
||
of headingregressies bruikbaar; de volledige kwaliteitsgate slaagt.
|
||
verification:
|
||
- python -m pytest tests/integration/test_auth_login.py tests/integration/test_tasks_and_more_views.py
|
||
- Browseraudit op 390x844, 1280x600, 1440x900 en 3440x1440
|
||
- ./scripts/codex_verify.sh
|
||
primary_paths:
|
||
- apps/jobs/services/demo_seed.py
|
||
- apps/jobs/services/activity.py
|
||
- apps/jobs/services/cockpit.py
|
||
- apps/sources/tasks.py
|
||
- templates/base.html
|
||
- templates/dashboard/today.html
|
||
- templates/registration/login.html
|
||
- tests/integration/test_auth_login.py
|
||
- tests/integration/test_tasks_and_more_views.py
|
||
result:
|
||
completed_at: '2026-08-12'
|
||
note: Publieke demo wordt bij iedere sessie idempotent hersteld met 6 actuele fictieve vacatures, tijdsbestendige
|
||
opvolging en 9 fictieve mailboxkoppelingen; EMAIL-bronnen en demo-mailboxen zijn uit de verkeerde schedulers
|
||
en activityfeeds uitgesloten, statuscopy en loginplaceholder zijn gecorrigeerd. Gerichte 51 tests en volledige
|
||
gate met 327 tests groen, 84,04% dekking.
|
||
- id: VR-230
|
||
title: Herstel de immutable Gitea-releasepublicatie
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-229
|
||
summary: Verwijder de externe GitHub-API-rate-limit uit de releasebootstrap en publiceer de actuele productiebuild
|
||
opnieuw als aantoonbaar immutable private-registryimage.
|
||
acceptance_criteria:
|
||
- De uv-bootstrap is op een immutable actioncommit en een exacte uv-versie gepind.
|
||
- De releaseworkflow gebruikt voor uv-downloads geen GitHub Releases-API die op een gedeeld runner-IP kan limiteren.
|
||
- Gitea Actions publiceert een private registryimage met digest, SBOM, checksums en release notes.
|
||
- Unraid is op de gepubliceerde digest gepind en live health/readiness slagen.
|
||
verification:
|
||
- uv run pytest tests/unit/test_deployment_configuration.py
|
||
- ./scripts/codex_verify.sh
|
||
- Gitea Actions releasebewijs en live Unraid health/readiness
|
||
primary_paths:
|
||
- .gitea/workflows/release.yml
|
||
- tests/unit/test_deployment_configuration.py
|
||
- docs/audit/FINAL_ACCEPTANCE.md
|
||
result:
|
||
completed_at: '2026-08-12'
|
||
note: Releasebootstrap gepind op immutable setup-uv v8.1.0-commit en uv 0.11.12 via Astral-mirror; Gitea Actions-run
|
||
3062 publiceerde digest sha256:98f4b33d met checksum-geldige SBOM/release-evidence; Unraid gepind op volledige
|
||
digest en live health/readiness groen.
|
||
- id: VR-231
|
||
title: Sluit de operationele 0.3.17-restpunten
|
||
status: done
|
||
priority: P0
|
||
requirement_ids:
|
||
- NFR-009
|
||
depends_on:
|
||
- VR-230
|
||
summary: Verwijder de achterhaalde push-to-deployroute, herstel voldoende Docker-netwerkcapaciteit, valideer de
|
||
resterende mailboxfout en maak actuele versus historische deploymentstatus ondubbelzinnig.
|
||
acceptance_criteria:
|
||
- Main-pushes maken geen onbeperkt wachtende deployruns meer; alleen de immutable tagrelease bouwt en publiceert.
|
||
- Unraid heeft een persistente, conflictvrije default address pool met minstens 256 kleine bridge-netwerken.
|
||
- De Jobat-productiemailbox slaagt opnieuw via de bestaande OAuth/IMAP-taak of levert een exact extern restpunt.
|
||
- Projectstatus en deploymentdocumentatie beschrijven alleen het actuele releasepad als operationele waarheid.
|
||
verification:
|
||
- uv run pytest tests/unit/test_deployment_configuration.py
|
||
- ./scripts/codex_verify.sh
|
||
- Live Docker-netwerk-, mailbox-, container- en readinesssmokes
|
||
primary_paths:
|
||
- .gitea/workflows/release.yml
|
||
- docs/operations/GITEA_DEPLOYMENT.md
|
||
- docs/operations/UNRAID_DEPLOYMENT.md
|
||
- docs/ai/PROJECT_STATE.md
|
||
- tests/unit/test_deployment_configuration.py
|
||
result:
|
||
completed_at: '2026-08-12'
|
||
note: Oude main-pushdeploy verwijderd en run 3065 begrensd geannuleerd; Jobat OAuth/IMAP-herpoll groen met 61
|
||
duplicates en 0 fouten; Unraid persistent op conflictvrije 10.200.0.0/16→/24-pool gezet en live proefnetwerk
|
||
bewezen; na Docker-herstart alle vooraf actieve containers hersteld en geen unhealthy containers, VacatureRadar
|
||
publiek/intern healthy.
|