feat(legal): Zustimmungs-Nachweise mit IP, Gerät/Browser & Hash (v1.7.8)
Belastbarer Einwilligungsnachweis: - Schema/Migration: legal_acceptances + ipAddress, userAgent (contentHash bestand bereits) - Erfassung bei Registrierung und jeder Zustimmung (/api/legal/accept) - Admin /admin/legal: neue Spalten IP + Gerät/Browser + Hash; CSV-Export um ipAddress, userAgent, contentHash erweitert - Datenschutzerklärung + Dateninventar: IP/User-Agent als dokumentierter Beweiszweck ergänzt Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -29,7 +29,7 @@ export async function GET(req: NextRequest) {
|
||||
where: userFilter,
|
||||
orderBy: { acceptedAt: 'desc' },
|
||||
take: 2000,
|
||||
select: { id: true, userId: true, organizationId: true, documentType: true, documentVersion: true, context: true, acceptedAt: true },
|
||||
select: { id: true, userId: true, organizationId: true, documentType: true, documentVersion: true, context: true, acceptedAt: true, contentHash: true, ipAddress: true, userAgent: true },
|
||||
})
|
||||
|
||||
// Nur die notwendigen Nachweisdaten anreichern (E-Mail/Name) — keine überflüssigen Personendaten.
|
||||
@@ -43,11 +43,11 @@ export async function GET(req: NextRequest) {
|
||||
}))
|
||||
|
||||
if (format === 'csv') {
|
||||
const header = ['acceptedAt', 'email', 'name', 'documentType', 'documentVersion', 'context', 'organizationId']
|
||||
const header = ['acceptedAt', 'email', 'name', 'documentType', 'documentVersion', 'context', 'ipAddress', 'userAgent', 'contentHash', 'organizationId']
|
||||
const esc = (v: any) => `"${String(v ?? '').replace(/"/g, '""')}"`
|
||||
const lines = [header.join(',')]
|
||||
for (const r of rows) {
|
||||
lines.push([new Date(r.acceptedAt).toISOString(), r.email, r.name, r.documentType, r.documentVersion, r.context, r.organizationId || ''].map(esc).join(','))
|
||||
lines.push([new Date(r.acceptedAt).toISOString(), r.email, r.name, r.documentType, r.documentVersion, r.context, r.ipAddress || '', r.userAgent || '', r.contentHash || '', r.organizationId || ''].map(esc).join(','))
|
||||
}
|
||||
return new NextResponse(lines.join('\r\n'), {
|
||||
headers: {
|
||||
|
||||
Reference in New Issue
Block a user