<?php

declare(strict_types=1);

namespace OCA\Mitgliederverwaltung\Controller;

use OCA\Mitgliederverwaltung\Service\FileLinkService;
use OCP\AppFramework\ApiController;
use OCP\AppFramework\Db\DoesNotExistException;
use OCP\AppFramework\Http;
use OCP\AppFramework\Http\Attribute\NoCSRFRequired;
use OCP\AppFramework\Http\JSONResponse;
use OCP\IRequest;
use Psr\Log\LoggerInterface;

/**
 * REST API controller for Nextcloud Files integration.
 *
 * Provides endpoints for browsing member/Lager folders and managing
 * file integration settings (base path, pattern, auto-create).
 *
 * Part of Issue #52.
 */
class FileController extends ApiController {

    use ApiControllerTrait;

    private FileLinkService $fileLinkService;
    private LoggerInterface $logger;

    public function __construct(
        string $appName,
        IRequest $request,
        FileLinkService $fileLinkService,
        LoggerInterface $logger
    ) {
        parent::__construct($appName, $request);
        $this->fileLinkService = $fileLinkService;
        $this->logger = $logger;
    }

    /**
     * Get current file integration settings.
     *
     * GET /api/v1/files/settings
     */
    #[NoCSRFRequired]
    public function getSettings(): JSONResponse {
        try {
            $settings = $this->fileLinkService->getSettings();
            return new JSONResponse($settings);
        } catch (\Exception $e) {
            $this->logger->error('Failed to get file settings', [
                'exception' => $e,
                'app' => 'mitgliederverwaltung',
            ]);
            return new JSONResponse(
                ['error' => 'Internal server error'],
                Http::STATUS_INTERNAL_SERVER_ERROR
            );
        }
    }

    /**
     * Update file integration settings.
     *
     * PUT /api/v1/files/settings
     */
    public function updateSettings(): JSONResponse {
        try {
            $data = $this->getRequestData();
            $this->fileLinkService->updateSettings($data);

            return new JSONResponse($this->fileLinkService->getSettings());
        } catch (\Exception $e) {
            $this->logger->error('Failed to update file settings', [
                'exception' => $e,
                'app' => 'mitgliederverwaltung',
            ]);
            return new JSONResponse(
                ['error' => 'Internal server error'],
                Http::STATUS_INTERNAL_SERVER_ERROR
            );
        }
    }

    /**
     * List files in a member's folder.
     *
     * GET /api/v1/members/{memberId}/files
     */
    #[NoCSRFRequired]
    public function memberFiles(int $memberId): JSONResponse {
        try {
            $result = $this->fileLinkService->getMemberFilesById($memberId);
            return new JSONResponse($result);
        } catch (DoesNotExistException $e) {
            return new JSONResponse(
                ['error' => 'Mitglied nicht gefunden'],
                Http::STATUS_NOT_FOUND
            );
        } catch (\Exception $e) {
            $this->logger->error('Failed to list member files', [
                'memberId' => $memberId,
                'exception' => $e,
                'app' => 'mitgliederverwaltung',
            ]);
            return new JSONResponse(
                ['error' => 'Internal server error'],
                Http::STATUS_INTERNAL_SERVER_ERROR
            );
        }
    }

    /**
     * Ensure a member's folder exists (creates if auto-create is enabled).
     *
     * POST /api/v1/members/{memberId}/files/ensure-folder
     */
    public function ensureFolder(int $memberId): JSONResponse {
        try {
            $result = $this->fileLinkService->ensureMemberFolderById($memberId, true);

            if ($result['exists']) {
                return new JSONResponse([
                    'status' => 'ok',
                    'path' => $result['path'],
                ]);
            }

            return new JSONResponse(
                ['error' => 'Ordner konnte nicht erstellt werden. Auto-Erstellung ist moeglicherweise deaktiviert.'],
                Http::STATUS_BAD_REQUEST
            );
        } catch (DoesNotExistException $e) {
            return new JSONResponse(
                ['error' => 'Mitglied nicht gefunden'],
                Http::STATUS_NOT_FOUND
            );
        } catch (\Exception $e) {
            $this->logger->error('Failed to ensure member folder', [
                'memberId' => $memberId,
                'exception' => $e,
                'app' => 'mitgliederverwaltung',
            ]);
            return new JSONResponse(
                ['error' => 'Internal server error'],
                Http::STATUS_INTERNAL_SERVER_ERROR
            );
        }
    }

    /**
     * Browse files in a Lager's folder.
     *
     * GET /api/v1/lager/{lagerId}/files/browse
     */
    #[NoCSRFRequired]
    public function lagerFiles(int $lagerId): JSONResponse {
        try {
            $result = $this->fileLinkService->getLagerFilesById($lagerId);
            return new JSONResponse($result);
        } catch (DoesNotExistException $e) {
            return new JSONResponse(
                ['error' => 'Lager nicht gefunden'],
                Http::STATUS_NOT_FOUND
            );
        } catch (\Exception $e) {
            $this->logger->error('Failed to browse Lager files', [
                'lagerId' => $lagerId,
                'exception' => $e,
                'app' => 'mitgliederverwaltung',
            ]);
            return new JSONResponse(
                ['error' => 'Internal server error'],
                Http::STATUS_INTERNAL_SERVER_ERROR
            );
        }
    }

    /**
     * Ensure a Lager's folder exists (creates it as an explicit user action).
     *
     * POST /api/v1/lager/{lagerId}/files/ensure-folder
     */
    public function ensureLagerFolder(int $lagerId): JSONResponse {
        try {
            $result = $this->fileLinkService->ensureLagerFolderById($lagerId, true);

            if ($result['exists']) {
                return new JSONResponse([
                    'status' => 'ok',
                    'path' => $result['path'],
                ]);
            }

            return new JSONResponse(
                ['error' => 'Ordner konnte nicht erstellt werden.'],
                Http::STATUS_BAD_REQUEST
            );
        } catch (DoesNotExistException $e) {
            return new JSONResponse(
                ['error' => 'Lager nicht gefunden'],
                Http::STATUS_NOT_FOUND
            );
        } catch (\Exception $e) {
            $this->logger->error('Failed to ensure Lager folder', [
                'lagerId' => $lagerId,
                'exception' => $e,
                'app' => 'mitgliederverwaltung',
            ]);
            return new JSONResponse(
                ['error' => 'Internal server error'],
                Http::STATUS_INTERNAL_SERVER_ERROR
            );
        }
    }

    // getRequestData() provided by ApiControllerTrait
}
