Datenschutz Weg B nach Prüfung: Zusagen auf den Dienst begrenzt, [OFFEN]-Markierungen, Upload-Sperren
Abschnitt 11: Sperre und Kürzung ab dem Lesen unserer Antwort, nur je Beitrag und E-Mail-Adresse (neues Gesuch = neuer Beitrag); aussortierte Anfragen 30 Tage; feste Ausschlussliste der Websuche samt robots.txt; Kriterium für die Dauer der Reste; Kopie der Standardvertragsklauseln; Hinweis in der ersten Nachricht nennt den Widerspruch; Abschnitt 11 und 14: die KI sortiert aus, ein Mitarbeiter entscheidet über jede Antwort. Alarm-Postfach-Anbieter und Aufbewahrung der Server-Sicherungen stehen als sichtbare [OFFEN]-Markierung im Text (auch in Abschnitt 12). Tests: Pins angepasst, Markierungen nur die zwei erlaubten, neuer Test für Zusagen in Reichweite des Dienstes. Upload-Skript bricht ab, solange eine [OFFEN]-Markierung steht oder die Prüfsumme neben dem PDF nicht zur HTML passt. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
This commit is contained in:
1 parent
b3ca84a8e5
commit
23ab43f9fe
4 files changed
+100
-23
No files matched your search
@@ -1,5 +1,6 @@
|
||||
import { test } from 'node:test'
|
||||
import assert from 'node:assert/strict'
|
||||
import { createHash } from 'node:crypto'
|
||||
|
||||
// Hochladen der Datenschutzerklärung nach WOMS "Rechtliches" (scripts/datenschutz-hochladen.mjs): die Tests rufen main nur mit Nachbau-deps
|
||||
// auf, nie mit dem echten Schlüssel oder dem Netz. Das globale fetch wirft und zählt, damit ein Weg am Nachbau vorbei auffällt.
|
||||
@@ -13,7 +14,8 @@ const m = await import('../scripts/datenschutz-hochladen.mjs') // der Import lie
|
||||
const frueher = ['v1', 'v2', 'v3', 'v4', 'v5'].map((v, i) => ({ $id: `s${i}`, version: v, validFrom: `2026-09-0${i + 1}`, status: 'superseded', source: `x${i}` }))
|
||||
const AKTUELL = { $id: 'alt', version: 'v6', validFrom: '2026-10-05', status: 'current', source: 'kundenbereich@aaaaaaa:public/datenschutz.html' }
|
||||
// stand = das Datum, das im Nachbau der HTML-Datei hinter "Stand" steht (die PDF-Datei ist beliebiger Inhalt)
|
||||
function backend({ versionen = [...frueher, AKTUELL], karten = [{ $id: 'datenschutz', key: 'datenschutz' }], gitStatus = '', stand = '20.10.2026', vorhanden = () => true } = {}) {
|
||||
// zusatz = zusätzlicher Inhalt der HTML (zum Beispiel eine offene Markierung); summe = Inhalt der .sha256 (null = passend zur HTML, 'fehlt' = nicht lesbar)
|
||||
function backend({ versionen = [...frueher, AKTUELL], karten = [{ $id: 'datenschutz', key: 'datenschutz' }], gitStatus = '', stand = '20.10.2026', vorhanden = () => true, zusatz = '', summe = null } = {}) {
|
||||
const aufrufe = [], log = []
|
||||
const antwort = (obj) => ({ ok: true, status: 200, text: async () => JSON.stringify(obj) })
|
||||
const fetch = async (url, opt = {}) => {
|
||||
@@ -27,8 +29,12 @@ function backend({ versionen = [...frueher, AKTUELL], karten = [{ $id: 'datensch
|
||||
if (methode === 'PATCH' && pfad.includes('/collections/legalVersions/documents/')) return antwort({})
|
||||
throw new Error(`unerwartet: ${methode} ${pfad}`)
|
||||
}
|
||||
const html = () => Buffer.from(stand === null ? '<p class="meta">ohne Datum</p>' : `<p class="meta">Stand ${stand}</p>`)
|
||||
return { aufrufe, log, deps: { fetch, schluessel: () => 'test-schluessel', log: (z) => log.push(z), git: (args) => (args[0] === 'status' ? gitStatus : 'abc1234\n'), dateien: { existsSync: vorhanden, readFileSync: (rel) => (rel.endsWith('.html') ? html() : Buffer.from('x')) } } }
|
||||
const html = () => Buffer.from((stand === null ? '<p class="meta">ohne Datum</p>' : `<p class="meta">Stand ${stand}</p>`) + zusatz)
|
||||
const pruefsumme = () => {
|
||||
if (summe === 'fehlt') throw new Error('ENOENT')
|
||||
return Buffer.from(`${summe ?? createHash('sha256').update(html()).digest('hex')}\n`)
|
||||
}
|
||||
return { aufrufe, log, deps: { fetch, schluessel: () => 'test-schluessel', log: (z) => log.push(z), git: (args) => (args[0] === 'status' ? gitStatus : 'abc1234\n'), dateien: { existsSync: vorhanden, readFileSync: (rel) => (rel.endsWith('.html') ? html() : rel.endsWith('.sha256') ? pruefsumme() : Buffer.from('x')) } } }
|
||||
}
|
||||
const schreibend = (b) => b.aufrufe.filter((a) => a.methode !== 'GET')
|
||||
|
||||
@@ -91,6 +97,30 @@ test('Stand in der HTML muss der Freigabe entsprechen, sonst Abbruch vor jedem S
|
||||
const richtig = backend({ stand: '21.10.2026' })
|
||||
assert.equal(await m.main(['--freigabe=2026-10-21'], richtig.deps), 0, 'mit passender Freigabe geht derselbe Stand durch')
|
||||
})
|
||||
test('offene Markierung im Text: Abbruch vor jedem Schreiben, mit Nennung der Markierung; Kommentare zählen nicht', async () => {
|
||||
const offen = backend({ zusatz: '<p>bei <span class="offen">[OFFEN: Anbieter Alarm-Postfach]</span></p>' })
|
||||
assert.equal(await m.main(['--freigabe=2026-10-20'], offen.deps), 1)
|
||||
assert.ok(offen.log.some((z) => z.includes('offene Markierung') && z.includes('[OFFEN: Anbieter Alarm-Postfach]')), offen.log.join(' | '))
|
||||
const zweiMal = backend({ zusatz: '<p>[OFFEN: Aufbewahrung der Server-Sicherungen] und noch einmal [OFFEN: Aufbewahrung der Server-Sicherungen]</p>' })
|
||||
assert.equal(await m.main(['--freigabe=2026-10-20'], zweiMal.deps), 1)
|
||||
assert.equal(zweiMal.log.filter((z) => z.includes('offene Markierung'))[0].match(/Aufbewahrung der Server-Sicherungen/g).length, 1, 'jede Markierung nur einmal genannt')
|
||||
for (const b of [offen, zweiMal]) assert.equal(schreibend(b).length, 0)
|
||||
const kommentar = backend({ zusatz: '<!-- [OFFEN: nur eine Notiz im Quelltext] -->' })
|
||||
assert.equal(await m.main(['--freigabe=2026-10-20'], kommentar.deps), 0, 'eine Markierung im HTML-Kommentar ist nicht sichtbar')
|
||||
})
|
||||
test('Prüfsumme neben dem PDF muss zur HTML passen, sonst Abbruch vor jedem Schreiben (veraltetes PDF)', async () => {
|
||||
const veraltet = backend({ summe: 'a'.repeat(64) })
|
||||
assert.equal(await m.main(['--freigabe=2026-10-20'], veraltet.deps), 1)
|
||||
assert.ok(veraltet.log.some((z) => z.includes('das PDF ist nicht aus dieser HTML gedruckt') && z.includes('build-legal-pdfs.sh datenschutz')), veraltet.log.join(' | '))
|
||||
const fehlt = backend({ summe: 'fehlt' })
|
||||
assert.equal(await m.main(['--freigabe=2026-10-20'], fehlt.deps), 1)
|
||||
assert.ok(fehlt.log.some((z) => z.includes('WEBklar-Datenschutzerklaerung.pdf.sha256') && z.includes('fehlt')), fehlt.log.join(' | '))
|
||||
for (const b of [veraltet, fehlt]) assert.equal(schreibend(b).length, 0)
|
||||
// passende Prüfsumme (Standard im Nachbau): der Upload geht durch
|
||||
const passt = backend()
|
||||
assert.equal(await m.main(['--freigabe=2026-10-20'], passt.deps), 0)
|
||||
assert.equal(schreibend(passt).length, 4)
|
||||
})
|
||||
test('--probe liest nur: Bucket, Karte und Versionen, meldet eine fehlende Karte als Stopp', async () => {
|
||||
const b = backend()
|
||||
assert.equal(await m.main(['--probe'], b.deps), 0)
|
||||
|
||||
Reference in new issue
Block a user