From 0a7f9c0e4e83a846c6cdf727e8495ebbc04d3164 Mon Sep 17 00:00:00 2001 From: Andy Miller Date: Fri, 14 Nov 2025 15:40:09 +0000 Subject: [PATCH 1/2] regression fix for session/logout Signed-off-by: Andy Miller --- classes/plugin/AdminBaseController.php | 27 ++++++++++++++++++++++++++ themes/grav/app/utils/keepalive.js | 3 +++ themes/grav/js/admin.min.js | 3 +++ 3 files changed, 33 insertions(+) diff --git a/classes/plugin/AdminBaseController.php b/classes/plugin/AdminBaseController.php index 100b6eb0..6ce6df43 100644 --- a/classes/plugin/AdminBaseController.php +++ b/classes/plugin/AdminBaseController.php @@ -96,6 +96,8 @@ class AdminBaseController // Make sure that user is logged into admin. if (!$this->admin->authorize()) { + $this->respondUnauthorizedIfAjax(); + return false; } @@ -236,6 +238,31 @@ class AdminBaseController $this->close($response); } + /** + * Return a JSON 401 response when an unauthenticated request was clearly triggered via AJAX. + * + * @return void + */ + protected function respondUnauthorizedIfAjax(): void + { + $uri = $this->grav['uri'] ?? null; + $extension = $uri ? $uri->extension() : null; + $accept = $_SERVER['HTTP_ACCEPT'] ?? ''; + $requestedWith = $_SERVER['HTTP_X_REQUESTED_WITH'] ?? ''; + + $acceptsJson = is_string($accept) && (stripos($accept, 'application/json') !== false || stripos($accept, 'text/json') !== false); + $isAjax = ($extension === 'json') || $acceptsJson || (is_string($requestedWith) && strtolower($requestedWith) === 'xmlhttprequest'); + + if (!$isAjax) { + return; + } + + $this->sendJsonResponse([ + 'status' => 'unauthenticated', + 'message' => Admin::translate('PLUGIN_ADMIN.SESSION_EXPIRED_DESC') + ], 401); + } + /** * @param ResponseInterface $response * @return never-return diff --git a/themes/grav/app/utils/keepalive.js b/themes/grav/app/utils/keepalive.js index dc6e823b..2e24499e 100644 --- a/themes/grav/app/utils/keepalive.js +++ b/themes/grav/app/utils/keepalive.js @@ -26,6 +26,9 @@ class KeepAlive { return fetch(`${config.base_url_relative}/task${config.param_sep}keepAlive`, { credentials: 'same-origin', + headers: { + 'Accept': 'application/json' + }, method: 'post', body: data }) diff --git a/themes/grav/js/admin.min.js b/themes/grav/js/admin.min.js index b7edd2f8..514c76c5 100644 --- a/themes/grav/js/admin.min.js +++ b/themes/grav/js/admin.min.js @@ -1064,6 +1064,9 @@ var KeepAlive = /*#__PURE__*/function () { data.append('admin-nonce', external_GravAdmin_namespaceObject.config.admin_nonce); return fetch("".concat(external_GravAdmin_namespaceObject.config.base_url_relative, "/task").concat(external_GravAdmin_namespaceObject.config.param_sep, "keepAlive"), { credentials: 'same-origin', + headers: { + 'Accept': 'application/json' + }, method: 'post', body: data }).then(function (response) { From c4659c21be871f9d0fba160028ec7e832edcbf74 Mon Sep 17 00:00:00 2001 From: Andy Miller Date: Fri, 14 Nov 2025 15:41:22 +0000 Subject: [PATCH 2/2] prepare for release Signed-off-by: Andy Miller --- CHANGELOG.md | 13 +++++++++++++ blueprints.yaml | 2 +- 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index d9e23d63..a366932a 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,16 @@ +# v1.10.50 +## 11/14/2025 + +1. [](#new) + * Support for 'safe-upgrade' installation + * Support for safe-upgrade restore functionality in Tools +1. [](#improved) + * Improved session expiration/logout handling + * Various minor CSS fixes +1. [](#bugfix) + * Fix for deeply nested sortable fields (at last!) + * Restore admin session timeout modal by returning 401 for timed-out AJAX requests + # v1.10.49.1 ## 09/03/2025 diff --git a/blueprints.yaml b/blueprints.yaml index 54089d7a..1dd8f50d 100644 --- a/blueprints.yaml +++ b/blueprints.yaml @@ -1,7 +1,7 @@ name: Admin Panel slug: admin type: plugin -version: 1.10.49.1 +version: 1.10.50 description: Adds an advanced administration panel to manage your site icon: empire author: