From 28a0cd8153eb54e98593dab910a47da880f0c176 Mon Sep 17 00:00:00 2001 From: Chen Asraf Date: Wed, 25 Mar 2026 15:17:51 +0200 Subject: [PATCH] fix(admin): separate forum admin and server admin endpoints --- lib/Controller/AdminController.php | 107 ---- lib/Controller/ServerAdminController.php | 133 +++++ openapi-administration.json | 520 +++++++++--------- openapi-full.json | 520 +++++++++--------- src/AdminSettings.vue | 4 +- tests/unit/Controller/AdminControllerTest.php | 5 - .../Controller/ServerAdminControllerTest.php | 74 +++ 7 files changed, 729 insertions(+), 634 deletions(-) create mode 100644 lib/Controller/ServerAdminController.php create mode 100644 tests/unit/Controller/ServerAdminControllerTest.php diff --git a/lib/Controller/AdminController.php b/lib/Controller/AdminController.php index c21c110..4596e58 100644 --- a/lib/Controller/AdminController.php +++ b/lib/Controller/AdminController.php @@ -13,9 +13,7 @@ use OCA\Forum\Db\ForumUserMapper; use OCA\Forum\Db\PostMapper; use OCA\Forum\Db\RoleMapper; use OCA\Forum\Db\ThreadMapper; -use OCA\Forum\Migration\SeedHelper; use OCA\Forum\Service\AdminSettingsService; -use OCA\Forum\Service\StatsService; use OCA\Forum\Service\UserRoleService; use OCA\Forum\Service\UserService; use OCP\AppFramework\Http; @@ -26,7 +24,6 @@ use OCP\AppFramework\OCSController; use OCP\IRequest; use OCP\IUserManager; use OCP\IUserSession; -use OCP\Migration\IOutput; use Psr\Log\LoggerInterface; class AdminController extends OCSController { @@ -44,7 +41,6 @@ class AdminController extends OCSController { private IUserManager $userManager, private IUserSession $userSession, private AdminSettingsService $settingsService, - private StatsService $statsService, private LoggerInterface $logger, ) { parent::__construct($appName, $request); @@ -242,109 +238,6 @@ class AdminController extends OCSController { } } - /** - * Run the repair seeds command to restore default forum data - * - * @return DataResponse - * - * 200: Seeds repaired successfully - */ - #[ApiRoute(verb: 'POST', url: '/api/admin/repair-seeds')] - public function repairSeeds(): DataResponse { - try { - $messages = []; - $migrationOutput = new class($messages) implements IOutput { - /** @var array */ - private array $messages; - - public function __construct(array &$messages) { - $this->messages = &$messages; - } - - public function info($message): void { - $this->messages[] = $message; - } - - public function warning($message): void { - $this->messages[] = '[Warning] ' . $message; - } - - public function debug($message): void { - $this->messages[] = '[Debug] ' . $message; - } - - public function startProgress($max = 0): void { - } - - public function advance($step = 1, $description = ''): void { - } - - public function finishProgress(): void { - } - }; - - SeedHelper::seedAll($migrationOutput, true); - - $this->logger->info('Forum repair seeds completed successfully'); - return new DataResponse([ - 'success' => true, - 'message' => implode("\n", $messages), - ]); - } catch (\Exception $e) { - $this->logger->error('Error running repair seeds: ' . $e->getMessage()); - return new DataResponse([ - 'success' => false, - 'message' => 'Failed to repair seeds: ' . $e->getMessage(), - ], Http::STATUS_INTERNAL_SERVER_ERROR); - } - } - - /** - * Rebuild all forum statistics (users, categories, threads) - * - * @return DataResponse - * - * 200: Stats rebuilt successfully - */ - #[ApiRoute(verb: 'POST', url: '/api/admin/rebuild-stats')] - public function rebuildStats(): DataResponse { - try { - $userResult = $this->statsService->rebuildAllUserStats(); - $categoryResult = $this->statsService->rebuildAllCategoryStats(); - $threadResult = $this->statsService->rebuildAllThreadStats(); - - $messages = []; - $messages[] = sprintf( - 'Users processed: %d, created: %d, updated: %d', - $userResult['users'], - $userResult['created'], - $userResult['updated'] - ); - $messages[] = sprintf( - 'Categories processed: %d, updated: %d', - $categoryResult['categories'], - $categoryResult['updated'] - ); - $messages[] = sprintf( - 'Threads processed: %d, updated: %d', - $threadResult['threads'], - $threadResult['updated'] - ); - - $this->logger->info('Forum stats rebuild completed successfully'); - return new DataResponse([ - 'success' => true, - 'message' => implode("\n", $messages), - ]); - } catch (\Exception $e) { - $this->logger->error('Error rebuilding stats: ' . $e->getMessage()); - return new DataResponse([ - 'success' => false, - 'message' => 'Failed to rebuild stats: ' . $e->getMessage(), - ], Http::STATUS_INTERNAL_SERVER_ERROR); - } - } - /** * Get all available roles * diff --git a/lib/Controller/ServerAdminController.php b/lib/Controller/ServerAdminController.php new file mode 100644 index 0000000..ef73362 --- /dev/null +++ b/lib/Controller/ServerAdminController.php @@ -0,0 +1,133 @@ + +// SPDX-License-Identifier: AGPL-3.0-or-later + +namespace OCA\Forum\Controller; + +use OCA\Forum\Migration\SeedHelper; +use OCA\Forum\Service\StatsService; +use OCP\AppFramework\Http; +use OCP\AppFramework\Http\Attribute\ApiRoute; +use OCP\AppFramework\Http\DataResponse; +use OCP\AppFramework\OCSController; +use OCP\IRequest; +use OCP\Migration\IOutput; +use Psr\Log\LoggerInterface; + +class ServerAdminController extends OCSController { + + public function __construct( + string $appName, + IRequest $request, + private StatsService $statsService, + private LoggerInterface $logger, + ) { + parent::__construct($appName, $request); + } + + /** + * Run the repair seeds command to restore default forum data + * + * @return DataResponse + * + * 200: Seeds repaired successfully + */ + #[ApiRoute(verb: 'POST', url: '/api/server-admin/repair-seeds')] + public function repairSeeds(): DataResponse { + try { + $messages = []; + $migrationOutput = new class($messages) implements IOutput { + /** @var array */ + private array $messages; + + public function __construct(array &$messages) { + $this->messages = &$messages; + } + + public function info($message): void { + $this->messages[] = $message; + } + + public function warning($message): void { + $this->messages[] = '[Warning] ' . $message; + } + + public function debug($message): void { + $this->messages[] = '[Debug] ' . $message; + } + + public function startProgress($max = 0): void { + } + + public function advance($step = 1, $description = ''): void { + } + + public function finishProgress(): void { + } + }; + + SeedHelper::seedAll($migrationOutput, true); + + $this->logger->info('Forum repair seeds completed successfully'); + return new DataResponse([ + 'success' => true, + 'message' => implode("\n", $messages), + ]); + } catch (\Exception $e) { + $this->logger->error('Error running repair seeds: ' . $e->getMessage()); + return new DataResponse([ + 'success' => false, + 'message' => 'Failed to repair seeds: ' . $e->getMessage(), + ], Http::STATUS_INTERNAL_SERVER_ERROR); + } + } + + /** + * Rebuild all forum statistics (users, categories, threads) + * + * @return DataResponse + * + * 200: Stats rebuilt successfully + */ + #[ApiRoute(verb: 'POST', url: '/api/server-admin/rebuild-stats')] + public function rebuildStats(): DataResponse { + try { + $userResult = $this->statsService->rebuildAllUserStats(); + $categoryResult = $this->statsService->rebuildAllCategoryStats(); + $threadResult = $this->statsService->rebuildAllThreadStats(); + + $messages = []; + $messages[] = sprintf( + 'Users processed: %d, created: %d, updated: %d', + $userResult['users'], + $userResult['created'], + $userResult['updated'] + ); + $messages[] = sprintf( + 'Categories processed: %d, updated: %d', + $categoryResult['categories'], + $categoryResult['updated'] + ); + $messages[] = sprintf( + 'Threads processed: %d, updated: %d', + $threadResult['threads'], + $threadResult['updated'] + ); + + $this->logger->info('Forum stats rebuild completed successfully'); + return new DataResponse([ + 'success' => true, + 'message' => implode("\n", $messages), + ]); + } catch (\Exception $e) { + $this->logger->error('Error rebuilding stats: ' . $e->getMessage()); + return new DataResponse([ + 'success' => false, + 'message' => 'Failed to rebuild stats: ' . $e->getMessage(), + ], Http::STATUS_INTERNAL_SERVER_ERROR); + } + } +} diff --git a/openapi-administration.json b/openapi-administration.json index 4a2ed01..bdf1294 100644 --- a/openapi-administration.json +++ b/openapi-administration.json @@ -47,266 +47,6 @@ } }, "paths": { - "/ocs/v2.php/apps/forum/api/admin/repair-seeds": { - "post": { - "operationId": "admin-repair-seeds", - "summary": "Run the repair seeds command to restore default forum data", - "description": "This endpoint requires admin access", - "tags": [ - "admin" - ], - "security": [ - { - "bearer_auth": [] - }, - { - "basic_auth": [] - } - ], - "parameters": [ - { - "name": "OCS-APIRequest", - "in": "header", - "description": "Required to be true for the API request to pass", - "required": true, - "schema": { - "type": "boolean", - "default": true - } - } - ], - "responses": { - "200": { - "description": "Seeds repaired successfully", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": { - "type": "object", - "required": [ - "success", - "message" - ], - "properties": { - "success": { - "type": "boolean" - }, - "message": { - "type": "string" - } - } - } - } - } - } - } - } - } - }, - "401": { - "description": "Current user is not logged in", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": {} - } - } - } - } - } - } - }, - "403": { - "description": "Logged in account must be an admin", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": {} - } - } - } - } - } - } - } - } - } - }, - "/ocs/v2.php/apps/forum/api/admin/rebuild-stats": { - "post": { - "operationId": "admin-rebuild-stats", - "summary": "Rebuild all forum statistics (users, categories, threads)", - "description": "This endpoint requires admin access", - "tags": [ - "admin" - ], - "security": [ - { - "bearer_auth": [] - }, - { - "basic_auth": [] - } - ], - "parameters": [ - { - "name": "OCS-APIRequest", - "in": "header", - "description": "Required to be true for the API request to pass", - "required": true, - "schema": { - "type": "boolean", - "default": true - } - } - ], - "responses": { - "200": { - "description": "Stats rebuilt successfully", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": { - "type": "object", - "required": [ - "success", - "message" - ], - "properties": { - "success": { - "type": "boolean" - }, - "message": { - "type": "string" - } - } - } - } - } - } - } - } - } - }, - "401": { - "description": "Current user is not logged in", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": {} - } - } - } - } - } - } - }, - "403": { - "description": "Logged in account must be an admin", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": {} - } - } - } - } - } - } - } - } - } - }, "/ocs/v2.php/apps/forum/api/init/admin-users": { "get": { "operationId": "init-get-admin-users", @@ -722,6 +462,266 @@ } } } + }, + "/ocs/v2.php/apps/forum/api/server-admin/repair-seeds": { + "post": { + "operationId": "server_admin-repair-seeds", + "summary": "Run the repair seeds command to restore default forum data", + "description": "This endpoint requires admin access", + "tags": [ + "server_admin" + ], + "security": [ + { + "bearer_auth": [] + }, + { + "basic_auth": [] + } + ], + "parameters": [ + { + "name": "OCS-APIRequest", + "in": "header", + "description": "Required to be true for the API request to pass", + "required": true, + "schema": { + "type": "boolean", + "default": true + } + } + ], + "responses": { + "200": { + "description": "Seeds repaired successfully", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": { + "type": "object", + "required": [ + "success", + "message" + ], + "properties": { + "success": { + "type": "boolean" + }, + "message": { + "type": "string" + } + } + } + } + } + } + } + } + } + }, + "401": { + "description": "Current user is not logged in", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": {} + } + } + } + } + } + } + }, + "403": { + "description": "Logged in account must be an admin", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": {} + } + } + } + } + } + } + } + } + } + }, + "/ocs/v2.php/apps/forum/api/server-admin/rebuild-stats": { + "post": { + "operationId": "server_admin-rebuild-stats", + "summary": "Rebuild all forum statistics (users, categories, threads)", + "description": "This endpoint requires admin access", + "tags": [ + "server_admin" + ], + "security": [ + { + "bearer_auth": [] + }, + { + "basic_auth": [] + } + ], + "parameters": [ + { + "name": "OCS-APIRequest", + "in": "header", + "description": "Required to be true for the API request to pass", + "required": true, + "schema": { + "type": "boolean", + "default": true + } + } + ], + "responses": { + "200": { + "description": "Stats rebuilt successfully", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": { + "type": "object", + "required": [ + "success", + "message" + ], + "properties": { + "success": { + "type": "boolean" + }, + "message": { + "type": "string" + } + } + } + } + } + } + } + } + } + }, + "401": { + "description": "Current user is not logged in", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": {} + } + } + } + } + } + } + }, + "403": { + "description": "Logged in account must be an admin", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": {} + } + } + } + } + } + } + } + } + } } }, "tags": [ diff --git a/openapi-full.json b/openapi-full.json index 786fca7..ed9bc29 100644 --- a/openapi-full.json +++ b/openapi-full.json @@ -11967,266 +11967,6 @@ } } }, - "/ocs/v2.php/apps/forum/api/admin/repair-seeds": { - "post": { - "operationId": "admin-repair-seeds", - "summary": "Run the repair seeds command to restore default forum data", - "description": "This endpoint requires admin access", - "tags": [ - "admin" - ], - "security": [ - { - "bearer_auth": [] - }, - { - "basic_auth": [] - } - ], - "parameters": [ - { - "name": "OCS-APIRequest", - "in": "header", - "description": "Required to be true for the API request to pass", - "required": true, - "schema": { - "type": "boolean", - "default": true - } - } - ], - "responses": { - "200": { - "description": "Seeds repaired successfully", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": { - "type": "object", - "required": [ - "success", - "message" - ], - "properties": { - "success": { - "type": "boolean" - }, - "message": { - "type": "string" - } - } - } - } - } - } - } - } - } - }, - "401": { - "description": "Current user is not logged in", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": {} - } - } - } - } - } - } - }, - "403": { - "description": "Logged in account must be an admin", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": {} - } - } - } - } - } - } - } - } - } - }, - "/ocs/v2.php/apps/forum/api/admin/rebuild-stats": { - "post": { - "operationId": "admin-rebuild-stats", - "summary": "Rebuild all forum statistics (users, categories, threads)", - "description": "This endpoint requires admin access", - "tags": [ - "admin" - ], - "security": [ - { - "bearer_auth": [] - }, - { - "basic_auth": [] - } - ], - "parameters": [ - { - "name": "OCS-APIRequest", - "in": "header", - "description": "Required to be true for the API request to pass", - "required": true, - "schema": { - "type": "boolean", - "default": true - } - } - ], - "responses": { - "200": { - "description": "Stats rebuilt successfully", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": { - "type": "object", - "required": [ - "success", - "message" - ], - "properties": { - "success": { - "type": "boolean" - }, - "message": { - "type": "string" - } - } - } - } - } - } - } - } - } - }, - "401": { - "description": "Current user is not logged in", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": {} - } - } - } - } - } - } - }, - "403": { - "description": "Logged in account must be an admin", - "content": { - "application/json": { - "schema": { - "type": "object", - "required": [ - "ocs" - ], - "properties": { - "ocs": { - "type": "object", - "required": [ - "meta", - "data" - ], - "properties": { - "meta": { - "$ref": "#/components/schemas/OCSMeta" - }, - "data": {} - } - } - } - } - } - } - } - } - } - }, "/ocs/v2.php/apps/forum/api/init/admin-users": { "get": { "operationId": "init-get-admin-users", @@ -12642,6 +12382,266 @@ } } } + }, + "/ocs/v2.php/apps/forum/api/server-admin/repair-seeds": { + "post": { + "operationId": "server_admin-repair-seeds", + "summary": "Run the repair seeds command to restore default forum data", + "description": "This endpoint requires admin access", + "tags": [ + "server_admin" + ], + "security": [ + { + "bearer_auth": [] + }, + { + "basic_auth": [] + } + ], + "parameters": [ + { + "name": "OCS-APIRequest", + "in": "header", + "description": "Required to be true for the API request to pass", + "required": true, + "schema": { + "type": "boolean", + "default": true + } + } + ], + "responses": { + "200": { + "description": "Seeds repaired successfully", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": { + "type": "object", + "required": [ + "success", + "message" + ], + "properties": { + "success": { + "type": "boolean" + }, + "message": { + "type": "string" + } + } + } + } + } + } + } + } + } + }, + "401": { + "description": "Current user is not logged in", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": {} + } + } + } + } + } + } + }, + "403": { + "description": "Logged in account must be an admin", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": {} + } + } + } + } + } + } + } + } + } + }, + "/ocs/v2.php/apps/forum/api/server-admin/rebuild-stats": { + "post": { + "operationId": "server_admin-rebuild-stats", + "summary": "Rebuild all forum statistics (users, categories, threads)", + "description": "This endpoint requires admin access", + "tags": [ + "server_admin" + ], + "security": [ + { + "bearer_auth": [] + }, + { + "basic_auth": [] + } + ], + "parameters": [ + { + "name": "OCS-APIRequest", + "in": "header", + "description": "Required to be true for the API request to pass", + "required": true, + "schema": { + "type": "boolean", + "default": true + } + } + ], + "responses": { + "200": { + "description": "Stats rebuilt successfully", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": { + "type": "object", + "required": [ + "success", + "message" + ], + "properties": { + "success": { + "type": "boolean" + }, + "message": { + "type": "string" + } + } + } + } + } + } + } + } + } + }, + "401": { + "description": "Current user is not logged in", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": {} + } + } + } + } + } + } + }, + "403": { + "description": "Logged in account must be an admin", + "content": { + "application/json": { + "schema": { + "type": "object", + "required": [ + "ocs" + ], + "properties": { + "ocs": { + "type": "object", + "required": [ + "meta", + "data" + ], + "properties": { + "meta": { + "$ref": "#/components/schemas/OCSMeta" + }, + "data": {} + } + } + } + } + } + } + } + } + } } }, "tags": [ diff --git a/src/AdminSettings.vue b/src/AdminSettings.vue index 92bbe57..40ab404 100644 --- a/src/AdminSettings.vue +++ b/src/AdminSettings.vue @@ -221,7 +221,7 @@ export default { return runTask( this.repairSeeds, async (task) => { - const resp = await ocs.post('/admin/repair-seeds') + const resp = await ocs.post('/server-admin/repair-seeds') task.success = resp.data.success task.result = resp.data.message if (resp.data.success) { @@ -235,7 +235,7 @@ export default { return runTask( this.rebuildStats, async (task) => { - const resp = await ocs.post('/admin/rebuild-stats') + const resp = await ocs.post('/server-admin/rebuild-stats') task.success = resp.data.success task.result = resp.data.message }, diff --git a/tests/unit/Controller/AdminControllerTest.php b/tests/unit/Controller/AdminControllerTest.php index e9c6e0b..82456aa 100644 --- a/tests/unit/Controller/AdminControllerTest.php +++ b/tests/unit/Controller/AdminControllerTest.php @@ -12,7 +12,6 @@ use OCA\Forum\Db\PostMapper; use OCA\Forum\Db\RoleMapper; use OCA\Forum\Db\ThreadMapper; use OCA\Forum\Service\AdminSettingsService; -use OCA\Forum\Service\StatsService; use OCA\Forum\Service\UserRoleService; use OCA\Forum\Service\UserService; use OCP\IRequest; @@ -46,8 +45,6 @@ class AdminControllerTest extends TestCase { private IUserSession $userSession; /** @var AdminSettingsService&MockObject */ private AdminSettingsService $settingsService; - /** @var StatsService&MockObject */ - private StatsService $statsService; /** @var LoggerInterface&MockObject */ private LoggerInterface $logger; /** @var IRequest&MockObject */ @@ -65,7 +62,6 @@ class AdminControllerTest extends TestCase { $this->userManager = $this->createMock(IUserManager::class); $this->userSession = $this->createMock(IUserSession::class); $this->settingsService = $this->createMock(AdminSettingsService::class); - $this->statsService = $this->createMock(StatsService::class); $this->logger = $this->createMock(LoggerInterface::class); $this->controller = new AdminController( @@ -81,7 +77,6 @@ class AdminControllerTest extends TestCase { $this->userManager, $this->userSession, $this->settingsService, - $this->statsService, $this->logger ); } diff --git a/tests/unit/Controller/ServerAdminControllerTest.php b/tests/unit/Controller/ServerAdminControllerTest.php new file mode 100644 index 0000000..5f24ff9 --- /dev/null +++ b/tests/unit/Controller/ServerAdminControllerTest.php @@ -0,0 +1,74 @@ +request = $this->createMock(IRequest::class); + $this->statsService = $this->createMock(StatsService::class); + $this->logger = $this->createMock(LoggerInterface::class); + + $this->controller = new ServerAdminController( + Application::APP_ID, + $this->request, + $this->statsService, + $this->logger + ); + } + + public function testRebuildStatsReturnsResults(): void { + $this->statsService->expects($this->once()) + ->method('rebuildAllUserStats') + ->willReturn(['users' => 10, 'created' => 2, 'updated' => 8]); + $this->statsService->expects($this->once()) + ->method('rebuildAllCategoryStats') + ->willReturn(['categories' => 5, 'updated' => 5]); + $this->statsService->expects($this->once()) + ->method('rebuildAllThreadStats') + ->willReturn(['threads' => 20, 'updated' => 20]); + + $response = $this->controller->rebuildStats(); + + $this->assertEquals(200, $response->getStatus()); + $data = $response->getData(); + $this->assertTrue($data['success']); + $this->assertStringContainsString('Users processed: 10', $data['message']); + $this->assertStringContainsString('Categories processed: 5', $data['message']); + $this->assertStringContainsString('Threads processed: 20', $data['message']); + } + + public function testRebuildStatsHandlesException(): void { + $this->statsService->expects($this->once()) + ->method('rebuildAllUserStats') + ->willThrowException(new \Exception('DB error')); + + $this->logger->expects($this->once()) + ->method('error') + ->with($this->stringContains('Error rebuilding stats')); + + $response = $this->controller->rebuildStats(); + + $this->assertEquals(500, $response->getStatus()); + $data = $response->getData(); + $this->assertFalse($data['success']); + } +}