diff --git a/VERSION b/VERSION index f8a696c..661e7ae 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -1.7.2 +1.7.3 diff --git a/app/Http/Middleware/PublicSiteGate.php b/app/Http/Middleware/PublicSiteGate.php index b869224..81e394a 100644 --- a/app/Http/Middleware/PublicSiteGate.php +++ b/app/Http/Middleware/PublicSiteGate.php @@ -7,7 +7,6 @@ use App\Support\Settings; use Closure; use Illuminate\Http\Request; use Illuminate\Support\Facades\Auth; -use Symfony\Component\HttpFoundation\IpUtils; use Symfony\Component\HttpFoundation\Response; /** @@ -96,11 +95,22 @@ class PublicSiteGate return in_array($request->route()?->getName(), ['bootstrap.archive', 'files.public'], true); } + /** + * Dieselbe Frage wie das Konsolentor, aus derselben Quelle. + * + * Hier stand eine EIGENE Liste (`admin_access.trusted_ranges`), während + * `RestrictConsoleNetwork` das VPN-Subnetz PLUS die Freigabeliste liest, + * die der Betreiber in der Konsole pflegt. Zwei Vorstellungen davon, wer + * „wir" sind — und wer seine Büroadresse eingetragen hatte, kam auf + * `admin.` und auf `www.`/`app.`/`status.` nicht. Er stand also vor der + * Baustellenseite seines eigenen Portals und hielt das VPN für kaputt. + * + * Eine Liste, ein Tor. Wer die Konsole sehen darf, darf die versteckte + * Seite auch sehen — das ist dieselbe Person. + */ private function fromManagementNetwork(Request $request): bool { - $ranges = (array) config('admin_access.trusted_ranges', []); - - return $ranges !== [] && IpUtils::checkIp((string) $request->ip(), $ranges); + return RestrictConsoleNetwork::allows((string) $request->ip()); } /** diff --git a/tests/Feature/PublicSiteGateTest.php b/tests/Feature/PublicSiteGateTest.php index 5c133ac..b460b72 100644 --- a/tests/Feature/PublicSiteGateTest.php +++ b/tests/Feature/PublicSiteGateTest.php @@ -163,3 +163,16 @@ it('does not leave the portal drivable through Livewire while hidden', function expect($status)->not->toBe(503); }); + +it('lets the address the operator allowlisted through the hidden site, not only the VPN', function () { + // Zwei Tore hatten zwei Vorstellungen davon, wer „wir" sind: Die Konsole + // las VPN-Subnetz PLUS die Freigabeliste, dieses Tor nur eine eigene + // Konfigurationsliste. Wer seine Büroadresse eingetragen hatte, kam auf + // `admin.` und stand auf `www.`/`app.` vor der Baustellenseite seines + // eigenen Portals — und hielt das VPN für kaputt. + Settings::set('site.public', false); + Settings::set('console.allowed_ips', ['203.0.113.77']); + + $this->withServerVariables(['REMOTE_ADDR' => '203.0.113.77'])->get('/')->assertOk(); + $this->withServerVariables(['REMOTE_ADDR' => '198.51.100.9'])->get('/')->assertStatus(503); +});