Statt npm-Rebuild-Wartung aktualisiert sich der Bankleitzahlen-Datensatz jetzt zur Laufzeit. Ein Scheduler (taeglich 03:30 + Catch-up 90s) prueft gemaess konfigurierbarem Intervall und laedt current.json/next.json von npm/jsDelivr (Paket bankdata-germany) in das neue Bind-Mount-Volume BANKDATA_DIR (./data/bankdata -> /app/bankdata). Lookup bevorzugt den Volume-Datensatz vor den ins Image gebackenen Daten (Fallback). Es wird kein Fremdcode ausgefuehrt - nur JSON gelesen und die current+next-Delta-Logik nachgebaut. Validierung (>=1000 Eintraege, Format) + atomarer Write (tmp+rename) schuetzen den guten Stand vor Muell. Datenschutz: Der Updater sendet keine Kundendaten, laedt nur eine oeffentliche Datendatei; abschaltbar; bei Fehler/ohne Egress greift Builtin. Neue Einstellungen-Seite /settings/bank-data zeigt Datenstand, Update- Verfuegbarkeit und bietet "Jetzt aktualisieren" + Auto-Update-Schalter + Intervall. Endpoints GET /api/settings/blz, POST /api/settings/blz/update-now. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
56 lines
2.1 KiB
TypeScript
56 lines
2.1 KiB
TypeScript
import { Response } from 'express';
|
||
import { isValidIBAN } from 'ibantools';
|
||
import * as blzData from '../services/blzData.service.js';
|
||
import { ApiResponse, AuthRequest } from '../types/index.js';
|
||
|
||
/**
|
||
* IBAN-Lookup: prüft die Prüfziffer (mod-97, offline über ibantools) und liefert
|
||
* – für deutsche IBANs – BIC und Banknamen aus der Bundesbank-Bankleitzahlen-
|
||
* datei (offline; siehe blzData.service – Volume-Datensatz bevorzugt, sonst die
|
||
* ins Image gebackenen Daten). Die IBAN verlässt NICHT den Server; es findet
|
||
* KEIN externer Request statt. Zurückgegeben werden nur öffentliche
|
||
* Bankverzeichnis-Daten (BIC/Name), keine kundenbezogenen Informationen.
|
||
*
|
||
* Antwortformen (immer HTTP 200, sofern eine IBAN übergeben wurde):
|
||
* { valid: false } → Prüfziffer falsch (Tippfehler)
|
||
* { valid: true, bic, bankName, blz } → gültig + DE-Bank gefunden
|
||
* { valid: true, bic: null, bankName: null } → gültig, aber keine DE-Bankdaten
|
||
* (Nicht-DE-IBAN oder unbekannte BLZ)
|
||
*/
|
||
export async function lookupIban(req: AuthRequest, res: Response): Promise<void> {
|
||
try {
|
||
const raw = typeof req.body?.iban === 'string' ? req.body.iban : '';
|
||
const iban = raw.replace(/\s+/g, '').toUpperCase();
|
||
|
||
if (!iban) {
|
||
res.status(400).json({ success: false, error: 'Feld IBAN ist erforderlich.' } as ApiResponse);
|
||
return;
|
||
}
|
||
|
||
if (!isValidIBAN(iban)) {
|
||
res.json({ success: true, data: { valid: false, iban } } as ApiResponse);
|
||
return;
|
||
}
|
||
|
||
const country = iban.slice(0, 2);
|
||
const bank = country === 'DE' ? blzData.lookupByIban(iban) : null;
|
||
|
||
res.json({
|
||
success: true,
|
||
data: {
|
||
valid: true,
|
||
iban,
|
||
country,
|
||
bic: bank?.bic ?? null,
|
||
bankName: bank?.bankName ?? null,
|
||
blz: bank?.blz ?? null,
|
||
},
|
||
} as ApiResponse);
|
||
} catch (error) {
|
||
res.status(500).json({
|
||
success: false,
|
||
error: error instanceof Error ? error.message : 'Fehler beim IBAN-Nachschlagen',
|
||
} as ApiResponse);
|
||
}
|
||
}
|