Zwei Features an derselben Stelle, die im Arbeitsverzeichnis nebeneinander lagen und sich dieselben Dateien teilen (Routen, BankingController, Bankzugang, Zugangsformular, Dokumentation) – getrennte Commits ließen sich daraus nur mit einem kaputten Zwischenstand schneiden. PayPal als zweite Art von Bankverbindung ---------------------------------------- „Bankverbindung anlegen“ führt zur Wahl der Art: HBCI/FinTS oder PayPal (bank_zugaenge.typ, Migration 014). Die Abfrage läuft über die Classic-NVP-API (Services\PaypalNvp, TransactionSearch und GetBalance). Kein Dreischritt, da PayPal genau ein Guthabenkonto führt – Zugangsdaten und Kontenzuordnung stehen in einem Formular. Konten, Umsätze, Protokoll, Regeln und Abgleich bleiben dieselben. Bankleitzahlen-Verzeichnis -------------------------- Verwaltung → Bankleitzahlen (/verwaltung/bankinstitute, Migration 015) nimmt die CSV-Institutsliste der Deutschen Kreditwirtschaft auf und beantwortet damit die eine Angabe, die beim Anlegen einer FinTS-Verbindung regelmäßig fehlt: den PIN/TAN-Zugangspunkt. Reine Nachschlagedaten ohne benutzer_id; ein Import ersetzt den gesamten Bestand, statt ihn zu ergänzen. „Nur prüfen“ und „Übernehmen“ sind zwei Knöpfe an derselben Datei – abgelegt wird sie nicht, ihr Inhalt steht ja in der Tabelle. Services\FintsInstituteImport nimmt der Datei ihre Eigenheiten ab: ISO-8859-1 statt UTF-8, ein Institutsname über zwei Zeilen in Anführungszeichen, dieselbe Bankleitzahl vielfach (eine Zeile je Filiale), Hunderte leerer Zeilen am Ende, Text statt Adresse, wo es keinen PIN/TAN-Zugang gibt. Spalten werden über ihre Überschrift angesprochen; fehlen BLZ und Institut, bricht der Import ab. Gesucht wird über Bankleitzahl, BIC, Name und Ort in einem Zug: „1822“ steht bei der 1822direkt im Namen und bei der Frankfurter Sparkasse im BIC, in keiner der beiden Bankleitzahlen. Aus der Trefferliste führt „Verbindung anlegen“ ins gefüllte FinTS-Formular. Die FinTS-Adresse ist damit kein Pflichtfeld mehr – bleibt sie leer, wird sie zur Bankleitzahl nachgeschlagen. Findet auch das nichts, weist Bankzugang den Zugang ab, statt ihn ohne Gegenstelle zu speichern. Tests: 31_PaypalZugangTest, 32_BankinstituteTest, e2e/specs/banking.spec.js, e2e/specs/bankinstitute.spec.js. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
135 lines
5.5 KiB
PHP
135 lines
5.5 KiB
PHP
<?php
|
||
|
||
use Finanzmanager\Services\Dateiformat;
|
||
use Finanzmanager\View;
|
||
|
||
/** @var array<string,int> $zahlen */
|
||
|
||
include __DIR__ . '/../layout/kopf.php';
|
||
?>
|
||
|
||
<div class="kachelraster fussbuendig">
|
||
<div class="kachel">
|
||
<header><h2>Kategorien</h2></header>
|
||
<p class="kennzahl"><?= (int)$zahlen['kategorien'] ?></p>
|
||
<p class="platzhalter">
|
||
<?= (int)$zahlen['einnahmen'] ?> Einnahmen, <?= (int)$zahlen['ausgaben'] ?> Ausgaben.
|
||
Hierarchisch, mit Klassen als zweiter Auswertungsdimension.
|
||
</p>
|
||
<div class="knopfleiste">
|
||
<a href="/verwaltung/kategorien" class="knopf klein primaer">Kategorien verwalten</a>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="kachel">
|
||
<header><h2>Klassen</h2></header>
|
||
<p class="kennzahl"><?= (int)$zahlen['klassen'] ?></p>
|
||
<p class="platzhalter">
|
||
Zweite Dimension neben der Kategorie – etwa Ehemann, Ehefrau, Haus 1.
|
||
</p>
|
||
<div class="knopfleiste">
|
||
<a href="/verwaltung/klassen" class="knopf klein primaer">Klassen verwalten</a>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="kachel">
|
||
<header><h2>Konten</h2></header>
|
||
<p class="kennzahl"><?= (int)$zahlen['konten'] ?></p>
|
||
<p class="platzhalter">
|
||
In <?= (int)$zahlen['kontengruppen'] ?> Kontengruppen gegliedert.
|
||
</p>
|
||
<div class="knopfleiste">
|
||
<a href="/konten" class="knopf klein primaer">Kontenübersicht</a>
|
||
<a href="/verwaltung/kontengruppen" class="knopf klein">Kontengruppen</a>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="kachel">
|
||
<header><h2>Import/Export</h2></header>
|
||
<p class="platzhalter">
|
||
Stammdaten und Buchungen aus dem Lexware FinanzManager übernehmen oder den
|
||
eigenen Bestand herausgeben – wahlweise als QIF oder als CSV.
|
||
</p>
|
||
<div class="knopfleiste">
|
||
<?php /* data-formatwahl öffnet den Auswahldialog; ohne Skript führt der Link
|
||
auf dieselbe Auswahl als Seite. */ ?>
|
||
<a href="/verwaltung/import" class="knopf klein primaer" data-formatwahl="Import">Import</a>
|
||
<a href="/verwaltung/export" class="knopf klein" data-formatwahl="Export">Export</a>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="kachel">
|
||
<header><h2>Online-Banking</h2></header>
|
||
<p class="platzhalter">
|
||
Bankverbindungen über FinTS, Umsatzabruf mit Abgleich gegen vorhandene
|
||
Buchungen und Regeln für die automatische Kategorisierung.
|
||
</p>
|
||
<div class="knopfleiste">
|
||
<a href="/banking" class="knopf klein primaer">Bankverbindungen</a>
|
||
<a href="/banking/regeln" class="knopf klein">Regeln</a>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="kachel">
|
||
<header><h2>Bankleitzahlen</h2></header>
|
||
<p class="kennzahl"><?= number_format((int)$zahlen['bankinstitute'], 0, ',', '.') ?></p>
|
||
<p class="platzhalter">
|
||
Das Verzeichnis der FinTS-Institute – dort steht die FinTS-Adresse zur
|
||
Bankleitzahl, die beim Anlegen einer Bankverbindung sonst zu suchen wäre.
|
||
Die Liste wird als CSV eingelesen.
|
||
</p>
|
||
<div class="knopfleiste">
|
||
<a href="/verwaltung/bankinstitute" class="knopf klein primaer">Nachschlagen und aktualisieren</a>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="kachel">
|
||
<header><h2>Termine</h2></header>
|
||
<p class="kennzahl"><?= (int)$zahlen['reihen'] ?></p>
|
||
<p class="platzhalter">
|
||
Aktive Reihen – offene Erinnerungen: <?= (int)$zahlen['erinnerungen'] ?>.
|
||
</p>
|
||
<div class="knopfleiste">
|
||
<a href="/termine" class="knopf klein primaer">Regelmäßige Buchungen</a>
|
||
<a href="/termine/kalender" class="knopf klein">Finanzkalender</a>
|
||
<a href="/termine/erinnerungen" class="knopf klein">Erinnerungen</a>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="kachel">
|
||
<header><h2>Verträge</h2></header>
|
||
<p class="kennzahl"><?= (int)$zahlen['vertraege'] ?></p>
|
||
<p class="platzhalter">
|
||
Laufende Verträge – Fristen in den nächsten 90 Tagen: <?= (int)$zahlen['fristen'] ?>.
|
||
</p>
|
||
<div class="knopfleiste">
|
||
<a href="/vertraege" class="knopf klein primaer">Verträge</a>
|
||
<a href="/vertraege/adressen" class="knopf klein">Adressen</a>
|
||
<a href="/vertraege/sparziele" class="knopf klein">Sparziele</a>
|
||
<a href="/vertraege/kredite" class="knopf klein">Kredite</a>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
|
||
<?php /*
|
||
Die Formatwahl von Import und Export. Die Karten stehen hier im Markup und
|
||
nicht im Skript: Die Liste der Formate gehört Dateiformat::ALLE, und ein
|
||
Inline-Skript verböte ohnehin die Content-Security-Policy. Das Skript setzt
|
||
nur die Ziele und öffnet den Dialog; ohne Skript führen die Knöpfe auf
|
||
dieselbe Auswahl als eigene Seite. */ ?>
|
||
<dialog class="formatdialog" id="formatwahl">
|
||
<h2 data-formatdialog-titel>Format wählen</h2>
|
||
<div class="formatwahl">
|
||
<?php foreach (Dateiformat::ALLE as $schluessel => $name): ?>
|
||
<a class="formatkarte" href="#" data-format="<?= View::h($schluessel) ?>">
|
||
<span class="formatname"><?= View::h($name) ?></span>
|
||
<span class="nebentext"><?= View::h(Dateiformat::BESCHREIBUNGEN[$schluessel] ?? '') ?></span>
|
||
</a>
|
||
<?php endforeach; ?>
|
||
</div>
|
||
<form method="dialog" class="knopfleiste">
|
||
<button type="submit" class="knopf klein">Abbrechen</button>
|
||
</form>
|
||
</dialog>
|
||
|
||
<?php include __DIR__ . '/../layout/fuss.php'; ?>
|