<?php

namespace App\Traits;

use App\Services\MemberFileService;
use Illuminate\Support\Facades\Log;

trait HandlesS3Files
{
    /**
     * Get file service instance
     */
    protected function getFileService(): MemberFileService
    {
        return app(MemberFileService::class);
    }

    /**
     * Get file URL for display
     */
    public function getFileUrl(?string $filePath, string $expiresIn = '+1 hour'): ?string
    {
        if (!$filePath) {
            return null;
        }

        return $this->getFileService()->getFileUrl($filePath, $expiresIn);
    }

    /**
     * Check if file exists in S3
     */
    public function fileExists(?string $filePath): bool
    {
        if (!$filePath) {
            return false;
        }

        try {
            return \Illuminate\Support\Facades\Storage::disk('s3')->exists($filePath);
        } catch (\Exception $e) {
            Log::warning("Error checking file existence", [
                'path' => $filePath,
                'error' => $e->getMessage()
            ]);
            return false;
        }
    }

    /**
     * Get file info
     */
    public function getFileInfo(?string $filePath): ?array
    {
        if (!$filePath) {
            return null;
        }

        return $this->getFileService()->getFileInfo($filePath);
    }

    /**
     * Delete file from S3
     */
    public function deleteFile(string $filePath): bool
    {
        return $this->getFileService()->deleteFile($filePath);
    }

    /**
     * Get file name from path
     */
    public function getFileName(?string $filePath): ?string
    {
        if (!$filePath) {
            return null;
        }

        return basename($filePath);
    }

    /**
     * Check if path is S3 path
     */
    public function isS3Path(?string $path): bool
    {
        if (!$path) {
            return false;
        }

        return strpos($path, '/members/') !== false ||
               strpos($path, session('currentClient', 'default')) === 0;
    }

    /**
     * Convert file paths array to string for database storage
     */
    public function filePathsToString(array $paths): string
    {
        return implode('|', array_filter($paths));
    }

    /**
     * Convert file paths string from database to array
     */
    public function stringToFilePaths(?string $pathsString): array
    {
        if (!$pathsString) {
            return [];
        }

        return array_filter(explode('|', $pathsString));
    }

    /**
     * Get multiple file URLs
     */
    public function getMultipleFileUrls(array $filePaths): array
    {
        $urls = [];
        foreach ($filePaths as $path) {
            $url = $this->getFileUrl($path);
            if ($url) {
                $urls[$path] = $url;
            }
        }
        return $urls;
    }

    /**
     * Clean up files for deleted member
     */
    public function cleanupMemberFiles(int $memberId): void
    {
        try {
            $currentClient = session('currentClient', 'default');
            $memberPath = $currentClient . '/members/' . $memberId . '/';

            $disk = \Illuminate\Support\Facades\Storage::disk('s3');

            // Delete all files in member's folder
            $files = $disk->allFiles($memberPath);
            foreach ($files as $file) {
                $disk->delete($file);
            }

            // Delete empty directories
            $directories = $disk->allDirectories($memberPath);
            foreach (array_reverse($directories) as $directory) {
                $disk->deleteDirectory($directory);
            }

            Log::info("Cleaned up files for deleted member", ['member_id' => $memberId]);

        } catch (\Exception $e) {
            Log::error("Error cleaning up member files", [
                'member_id' => $memberId,
                'error' => $e->getMessage()
            ]);
        }
    }

    /**
     * Validate file upload
     */
    public function validateFileUpload($file, string $type = 'document'): array
    {
        $errors = [];

        if (!$file) {
            $errors[] = 'No file provided';
            return $errors;
        }

        if (!$file->isValid()) {
            $errors[] = 'Invalid file upload';
            return $errors;
        }

        $extension = strtolower($file->getClientOriginalExtension());
        $size = $file->getSize();

        if ($type === 'image') {
            $allowedExtensions = ['jpg', 'jpeg', 'png', 'gif'];
            $maxSize = 2048 * 1024; // 2MB

            if (!in_array($extension, $allowedExtensions)) {
                $errors[] = 'Invalid image format. Allowed: ' . implode(', ', $allowedExtensions);
            }

            if ($size > $maxSize) {
                $errors[] = 'Image too large. Maximum size: 2MB';
            }

        } elseif ($type === 'document') {
            $allowedExtensions = ['jpg', 'jpeg', 'png', 'pdf', 'doc', 'docx'];
            $maxSize = 10240 * 1024; // 10MB

            if (!in_array($extension, $allowedExtensions)) {
                $errors[] = 'Invalid document format. Allowed: ' . implode(', ', $allowedExtensions);
            }

            if ($size > $maxSize) {
                $errors[] = 'Document too large. Maximum size: 10MB';
            }
        }

        return $errors;
    }
}
