<?php

namespace App\Http\Controllers\Admin;

use App\Http\Controllers\Controller;
use Illuminate\Http\Request;
use App\Models\Transaction\Order;
use App\Models\Transaction\Invoice;
use App\Models\Transaction\DispenseRecord;
use App\Models\Transaction\PaymentType;
use App\Models\Transaction\OrderItem;
use App\Models\Transaction\PickupCode;
use App\Models\Transaction\PickupCodeLog;
use App\Models\Transaction\PassCode;
use App\Models\Transaction\PassCodeLog;
use App\Models\Machine\Machine;
use Carbon\Carbon;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\DB;

use App\Models\System\SystemOperationLog;

class SalesController extends Controller
{
    // 銷售中心 (銷售&金流紀錄)
    public function index(Request $request)
    {
        $tab = $request->input('tab', 'orders');
        $isAjax = $request->ajax();
        
        // 取得篩選參數
        $search = $request->input('search');
        $machineId = $request->input('machine_id');
        $paymentType = $request->input('payment_type');
        $status = $request->input('status');
        $startDate = $request->input('start_date');
        $endDate = $request->input('end_date');

        $data = [
            'title' => '銷售&金流紀錄',
            'description' => '銷售交易與金流明細查詢',
            'tab' => $tab,
            'filters' => [
                'search' => $search,
                'machine_id' => $machineId,
                'payment_type' => $paymentType,
                'status' => $status,
                'start_date' => $startDate,
                'end_date' => $endDate,
            ],
            'machines' => Machine::select('id', 'name', 'serial_no')->get(),
            'paymentTypes' => Order::getPaymentTypeLabels(),
        ];

        // 1. 建立基本查詢 (套用共用過濾器：機台、日期)
        $ordersQuery = Order::with(['machine:id,name,serial_no', 'invoice:id,order_id,invoice_no', 'items']);
        $invoicesQuery = Invoice::with(['machine:id,name,serial_no', 'order:id,order_no,flow_id,payment_type']);
        $dispenseQuery = DispenseRecord::with(['order:id,order_no,flow_id', 'machine:id,name,serial_no', 'product:id,name']);

        // 共用過濾器：日期
        if ($startDate && $endDate) {
            $start = Carbon::parse($startDate);
            $end = Carbon::parse($endDate)->endOfMinute();
            $ordersQuery->whereBetween('created_at', [$start, $end]);
            $invoicesQuery->whereBetween('invoice_date', [$start, $end]);
            $dispenseQuery->whereBetween('machine_time', [$start, $end]);
        }

        // 共用過濾器：機台
        if ($machineId) {
            $ordersQuery->where('machine_id', $machineId);
            $invoicesQuery->where('machine_id', $machineId);
            $dispenseQuery->where('machine_id', $machineId);
        }

        // 2. 應用獨立過濾器：搜尋 (僅對當前 Tab 應用)
        if ($search) {
            if ($tab === 'orders') {
                $ordersQuery->where(function($q) use ($search) {
                    $q->where('order_no', 'like', "%{$search}%")
                      ->orWhere('flow_id', 'like', "%{$search}%")
                      ->orWhere('invoice_info', 'like', "%{$search}%")
                      ->orWhere('member_barcode', 'like', "%{$search}%");
                });
            } elseif ($tab === 'invoices') {
                $invoicesQuery->where(function($q) use ($search) {
                    $q->where('invoice_no', 'like', "%{$search}%")
                      ->orWhere('flow_id', 'like', "%{$search}%");
                });
            } elseif ($tab === 'dispense') {
                $dispenseQuery->where(function($q) use ($search) {
                    $q->where('slot_no', 'like', "%{$search}%")
                      ->orWhereHas('product', function($pq) use ($search) {
                          $pq->where('name', 'like', "%{$search}%");
                      })
                      ->orWhereHas('order', function($oq) use ($search) {
                          $oq->where('order_no', 'like', "%{$search}%");
                      });
                });
            }
        }

        // 訂單專用過濾器
        if ($tab === 'orders') {
            if ($paymentType) $ordersQuery->where('payment_type', $paymentType);
            if ($status) $ordersQuery->where('status', $status);
        }

        // 3. 執行分頁 (使用獨立的 pageName)
        $perPage = $request->input('per_page', 10);
        $data['orders'] = $ordersQuery->latest()->paginate($perPage, ['*'], 'orders_page')->withQueryString();
        $data['invoices'] = $invoicesQuery->latest()->paginate($perPage, ['*'], 'invoices_page')->withQueryString();
        $data['dispenseLogs'] = $dispenseQuery->latest()->paginate($perPage, ['*'], 'dispense_page')->withQueryString();

        if ($isAjax) {
            return response()->json([
                'success' => true,
                'tab' => $tab,
                'html' => view('admin.sales.partials.tab-' . $tab, $data)->render()
            ]);
        }

        return view('admin.sales.index', $data);
    }

    /**
     * 取得單筆交易詳情 (用於 Slide-over)
     */
    public function show(Order $order)
    {
        $order->load(['machine', 'invoice', 'items', 'dispenseRecords.product']);
        
        return response()->json([
            'success' => true,
            'html' => view('admin.sales.partials.order-detail-panel', [
                'order' => $order,
                'paymentTypes' => Order::getPaymentTypeLabels()
            ])->render()
        ]);
    }

    // 取貨碼設定
    public function pickupCodes(Request $request)
    {
        $tab = $request->input('tab', 'list');
        $isAjax = $request->ajax();

        $data = [
            'title' => '取貨碼設定',
            'description' => '產生與管理商品取貨驗證碼',
            'tab' => $tab,
        ];

        // 1. 取貨碼列表 (list)
        if (!$isAjax || $tab === 'list') {
            $query = PickupCode::with(['machine.slots.product', 'creator', 'order'])->latest();

            if ($request->search) {
                $query->where(function ($q) use ($request) {
                    $q->where('code', 'like', "%{$request->search}%")
                        ->orWhereHas('machine', function ($mq) use ($request) {
                            $mq->where('name', 'like', "%{$request->search}%")
                                ->orWhere('serial_no', 'like', "%{$request->search}%");
                        });
                });
            }

            if ($request->status && trim($request->status) !== '') {
                $query->where('status', trim($request->status));
            }

            $per_page = $request->input('per_page', 10);
            $data['pickupCodes'] = $query->paginate($per_page, ['*'], 'list_page')->withQueryString();
            
            // 供新增彈窗使用的機台清單
            $data['machines'] = Machine::all();
        }

        // 2. 操作紀錄 (logs)
        if (!$isAjax || $tab === 'logs') {
            $logQuery = PickupCodeLog::with(['user:id,name', 'machine:id,name,serial_no', 'pickupCode', 'order']);

            if ($request->filled('search_log')) {
                $search = $request->input('search_log');
                $logQuery->where(function ($q) use ($search) {
                    $q->where('remark', 'like', "%{$search}%")
                      ->orWhereHas('pickupCode', function($pq) use ($search) {
                          $pq->where('code', 'like', "%{$search}%");
                      });
                });
            }

            // 新增：類型篩選
            if ($request->filled('action')) {
                $logQuery->where('action', $request->action);
            }

            // 新增：日期區間篩選
            if ($request->filled('start_date') && $request->filled('end_date')) {
                try {
                    $start = \Carbon\Carbon::parse($request->start_date)->startOfMinute();
                    $end = \Carbon\Carbon::parse($request->end_date)->endOfMinute();
                    $logQuery->whereBetween('created_at', [$start, $end]);
                } catch (\Exception $e) { }
            }

            $data['logs'] = $logQuery->latest()
                ->paginate($request->input('per_page', 10), ['*'], 'log_page')
                ->withQueryString();

            // 定義可用動作
            $data['actions'] = [
                'create' => __('create'),
                'update' => __('update'),
                'cancel' => __('cancel'),
                'used' => __('used'),
                'consume' => __('consume'),
                'consume_failed' => __('consume_failed'),
                'verify_success' => __('verify_success'),
            ];
        }

        if ($isAjax) {
            return response()->json([
                'success' => true,
                'tab' => $tab,
                'html' => view('admin.sales.pickup-codes.partials.tab-' . $tab, $data)->render()
            ]);
        }

        return view('admin.sales.pickup-codes.index', $data);
    }

    /**
     * 產生取貨碼
     */
    public function storePickupCode(Request $request)
    {
        $validated = $request->validate([
            'machine_id' => 'required|exists:machines,id',
            'slot_no' => 'required|string',
            'usage_limit' => 'nullable|integer|min:1|max:20',
            'expires_hours' => 'nullable|integer|min:1|max:720', 
            'expires_at' => 'nullable|date|after:now',
            'custom_code' => 'nullable|string|min:4|max:12',
        ]);

        $machine = Machine::findOrFail($validated['machine_id']);
        
        // 處理過期時間：優先使用直接傳入的日期，否則使用時數計算
        $expiresAt = $request->filled('expires_at') 
            ? Carbon::parse($validated['expires_at']) 
            : now()->addHours((int) ($request->expires_hours ?? 24));

        $pickupCode = PickupCode::create([
            'machine_id' => $validated['machine_id'],
            'slot_no' => $validated['slot_no'],
            'code' => $request->custom_code ?? PickupCode::generateUniqueCode($validated['machine_id']),
            'usage_limit' => $validated['usage_limit'] ?? 1,
            'usage_count' => 0,
            'expires_at' => $expiresAt,
            'status' => 'active',
            'company_id' => $machine->company_id,
            'created_by' => Auth::id(),
        ]);

        SystemOperationLog::create([
            'company_id' => $machine->company_id,
            'user_id' => Auth::id(),
            'module' => 'pickup_code',
            'action' => 'create',
            'target_id' => $pickupCode->id,
            'target_type' => PickupCode::class,
            'new_values' => $pickupCode->toArray(),
        ]);

        return back()->with('success', __('Pickup code generated: :code', ['code' => $pickupCode->code]));
    }

    /**
     * 更新取貨碼 (僅限修改時間)
     */
    public function updatePickupCode(Request $request, PickupCode $pickupCode)
    {
        $validated = $request->validate([
            'expires_at' => 'nullable|date|after:now',
            'usage_limit' => 'nullable|integer|min:1|max:20',
        ]);

        $oldValues = $pickupCode->toArray();

        $pickupCode->update(array_filter([
            'expires_at' => $validated['expires_at'] ?? null,
            'usage_limit' => $validated['usage_limit'] ?? null,
        ]));

        SystemOperationLog::create([
            'company_id' => $pickupCode->company_id,
            'user_id' => Auth::id(),
            'module' => 'pickup_code',
            'action' => 'update',
            'target_id' => $pickupCode->id,
            'target_type' => PickupCode::class,
            'old_values' => $oldValues,
            'new_values' => $pickupCode->toArray(),
        ]);

        return back()->with('success', __('Pickup code updated.'));
    }

    /**
     * 刪除/取消取貨碼
     */
    public function destroyPickupCode(PickupCode $pickupCode)
    {
        $oldValues = $pickupCode->toArray();
        $pickupCode->update(['status' => 'cancelled']);

        SystemOperationLog::create([
            'company_id' => $pickupCode->company_id,
            'user_id' => Auth::id(),
            'module' => 'pickup_code',
            'action' => 'cancel',
            'target_id' => $pickupCode->id,
            'target_type' => PickupCode::class,
            'old_values' => $oldValues,
            'new_values' => $pickupCode->toArray(),
        ]);

        return back()->with('success', __('Pickup code cancelled.'));
    }

    // 購買單
    public function orders()
    {
        return view('admin.placeholder', [
            'title' => '購買單',
            'description' => '購買訂單管理',
        ]);
    }

    // 促銷時段設定
    public function promotions()
    {
        return view('admin.placeholder', [
            'title' => '促銷時段設定',
            'description' => '促銷活動時間設定',
        ]);
    }

    // 通行碼設定
    public function passCodes(Request $request)
    {
        $tab = $request->input('tab', 'list');
        $isAjax = $request->ajax();

        $data = [
            'title' => '通行碼設定',
            'description' => '特殊通行權限碼管理 (測試/補貨用)',
            'tab' => $tab,
        ];

        // 1. 通行碼列表 (list)
        if (!$isAjax || $tab === 'list') {
            $query = PassCode::with(['machine', 'creator'])->latest();

            if ($request->search) {
                $query->where(function ($q) use ($request) {
                    $q->where('code', 'like', "%{$request->search}%")
                        ->orWhere('name', 'like', "%{$request->search}%")
                        ->orWhereHas('machine', function ($mq) use ($request) {
                            $mq->where('name', 'like', "%{$request->search}%")
                                ->orWhere('serial_no', 'like', "%{$request->search}%");
                        });
                });
            }

            if ($request->status && trim($request->status) !== '') {
                $status = trim($request->status);
                if ($status === 'active') {
                    $query->where('status', 'active')
                        ->where(function ($q) {
                            $q->whereNull('expires_at')
                                ->orWhere('expires_at', '>', now());
                        });
                } elseif ($status === 'expired') {
                    $query->where('status', 'active')
                        ->whereNotNull('expires_at')
                        ->where('expires_at', '<=', now());
                } else {
                    $query->where('status', $status);
                }
            }

            $data['passCodes'] = $query->paginate($request->input('per_page', 10), ['*'], 'list_page')->withQueryString();
            $data['machines'] = Machine::all();
        }

        // 2. 操作紀錄 (logs)
        if (!$isAjax || $tab === 'logs') {
            $logQuery = PassCodeLog::with(['user:id,name', 'machine:id,name,serial_no', 'passCode']);

            if ($request->filled('search_log')) {
                $search = $request->input('search_log');
                $logQuery->where(function ($q) use ($search) {
                    $q->where('remark', 'like', "%{$search}%")
                      ->orWhereHas('passCode', function($pq) use ($search) {
                          $pq->where('code', 'like', "%{$search}%")
                            ->orWhere('name', 'like', "%{$search}%");
                      });
                });
            }

            // 新增：類型篩選
            if ($request->filled('action')) {
                $logQuery->where('action', $request->action);
            }

            // 新增：日期區間篩選
            if ($request->filled('start_date') && $request->filled('end_date')) {
                try {
                    $start = \Carbon\Carbon::parse($request->start_date)->startOfMinute();
                    $end = \Carbon\Carbon::parse($request->end_date)->endOfMinute();
                    $logQuery->whereBetween('created_at', [$start, $end]);
                } catch (\Exception $e) { }
            }

            $data['logs'] = $logQuery->latest()
                ->paginate($request->input('per_page', 10), ['*'], 'log_page')
                ->withQueryString();

            // 定義可用動作
            $data['actions'] = [
                'create' => __('create'),
                'update' => __('update'),
                'cancel' => __('cancel'),
                'used' => __('used'),
                'consume' => __('consume'),
                'verify_success' => __('verify_success'),
            ];
        }

        if ($isAjax) {
            return response()->json([
                'success' => true,
                'tab' => $tab,
                'html' => view('admin.sales.pass-codes.partials.tab-' . $tab, $data)->render()
            ]);
        }

        return view('admin.sales.pass-codes.index', $data);
    }

    /**
     * 產生通行碼
     */
    public function storePassCode(Request $request)
    {
        $validated = $request->validate([
            'machine_id' => 'required|exists:machines,id',
            'name' => 'required|string|max:50',
            'expires_days' => 'nullable|integer|min:0',
            'custom_code' => 'required|string|min:4|max:12',
        ]);

        $machine = Machine::findOrFail($validated['machine_id']);
        $expiresAt = $request->expires_days ? now()->addDays((int) $request->expires_days) : null;

        $passCode = PassCode::create([
            'machine_id' => $validated['machine_id'],
            'name' => $validated['name'] ?? 'Manual Generate',
            'code' => $validated['custom_code'] ?? PassCode::generateUniqueCode($validated['machine_id']),
            'expires_at' => $expiresAt,
            'status' => 'active',
            'company_id' => $machine->company_id,
            'created_by' => Auth::id(),
        ]);

        SystemOperationLog::create([
            'company_id' => $machine->company_id,
            'user_id' => Auth::id(),
            'module' => 'pass_code',
            'action' => 'create',
            'target_id' => $passCode->id,
            'target_type' => PassCode::class,
            'new_values' => $passCode->toArray(),
        ]);

        return back()->with('success', __('Pass code created: :code', ['code' => $passCode->code]));
    }

    /**
     * 更新通行碼
     */
    public function updatePassCode(Request $request, PassCode $passCode)
    {
        $validated = $request->validate([
            'name' => 'nullable|string|max:50',
            'expires_at' => 'nullable|date',
            'status' => 'nullable|in:active,disabled',
        ]);

        // 確保 expires_at 為空字串時轉為 null
        if (isset($validated['expires_at']) && empty($validated['expires_at'])) {
            $validated['expires_at'] = null;
        }

        $oldValues = $passCode->toArray();

        $passCode->update(array_filter($validated, function ($value, $key) use ($request) {
            return $request->has($key);
        }, ARRAY_FILTER_USE_BOTH));

        SystemOperationLog::create([
            'company_id' => $passCode->company_id,
            'user_id' => Auth::id(),
            'module' => 'pass_code',
            'action' => 'update',
            'target_id' => $passCode->id,
            'target_type' => PassCode::class,
            'old_values' => $oldValues,
            'new_values' => $passCode->toArray(),
        ]);

        return back()->with('success', __('Pass code updated.'));
    }

    /**
     * 刪除通行碼 (改為停用)
     */
    public function destroyPassCode(PassCode $passCode)
    {
        $oldValues = $passCode->toArray();
        $passCode->update(['status' => 'disabled']);

        SystemOperationLog::create([
            'company_id' => $passCode->company_id,
            'user_id' => Auth::id(),
            'module' => 'pass_code',
            'action' => 'cancel',
            'target_id' => $passCode->id,
            'target_type' => PassCode::class,
            'old_values' => $oldValues,
            'new_values' => $passCode->toArray(),
        ]);

        return back()->with('success', __('Pass code cancelled.'));
    }

    // 來店禮設定
    public function storeGifts()
    {
        return view('admin.placeholder', [
            'title' => '來店禮設定',
            'description' => '來店優惠活動設定',
        ]);
    }
}
