<?php

namespace App\Http\Controllers\Api;

use App\Http\Controllers\Controller;
use App\Models\Discussion;
use App\Models\KnowledgeBaseQuestion;
use App\Models\SearchLog;
use App\Services\SearchService;
use Illuminate\Http\Request;
use Illuminate\Http\JsonResponse;
use Illuminate\Support\Facades\DB;

/**
 * SearchApiController
 * 
 * Handles API endpoints for global search functionality.
 * Provides AJAX endpoints for searching across all knowledge sharing content.
 * 
 * @package App\Http\Controllers\Api
 */
class SearchApiController extends Controller
{
    /**
     * Create a new controller instance.
     */
    public function __construct(
        protected SearchService $searchService
    ) {}

    /**
     * Perform a global search across all knowledge sharing content.
     *
     * @param \Illuminate\Http\Request $request
     * @return \Illuminate\Http\JsonResponse
     */
    public function search(Request $request): JsonResponse
    {
        $request->validate([
            'q' => 'required|string|min:2|max:255',
            'type' => 'nullable|in:all,discussions,knowledge-base',
            'page' => 'nullable|integer|min:1',
        ]);

        $query = trim($request->get('q'));
        $type = $request->get('type', 'all');
        $page = $request->get('page', 1);
        $perPage = 10;

        $results = [
            'discussions' => [],
            'knowledge_base' => [],
            'total' => 0,
        ];

        // Log the search
        $this->logSearch($query, $request);

        // Search Discussions
        if ($type === 'all' || $type === 'discussions') {
            $discussions = Discussion::query()
                ->published()
                ->where(function ($q) use ($query) {
                    $q->where('title', 'LIKE', "%{$query}%")
                        ->orWhere('content', 'LIKE', "%{$query}%");
                })
                ->with(['user', 'topic'])
                ->select(['id', 'title', 'slug', 'excerpt', 'user_id', 'topic_id', 'view_count', 'created_at'])
                ->latest()
                ->paginate($perPage, ['*'], 'discussion_page', $page);

            $results['discussions'] = [
                'data' => $discussions->map(function ($discussion) use ($query) {
                    return [
                        'id' => $discussion->id,
                        'type' => 'discussion',
                        'title' => $this->highlightQuery($discussion->title, $query),
                        'excerpt' => $this->highlightQuery($discussion->excerpt ?? $this->truncateContent($discussion->content, 150), $query),
                        'slug' => $discussion->slug,
                        'url' => route('public.discussions.show', $discussion->slug),
                        'author' => [
                            'name' => $discussion->user->name,
                            'avatar' => $discussion->user->avatar ?? null,
                        ],
                        'topic' => $discussion->topic ? [
                            'name' => $discussion->topic->name,
                            'slug' => $discussion->topic->slug,
                        ] : null,
                        'stats' => [
                            'views' => $discussion->view_count,
                        ],
                        'created_at' => $discussion->created_at->toISOString(),
                    ];
                }),
                'meta' => [
                    'current_page' => $discussions->currentPage(),
                    'last_page' => $discussions->lastPage(),
                    'total' => $discussions->total(),
                ],
            ];
            $results['total'] += $discussions->total();
        }

        // Search Knowledge Base
        if ($type === 'all' || $type === 'knowledge-base') {
            $questions = KnowledgeBaseQuestion::query()
                ->published()
                ->where(function ($q) use ($query) {
                    $q->where('title', 'LIKE', "%{$query}%")
                        ->orWhere('content', 'LIKE', "%{$query}%");
                })
                ->with(['user', 'category'])
                ->select(['id', 'title', 'slug', 'excerpt', 'user_id', 'category_id', 'view_count', 'created_at'])
                ->latest()
                ->paginate($perPage, ['*'], 'kb_page', $page);

            $results['knowledge_base'] = [
                'data' => $questions->map(function ($question) use ($query) {
                    return [
                        'id' => $question->id,
                        'type' => 'knowledge_base',
                        'title' => $this->highlightQuery($question->title, $query),
                        'excerpt' => $this->highlightQuery($question->excerpt ?? $this->truncateContent($question->content, 150), $query),
                        'slug' => $question->slug,
                        'url' => route('public.knowledge-base.show', $question->slug),
                        'author' => [
                            'name' => $question->user->name,
                            'avatar' => $question->user->avatar ?? null,
                        ],
                        'category' => $question->category ? [
                            'name' => $question->category->name,
                            'slug' => $question->category->slug,
                        ] : null,
                        'stats' => [
                            'views' => $question->view_count,
                        ],
                        'created_at' => $question->created_at->toISOString(),
                    ];
                }),
                'meta' => [
                    'current_page' => $questions->currentPage(),
                    'last_page' => $questions->lastPage(),
                    'total' => $questions->total(),
                ],
            ];
            $results['total'] += $questions->total();
        }

        return response()->json([
            'success' => true,
            'data' => $results,
            'query' => $query,
        ]);
    }

    /**
     * Get search suggestions for autocomplete.
     *
     * @param \Illuminate\Http\Request $request
     * @return \Illuminate\Http\JsonResponse
     */
    public function suggestions(Request $request): JsonResponse
    {
        $request->validate([
            'q' => 'required|string|min:2|max:100',
        ]);

        $query = trim($request->get('q'));
        $suggestions = [];

        // Get title suggestions from discussions
        $discussionSuggestions = Discussion::published()
            ->where('title', 'LIKE', "{$query}%")
            ->select(['title', 'slug'])
            ->orderByDesc('view_count')
            ->limit(5)
            ->get();

        foreach ($discussionSuggestions as $discussion) {
            $suggestions[] = [
                'text' => $discussion->title,
                'type' => 'discussion',
                'url' => route('public.discussions.show', $discussion->slug),
            ];
        }

        // Get title suggestions from knowledge base
        $kbSuggestions = KnowledgeBaseQuestion::published()
            ->where('title', 'LIKE', "{$query}%")
            ->select(['title', 'slug'])
            ->orderByDesc('view_count')
            ->limit(5)
            ->get();

        foreach ($kbSuggestions as $question) {
            $suggestions[] = [
                'text' => $question->title,
                'type' => 'knowledge_base',
                'url' => route('public.knowledge-base.show', $question->slug),
            ];
        }

        // Get popular search queries
        $popularSearches = SearchLog::where('query', 'LIKE', "{$query}%")
            ->select('query', DB::raw('COUNT(*) as count'))
            ->groupBy('query')
            ->orderByDesc('count')
            ->limit(5)
            ->get();

        foreach ($popularSearches as $search) {
            // Avoid duplicates
            if (!collect($suggestions)->contains('text', $search->query)) {
                $suggestions[] = [
                    'text' => $search->query,
                    'type' => 'popular',
                    'url' => route('public.discussions.search', ['q' => $search->query]),
                ];
            }
        }

        return response()->json([
            'success' => true,
            'data' => $suggestions,
            'query' => $query,
        ]);
    }

    /**
     * Get popular searches.
     *
     * @param \Illuminate\Http\Request $request
     * @return \Illuminate\Http\JsonResponse
     */
    public function popular(Request $request): JsonResponse
    {
        $popularSearches = SearchLog::select('query', DB::raw('COUNT(*) as count'))
            ->where('created_at', '>=', now()->subDays(30))
            ->groupBy('query')
            ->orderByDesc('count')
            ->limit(10)
            ->get();

        return response()->json([
            'success' => true,
            'data' => $popularSearches->map(function ($search) {
                return [
                    'query' => $search->query,
                    'count' => $search->count,
                    'url' => route('public.discussions.search', ['q' => $search->query]),
                ];
            }),
        ]);
    }

    /**
     * Get recent searches for the authenticated user.
     *
     * @param \Illuminate\Http\Request $request
     * @return \Illuminate\Http\JsonResponse
     */
    public function recent(Request $request): JsonResponse
    {
        $user = auth()->user();

        $recentSearches = SearchLog::where('user_id', $user->id ?? null)
            ->when(!$user, function ($query) use ($request) {
                $query->where('ip_address', $request->ip());
            })
            ->select('query', DB::raw('MAX(created_at) as last_searched'))
            ->groupBy('query')
            ->orderByDesc('last_searched')
            ->limit(5)
            ->get();

        return response()->json([
            'success' => true,
            'data' => $recentSearches->map(function ($search) {
                return [
                    'query' => $search->query,
                    'last_searched' => $search->last_searched,
                    'url' => route('public.discussions.search', ['q' => $search->query]),
                ];
            }),
        ]);
    }

    /**
     * Log a search query.
     *
     * @param string $query
     * @param \Illuminate\Http\Request $request
     * @return void
     */
    protected function logSearch(string $query, Request $request): void
    {
        try {
            SearchLog::create([
                'query' => $query,
                'user_id' => auth()->id(),
                'ip_address' => $request->ip(),
                'user_agent' => $request->userAgent(),
                'results_count' => 0, // Will be updated after search completes if needed
            ]);
        } catch (\Exception $e) {
            // Silently fail if logging doesn't work
        }
    }

    /**
     * Highlight the search query in the text.
     *
     * @param string $text
     * @param string $query
     * @return string
     */
    protected function highlightQuery(string $text, string $query): string
    {
        if (empty($query)) {
            return $text;
        }

        $highlighted = preg_replace(
            '/(' . preg_quote($query, '/') . ')/i',
            '<mark class="bg-yellow-200 text-yellow-900">$1</mark>',
            $text
        );

        return $highlighted;
    }

    /**
     * Truncate content to a specified length.
     *
     * @param string $content
     * @param int $length
     * @return string
     */
    protected function truncateContent(string $content, int $length = 150): string
    {
        $content = strip_tags($content);
        
        if (strlen($content) <= $length) {
            return $content;
        }

        return substr($content, 0, $length) . '...';
    }
}
