Offene PayPal-Zahlungen bleiben nach dem Abschalten erreichbar
Wird PayPal in den Mandant-Einstellungen abgeschaltet, waehrend noch Zahlungen unzugeordnet in der Warteschlange liegen, kaeme ohne diese Ausnahme niemand mehr an sie heran - weder ueber das Menue noch ueber die URL. paypal_inbox_accessible() haelt Menuepunkt und Seite deshalb offen, solange paypal_count_unmatched() etwas findet; die Seite weist per Hinweis darauf hin, dass sie nach dem Abarbeiten verschwindet. Eine Sperre durch den Betreiber sticht die Ausnahme. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
@@ -328,3 +328,54 @@ function paypal_ignore_payment(PDO $pdo, int $tenantId, int $paymentId, ?int $ac
|
||||
|
||||
return ['ok' => false, 'error' => 'Diese Zahlung ist nicht (mehr) offen.'];
|
||||
}
|
||||
|
||||
/**
|
||||
* Anzahl der offenen Zahlungen in der Warteschlange. Bewusst als eigene
|
||||
* Zaehl-Abfrage neben paypal_fetch_unmatched(): die Navigation braucht nur
|
||||
* die Information "gibt es noch etwas zu tun", nicht die Datensaetze.
|
||||
*/
|
||||
function paypal_count_unmatched(PDO $pdo, int $tenantId): int
|
||||
{
|
||||
static $cache = [];
|
||||
|
||||
if (array_key_exists($tenantId, $cache)) {
|
||||
return $cache[$tenantId];
|
||||
}
|
||||
|
||||
try {
|
||||
$stmt = $pdo->prepare(
|
||||
"SELECT COUNT(*) FROM paypal_payments WHERE tenant_id = ? AND status = 'unmatched'"
|
||||
);
|
||||
$stmt->execute([$tenantId]);
|
||||
$cache[$tenantId] = (int)$stmt->fetchColumn();
|
||||
} catch (Throwable $e) {
|
||||
// Fehlt die Tabelle, gibt es auch keine Warteschlange - die
|
||||
// Navigation darf daran nicht scheitern.
|
||||
$cache[$tenantId] = 0;
|
||||
}
|
||||
|
||||
return $cache[$tenantId];
|
||||
}
|
||||
|
||||
/**
|
||||
* Darf die Zuordnungsseite geoeffnet werden? Die Funktion kennt drei Faelle:
|
||||
* der Betreiber hat gesperrt (nein), der Mandant bietet PayPal an (ja) - und
|
||||
* dazwischen der Fall, dass der Mandant PayPal gerade abgeschaltet hat,
|
||||
* aber noch Zahlungen unzugeordnet in der Warteschlange liegen. Die waeren
|
||||
* sonst weder ueber das Menue noch ueber die URL erreichbar; die Seite bleibt
|
||||
* deshalb offen, bis die Warteschlange leer ist.
|
||||
*/
|
||||
function paypal_inbox_accessible(PDO $pdo, int $tenantId): bool
|
||||
{
|
||||
require_once __DIR__ . '/features.php';
|
||||
|
||||
if (!app_feature_enabled($pdo, $tenantId, 'paypal_inbox')) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (app_feature_available($pdo, $tenantId, 'paypal_inbox')) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return paypal_count_unmatched($pdo, $tenantId) > 0;
|
||||
}
|
||||
|
||||
@@ -105,6 +105,13 @@ Design-Entscheidungen:
|
||||
Aufruf erscheint statt des Betreiber-Hinweises
|
||||
`app_feature_tenant_notice_html()` mit dem Weg zurück in die
|
||||
Mandant-Einstellungen.
|
||||
- **Ausnahme: offene Warteschlange.** Schaltet ein Mandant PayPal ab,
|
||||
während noch nicht zugeordnete Zahlungen liegen, wären diese weder über
|
||||
Menü noch über URL erreichbar. `paypal_inbox_accessible()`
|
||||
(`app/paypal-inbox.php`) hält Menüpunkt und Seite deshalb offen, solange
|
||||
`paypal_count_unmatched()` etwas findet – mit einem Hinweis auf der
|
||||
Seite. Ist die Warteschlange abgearbeitet, schließt sie sich von selbst.
|
||||
Eine Sperre durch den Betreiber sticht auch diese Ausnahme.
|
||||
- Jede Änderung landet als `backoffice.features_updated` im Audit-Log des
|
||||
betroffenen Mandanten – wie jeder andere Back-Office-Zugriff auch.
|
||||
|
||||
|
||||
+10
-1
@@ -45,6 +45,15 @@ $saasNavFeature = static function (string $key) use ($saasNavTenantId): bool {
|
||||
return app_feature_available(app_db_pdo(), $saasNavTenantId, $key);
|
||||
};
|
||||
|
||||
// Sonderfall PayPal: abgeschaltet heisst normalerweise unsichtbar - solange
|
||||
// aber noch Zahlungen unzugeordnet in der Warteschlange liegen, bleibt der
|
||||
// Menuepunkt stehen, sonst kaeme niemand mehr an sie heran.
|
||||
$saasNavPaypalInbox = true;
|
||||
if ($saasNavTenantId > 0) {
|
||||
require_once __DIR__ . '/app/paypal-inbox.php';
|
||||
$saasNavPaypalInbox = paypal_inbox_accessible(app_db_pdo(), $saasNavTenantId);
|
||||
}
|
||||
|
||||
// Das Back-Office war bisher nur ueber die direkte URL erreichbar. Es ist die
|
||||
// Zentralstelle des Betreibers und gehoert deshalb ins Menue - aber nur fuer
|
||||
// Platform-Admins, nicht fuer Mandanten-Rollen.
|
||||
@@ -74,7 +83,7 @@ if ($saasNavUser !== null) {
|
||||
<span class="menu-group-label">Verwaltung</span>
|
||||
<ul class="menu-group-items">
|
||||
<li><a href="einzahlung.php">Einzahlung eintragen</a></li>
|
||||
<?php if ($saasNavFeature('paypal_inbox')): ?>
|
||||
<?php if ($saasNavPaypalInbox): ?>
|
||||
<li><a href="paypal-zuordnung.php">PayPal-Zahlungen</a></li>
|
||||
<?php endif; ?>
|
||||
<li><a href="stricheintragen.php">Striche eintragen</a></li>
|
||||
|
||||
+17
-3
@@ -21,14 +21,21 @@ if ($saasUser !== null && saas_user_has_role(['owner', 'admin', 'treasurer'], $s
|
||||
// diesem Fall ausgeblendet - die Seite bleibt aber ueber die direkte URL
|
||||
// erreichbar und muss deshalb selbst pruefen.
|
||||
$sperrHinweis = null;
|
||||
$restarbeitHinweis = false;
|
||||
if ($hasAccess && !app_feature_enabled($pdo, $tenantId, 'paypal_inbox')) {
|
||||
// Der Betreiber hat die Funktion fuer diesen Mandanten nicht freigeschaltet.
|
||||
$sperrHinweis = app_feature_notice_html('paypal_inbox');
|
||||
$hasAccess = false;
|
||||
} elseif ($hasAccess && !app_feature_available($pdo, $tenantId, 'paypal_inbox')) {
|
||||
// Der Mandant selbst bietet PayPal nicht als Zahlungsweg an.
|
||||
$sperrHinweis = app_feature_tenant_notice_html('paypal_inbox');
|
||||
$hasAccess = false;
|
||||
// Der Mandant selbst bietet PayPal nicht mehr als Zahlungsweg an. Offene
|
||||
// Zahlungen muessen trotzdem noch zugeordnet werden koennen - erst mit
|
||||
// leerer Warteschlange schliesst die Seite.
|
||||
if (paypal_count_unmatched($pdo, $tenantId) > 0) {
|
||||
$restarbeitHinweis = true;
|
||||
} else {
|
||||
$sperrHinweis = app_feature_tenant_notice_html('paypal_inbox');
|
||||
$hasAccess = false;
|
||||
}
|
||||
}
|
||||
|
||||
$flash = null;
|
||||
@@ -145,6 +152,13 @@ include "nav.php";
|
||||
|
||||
<h2>PayPal-Zahlungen zuordnen</h2>
|
||||
|
||||
<?php if ($restarbeitHinweis): ?>
|
||||
<div class="hint-box warning"><p><b>PayPal ist in euren Mandant-Einstellungen deaktiviert.</b><br>
|
||||
Diese Seite bleibt geöffnet, bis die unten stehenden Zahlungen zugeordnet oder abgehakt sind.
|
||||
Danach verschwindet sie aus dem Menü – bis PayPal unter
|
||||
<a href="mandant-einstellungen.php">Mandant-Einstellungen</a> wieder eingeschaltet wird.</p></div>
|
||||
<?php endif; ?>
|
||||
|
||||
<?php if ($flash !== null): ?>
|
||||
<div class="hint-box <?php echo $flash['type'] === 'success' ? 'success' : 'error'; ?>"><p><?php echo saas_html($flash['text']); ?></p></div>
|
||||
<?php endif; ?>
|
||||
|
||||
Reference in New Issue
Block a user