195 lines
8.2 KiB
JavaScript
195 lines
8.2 KiB
JavaScript
import { test, beforeEach, afterEach } from 'node:test'
|
|
import assert from 'node:assert/strict'
|
|
import { config } from '../server/config.js'
|
|
import * as schalter from '../server/services/termine/schalter.js'
|
|
|
|
const { termineAus, termineFuerKunde, termineModus } = schalter
|
|
// Namensraum für termineTextformNoetig: fehlt der Export, scheitert nur sein Test
|
|
const termineTextformNoetig = (email) => schalter.termineTextformNoetig(email)
|
|
|
|
const TERMINE_ENV = [
|
|
'TERMINE_ENABLED',
|
|
'TERMINE_PILOT_EMAILS',
|
|
'TERMINE_FORM_MIN_SECONDS',
|
|
'TERMINE_MIN_ANTWORT_MS',
|
|
'APPWRITE_COLLECTION_TERMINE_CONFIG',
|
|
'APPWRITE_COLLECTION_TERMINE_BOOKINGS',
|
|
'APPWRITE_COLLECTION_TERMINE_CLAIMS',
|
|
'APPWRITE_COLLECTION_TERMINE_OUTBOX',
|
|
]
|
|
|
|
let original
|
|
beforeEach(() => {
|
|
original = { ...config.termine }
|
|
})
|
|
afterEach(() => {
|
|
Object.assign(config.termine, original)
|
|
})
|
|
|
|
/** Frische config.js-Instanz mit genau diesen Termine-Umgebungsvariablen (alle anderen entfernt). */
|
|
let freshCounter = 0
|
|
async function freshConfig(env = {}) {
|
|
const saved = Object.fromEntries(TERMINE_ENV.map((key) => [key, process.env[key]]))
|
|
for (const key of TERMINE_ENV) delete process.env[key]
|
|
Object.assign(process.env, env)
|
|
try {
|
|
freshCounter += 1
|
|
return (await import(`../server/config.js?termine-test=${freshCounter}`)).config
|
|
} finally {
|
|
for (const key of TERMINE_ENV) {
|
|
if (saved[key] === undefined) delete process.env[key]
|
|
else process.env[key] = saved[key]
|
|
}
|
|
}
|
|
}
|
|
|
|
test('Konfiguration: Vorgaben ohne Umgebungsvariablen', async () => {
|
|
const fresh = await freshConfig()
|
|
// avvVersion: Fassung der Bestellunterlagen (Berliner Tag des Fassungs-Commits), hier nur das Datumsmuster
|
|
assert.match(fresh.termine.avvVersion, /^\d{4}-\d{2}-\d{2}$/)
|
|
assert.deepEqual(fresh.termine, {
|
|
mode: 'off',
|
|
pilotEmails: [],
|
|
avvVersion: fresh.termine.avvVersion,
|
|
holdMinutes: 30,
|
|
zelleMin: 5,
|
|
mailsProStunde: 200,
|
|
mailsProFunktion: 40,
|
|
mailsReserve: 0.25,
|
|
mailListe: 100,
|
|
loeschDeckel: 2000,
|
|
loeschDeckelGesamt: 20000,
|
|
zellenDeckel: 5000,
|
|
formMinSekunden: 3,
|
|
minAntwortMs: 300,
|
|
})
|
|
assert.equal(fresh.collections.termineConfig, 'termineConfig')
|
|
assert.equal(fresh.collections.termineBookings, 'termineBookings')
|
|
assert.equal(fresh.collections.termineClaims, 'termineClaims')
|
|
assert.equal(fresh.collections.termineOutbox, 'termineOutbox')
|
|
})
|
|
|
|
test('Konfiguration: Umgebungsvariablen werden gelesen und bereinigt', async () => {
|
|
const fresh = await freshConfig({
|
|
TERMINE_ENABLED: ' Pilot ',
|
|
TERMINE_PILOT_EMAILS: ' Kenso.Gri@Gmail.com, ,justin@webklar.com ',
|
|
TERMINE_FORM_MIN_SECONDS: '0',
|
|
TERMINE_MIN_ANTWORT_MS: '0',
|
|
APPWRITE_COLLECTION_TERMINE_CONFIG: 'tConfig',
|
|
APPWRITE_COLLECTION_TERMINE_BOOKINGS: 'tBookings',
|
|
APPWRITE_COLLECTION_TERMINE_CLAIMS: 'tClaims',
|
|
APPWRITE_COLLECTION_TERMINE_OUTBOX: 'tOutbox',
|
|
})
|
|
assert.equal(fresh.termine.mode, 'pilot')
|
|
assert.deepEqual(fresh.termine.pilotEmails, ['kenso.gri@gmail.com', 'justin@webklar.com'])
|
|
assert.equal(fresh.termine.formMinSekunden, 0)
|
|
assert.equal(fresh.termine.minAntwortMs, 0)
|
|
assert.deepEqual(
|
|
[fresh.collections.termineConfig, fresh.collections.termineBookings, fresh.collections.termineClaims, fresh.collections.termineOutbox],
|
|
['tConfig', 'tBookings', 'tClaims', 'tOutbox'],
|
|
)
|
|
})
|
|
|
|
test('Konfiguration: leerer oder unbekannter Schalter ist off, ungueltige Sekunden fallen auf 3', async () => {
|
|
for (const value of ['', ' ', 'banane', 'true', '1', 'ON ']) {
|
|
const fresh = await freshConfig({ TERMINE_ENABLED: value })
|
|
assert.equal(fresh.termine.mode, value.trim().toLowerCase() === 'on' ? 'on' : 'off', `TERMINE_ENABLED=${JSON.stringify(value)}`)
|
|
}
|
|
for (const value of ['', 'abc', '-1', 'NaN']) {
|
|
const fresh = await freshConfig({ TERMINE_FORM_MIN_SECONDS: value })
|
|
assert.equal(fresh.termine.formMinSekunden, 3, `TERMINE_FORM_MIN_SECONDS=${JSON.stringify(value)}`)
|
|
}
|
|
assert.equal((await freshConfig({ TERMINE_FORM_MIN_SECONDS: '7' })).termine.formMinSekunden, 7)
|
|
for (const value of ['', 'abc', '-1', 'NaN']) {
|
|
const fresh = await freshConfig({ TERMINE_MIN_ANTWORT_MS: value })
|
|
assert.equal(fresh.termine.minAntwortMs, 300, `TERMINE_MIN_ANTWORT_MS=${JSON.stringify(value)}`)
|
|
}
|
|
assert.equal((await freshConfig({ TERMINE_MIN_ANTWORT_MS: '750' })).termine.minAntwortMs, 750)
|
|
})
|
|
|
|
test('termineModus: leer und unbekannt sind off, pilot und on bleiben', () => {
|
|
for (const value of [undefined, null, '', 'banane', 'PILOT', 'true']) {
|
|
config.termine.mode = value
|
|
assert.equal(termineModus(), 'off', `mode=${JSON.stringify(value)}`)
|
|
assert.equal(termineAus(), true)
|
|
}
|
|
config.termine.mode = 'pilot'
|
|
assert.equal(termineModus(), 'pilot')
|
|
assert.equal(termineAus(), false)
|
|
config.termine.mode = 'on'
|
|
assert.equal(termineModus(), 'on')
|
|
assert.equal(termineAus(), false)
|
|
})
|
|
|
|
test('termineModus: Aenderung von config.termine.mode wirkt sofort', () => {
|
|
config.termine.mode = 'off'
|
|
assert.equal(termineModus(), 'off')
|
|
config.termine.mode = 'on'
|
|
assert.equal(termineModus(), 'on')
|
|
config.termine.mode = 'off'
|
|
assert.equal(termineAus(), true)
|
|
})
|
|
|
|
test('termineFuerKunde: off sperrt alle, auch mit Stern in der Liste', () => {
|
|
config.termine.mode = 'off'
|
|
config.termine.pilotEmails = ['*', 'kenso.gri@gmail.com']
|
|
assert.equal(termineFuerKunde('kenso.gri@gmail.com'), false)
|
|
assert.equal(termineFuerKunde('jemand@example.com'), false)
|
|
})
|
|
|
|
test('termineFuerKunde: pilot erlaubt nur Adressen der Liste, Schreibweise egal', () => {
|
|
config.termine.mode = 'pilot'
|
|
config.termine.pilotEmails = ['kenso.gri@gmail.com']
|
|
assert.equal(termineFuerKunde('KENSO.gri@gmail.com '), true)
|
|
assert.equal(termineFuerKunde('kenso.gri@gmail.com'), true)
|
|
assert.equal(termineFuerKunde('jemand@example.com'), false)
|
|
assert.equal(termineFuerKunde('kenso.gri@gmail.com.evil.de'), false)
|
|
})
|
|
|
|
test('termineFuerKunde: pilot mit Stern erlaubt alle, mit leerer Liste niemanden', () => {
|
|
config.termine.mode = 'pilot'
|
|
config.termine.pilotEmails = ['*']
|
|
assert.equal(termineFuerKunde('jemand@example.com'), true)
|
|
config.termine.pilotEmails = []
|
|
assert.equal(termineFuerKunde('kenso.gri@gmail.com'), false)
|
|
})
|
|
|
|
test('termineFuerKunde: pilot ohne E-Mail-Adresse ist false', () => {
|
|
config.termine.mode = 'pilot'
|
|
config.termine.pilotEmails = ['kenso.gri@gmail.com']
|
|
for (const email of [undefined, null, '', ' ']) assert.equal(termineFuerKunde(email), false)
|
|
})
|
|
|
|
test('termineFuerKunde: on gilt fuer alle ohne E-Mail-Filter', () => {
|
|
config.termine.mode = 'on'
|
|
config.termine.pilotEmails = ['kenso.gri@gmail.com']
|
|
assert.equal(termineFuerKunde('jemand@example.com'), true)
|
|
assert.equal(termineFuerKunde(undefined), true)
|
|
})
|
|
|
|
test('termineTextformNoetig: nur im Modus on und nur außerhalb der Pilotliste; „*“ und fehlende Adresse befreien nicht', () => {
|
|
for (const mode of ['off', 'pilot', undefined, '', 'banane']) {
|
|
config.termine.mode = mode
|
|
config.termine.pilotEmails = []
|
|
assert.equal(termineTextformNoetig('jemand@example.com'), false, `mode=${JSON.stringify(mode)}`)
|
|
config.termine.pilotEmails = ['*']
|
|
assert.equal(termineTextformNoetig('jemand@example.com'), false, `mode=${JSON.stringify(mode)} mit Stern`)
|
|
}
|
|
config.termine.mode = 'on'
|
|
config.termine.pilotEmails = []
|
|
assert.equal(termineTextformNoetig('jemand@example.com'), true)
|
|
config.termine.pilotEmails = ['kenso.gri@gmail.com']
|
|
assert.equal(termineTextformNoetig('jemand@example.com'), true)
|
|
assert.equal(termineTextformNoetig('KENSO.gri@gmail.com '), false, 'Pilotadresse, Schreibweise egal')
|
|
assert.equal(termineTextformNoetig('kenso.gri@gmail.com.evil.de'), true)
|
|
config.termine.pilotEmails = ['*']
|
|
assert.equal(termineTextformNoetig('jemand@example.com'), true, 'der Stern zählt in on nicht als Pilotadresse')
|
|
assert.equal(termineTextformNoetig('*'), true)
|
|
config.termine.pilotEmails = ['*', 'kenso.gri@gmail.com']
|
|
assert.equal(termineTextformNoetig('kenso.gri@gmail.com'), false)
|
|
for (const email of [undefined, null, '', ' ']) assert.equal(termineTextformNoetig(email), true, `ohne Adresse: ${JSON.stringify(email)}`)
|
|
// wirkt sofort wie die übrigen Schalter
|
|
config.termine.mode = 'pilot'
|
|
assert.equal(termineTextformNoetig('jemand@example.com'), false)
|
|
})
|