<?php

namespace App\Http\Controllers\Admin;

use App\Http\Controllers\Controller;
use App\Models\Category;
use Illuminate\Http\Request;

class CategoryController extends Controller
{
    public function index()
    {
        $tree = Category::tree();
        // flat list for parent dropdown
        $flat = $this->flatten($tree);
        return view('admin.categories.index', compact('tree', 'flat'));
    }

    public function create()
    {
        $flat = $this->flatten(Category::tree());
        $category = new Category();
        return view('admin.categories.form', compact('flat', 'category'));
    }

    public function store(Request $request)
    {
        $data = $this->validateCategory($request);
        Category::create($data);
        return redirect()->route('admin.categories.index')->with('success', 'Category created.');
    }

    public function edit(Category $category)
    {
        $flat = $this->flatten(Category::tree());
        // remove self and descendants from parent options
        $exclude = $this->collectIds($category);
        $exclude[] = $category->id;
        $flat = array_filter($flat, fn($f) => !in_array($f['id'], $exclude));
        return view('admin.categories.form', compact('flat', 'category'));
    }

    public function update(Request $request, Category $category)
    {
        $data = $this->validateCategory($request, $category->id);
        $category->update($data);
        return redirect()->route('admin.categories.index')->with('success', 'Category updated.');
    }

    public function destroy(Category $category)
    {
        $category->delete(); // cascade deletes children
        return back()->with('success', 'Category deleted.');
    }

    protected function validateCategory(Request $request, $id = null): array
    {
        return $request->validate([
            'parent_id'   => ['nullable', 'exists:categories,id'],
            'name'        => ['required', 'string', 'max:255'],
            'description' => ['nullable', 'string'],
            'icon'        => ['nullable', 'string', 'max:100'],
            'sort_order'  => ['nullable', 'integer'],
            'is_active'   => ['nullable', 'boolean'],
        ]);
    }

    protected function flatten($categories, int $depth = 0): array
    {
        $out = [];
        foreach ($categories as $cat) {
            $out[] = [
                'id'    => $cat->id,
                'name'  => str_repeat('— ', $depth) . $cat->name,
                'depth' => $depth,
                'raw'   => $cat,
            ];
            if ($cat->relationLoaded('childrenRecursive') && $cat->childrenRecursive->isNotEmpty()) {
                $out = array_merge($out, $this->flatten($cat->childrenRecursive, $depth + 1));
            }
        }
        return $out;
    }

    protected function collectIds(Category $cat): array
    {
        $ids = [];
        foreach ($cat->children as $child) {
            $ids[] = $child->id;
            $ids = array_merge($ids, $this->collectIds($child));
        }
        return $ids;
    }
}
