<?php

namespace App\Services\Client;

use App\Models\Order;
use App\Models\OrderRecord;
use App\Models\WalletRefundRecord;

use App\Models\User;
use App\Models\MemberAddress;
use App\Models\CoachUser;
use App\Models\Project;
use App\Models\AgentInfo;
use App\Models\AgentConfig;
use App\Models\CoachConfig;
use App\Models\Wallet;
use App\Models\Coupon;
use App\Models\CoachSchedule;
use App\Models\MemberUser;
use App\Models\OrderHistory;
use App\Models\OrderGrabRecord;

use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\DB;
use Exception;

class OrderService
{
    protected AgentService $agentService;
    protected ProjectService $projectService;
    
    public function __construct(
        AgentService $agentService,
        ProjectService $projectService
    ) {
        $this->agentService = $agentService;
        $this->projectService = $projectService;
    }

     /**
     * 订单初始化
     */
    public function initialize($userId, $coachId, $areaCode, $projectId)
    {
        // 查询用户钱包
        $wallet = Wallet::where('user_id', $userId)->first();

        // 查询默认地址
        $address = MemberAddress::where('user_id', $userId)
            ->where('is_default', 1)
            ->first();

        if ($address) {
            $areaCode = $address->area_code;
        }

        // 查询技师数据
        $coach = CoachUser::where('id', $coachId)
            ->where('state', 'enable')
            ->where('auth_state', 'passed')
            ->first();

        // 查询技师排班
        // $schedule = CoachSchedule::where('coach_id', $coachId)
        //     ->where('date', date('Y-m-d'))
        //     ->first();

        // // 查询用户优惠券
        // $coupons = Coupon::where('user_id', $userId)
        //     ->where('state', 'enable')
        //     ->where('expire_time', '>', now())
        //     ->get();

        // 获取代理商
        $agent = $this->agentService->getAgent($areaCode);

        // 获取项目详情
        $project = $this->projectService->getProjectDetail($projectId, $agent->id);

        // 计算订单金额
        $amounts = $this->calculateOrderAmount($userId, $address->id, $coachId, $projectId, $agent->id);

        return [
            'wallet' => $wallet,
            'coach' => $coach,
            'project' => $project,
            'address' => $address,
            // 'schedule' => $schedule,
            'amounts' => $amounts,
            // 'coupons' => $coupons
        ];
    }

    /**
     * 结束订单
     */
    public function finishOrder($userId, $orderId)
    {
        return DB::transaction(function() use ($userId, $orderId) {
            $order = Order::where('user_id', $userId)
                ->where('id', $orderId)
                ->first();

            if (!$order) {
                throw new Exception('订单不存在');
            }

            // 添加订单结束记录
            OrderRecord::create([
                'order_id' => $orderId,
                'user_id' => $userId,
                'state' => 'finish',
                'remark' => '服务完成'
            ]);

            // 修改订单状态
            $order->status = 'finished';
            $order->save();

            return ['message' => '订单已完成'];
        });
    }

    /**
     * 确认技师离开
     */
    public function confirmLeave($userId, $orderId)
    {
        return DB::transaction(function() use ($userId, $orderId) {
            $order = Order::where('user_id', $userId)
                ->where('id', $orderId)
                ->first();

            if (!$order) {
                throw new Exception('订单不存在');
            }

            // 添加订单撤离记录
            OrderRecord::create([
                'order_id' => $orderId,
                'user_id' => $userId,
                'state' => 'leave',
                'remark' => '技师已离开'
            ]);

            // 修改订单状态
            $order->status = 'allow_leave';
            $order->save();

            return ['message' => '已确认技师离开'];
        });
    }

    /**
     * 取消订单
     */
    public function cancelOrder($userId, $orderId)
    {
        return DB::transaction(function() use ($userId, $orderId) {
            $order = Order::where('user_id', $userId)
                ->where('id', $orderId)
                ->first();

            if (!$order) {
                throw new Exception('订单不存在');
            }

            // 添加订单取消记录
            OrderRecord::create([
                'order_id' => $orderId,
                'user_id' => $userId,
                'state' => 'cancel',
                'remark' => '用户取消订单'
            ]);

            // 修改订单状态
            $order->status = 'cancelled';
            $order->save();

            return ['message' => '订单已取消'];
        });
    }

    /**
     * 获取订单列表
     */
    public function getOrderList()
    {
        $userId = Auth::id();
        
        return Order::where('user_id', $userId)
            ->with([
                'project:id,title,cover,price',
                'coach:id,name,avatar',
                'agent:id,company_name',
                'address:id,address'
            ])
            ->orderBy('created_at', 'desc')
            ->paginate(10);
    }

    /**
     * 获取订单详情
     */
    public function getOrderDetail($orderId)
    {
        $userId = Auth::id();

        return Order::where('id', $orderId)
            ->where('user_id', $userId)
            ->with([
                'project:id,title,cover,price,duration',
                'coach:id,name,avatar,mobile',
                'agent:id,company_name',
                'address:id,address,latitude,longitude',
                'records' => function($query) {
                    $query->orderBy('created_at', 'asc');
                }
            ])
            ->firstOrFail();
    }

    /**
     * 订单退款
     */
    public function refundOrder($orderId)
    {
        $userId = Auth::id();

        return DB::transaction(function() use ($orderId, $userId) {
            // 查询并锁定订单
            $order = Order::where('id', $orderId)
                ->where('user_id', $userId)
                ->where('state', 'pending')
                ->lockForUpdate()
                ->firstOrFail();

            // 更新订单状态
            $order->state = 'refunded';
            $order->save();

            // 添加订单记录
            OrderRecord::create([
                'order_id' => $orderId,
                'object_id' => $userId,
                'object_type' => 'user',
                'state' => 'refund',
                'remark' => '订单退款'
            ]);

            // 创建退款记录
            WalletRefundRecord::create([
                'order_id' => $orderId,
                'user_id' => $userId,
                'amount' => $order->total_amount,
                'state' => 'success'
            ]);

            return ['message' => '退款成功'];
        });
    }

     /**
     * 获取代理商配置
     */
    public function getAgentConfig($agentId)
    {
        $agent = AgentInfo::where('id', $agentId)
            ->where('state', 'enable')
            ->firstOrFail();

        // $config = AgentConfig::where('agent_id', $agentId)->firstOrFail();

        return [
            // 'min_distance' => $config->min_distance,
            // 'min_fee' => $config->min_fee,
            // 'per_km_fee' => $config->per_km_fee
        ];
    }

    /**
     * 获取技师配置
     */
    public function getCoachConfig($coachId)
    {
        $coach = CoachUser::where('id', $coachId)
            ->where('state', 'enable')
            ->where('auth_state', 'passed')
            ->firstOrFail();

        // $config = CoachConfig::where('coach_id', $coachId)->firstOrFail();

        return [
            // 'delivery_fee_type' => $config->delivery_fee_type,
            // 'charge_delivery_fee' => $config->charge_delivery_fee
        ];
    }

    /**
     * 计算路费金额
     */
    public function calculateDeliveryFee($coachId, $agentId, $distance)
    {
        $coach = CoachUser::where('id', $coachId)
            ->where('state', 'enable')
            ->where('auth_state', 'passed')
            ->firstOrFail();

        $coachConfig = CoachConfig::where('coach_id', $coachId)->firstOrFail();

        if (!$coachConfig->charge_delivery_fee) {
            return 0;
        }

        $agentConfig = AgentConfig::where('agent_id', $agentId)->firstOrFail();

        $fee = 0;
        if ($distance <= $agentConfig->min_distance) {
            $fee = $agentConfig->min_fee;
        } else {
            $extraDistance = $distance - $agentConfig->min_distance;
            $fee = $agentConfig->min_fee + ($extraDistance * $agentConfig->per_km_fee);
        }

        return $coachConfig->delivery_fee_type == 'round_trip' ? $fee * 2 : $fee;
    }

    /**
     * 计算订单金额
     */
    public function calculateOrderAmount($userId, $addressId, $coachId, $projectId, $agentId, $useBalance = false)
    {
        // 参数校验
        $user = MemberUser::where('id', $userId)
            ->where('status', 1)
            ->firstOrFail();

        $address = MemberAddress::where('id', $addressId)
            ->where('user_id', $userId)
            ->firstOrFail();

        $coach = CoachUser::where('id', $coachId)
            ->where('state', 'enable')
            ->where('auth_state', 'passed')
            ->firstOrFail();

        $project = Project::where('id', $projectId)
            ->where('state', 'enable')
            ->firstOrFail();

        // 计算金额
        $projectAmount = $project->price;
        $deliveryFee = $this->calculateDeliveryFee($coachId, $agentId, $address->distance);
        $tipAmount = request()->has('order_id') ? Order::find(request()->input('order_id'))->tip_amount : 0;
        
        $couponAmount = 0;
        if (request()->has('coupon_id')) {
            // $coupon = Coupon::where('id', request()->input('coupon_id'))
            //     ->where('state', 'enable')
            //     ->firstOrFail();
            // $couponAmount = $coupon->amount;
        }

        $totalAmount = $projectAmount + $deliveryFee + $tipAmount - $couponAmount;

        $balanceAmount = 0;
        $payAmount = $totalAmount;

        if ($useBalance) {
            $wallet = Wallet::where('user_id', $userId)->first();
            if ($wallet && $wallet->balance >= $totalAmount) {
                $balanceAmount = $totalAmount;
                $payAmount = 0;
            } else if ($wallet) {
                $balanceAmount = $wallet->balance;
                $payAmount = $totalAmount - $balanceAmount;
            }
        }

        return [
            'total_amount' => $totalAmount,
            'balance_amount' => $balanceAmount,
            'pay_amount' => $payAmount,
            'coupon_amount' => $couponAmount,
            'tip_amount' => $tipAmount,
            'project_amount' => $projectAmount,
            'delivery_fee' => $deliveryFee
        ];
    }

    /**
     * 创建订单
     */
    public function createOrder($userId, $projectId, $addressId, $coachId, $useBalance, $orderId = null)
    {
        return DB::transaction(function() use ($userId, $projectId, $addressId, $coachId, $useBalance, $orderId) {
            // 参数校验
            $user = MemberUser::where('id', $userId)
                ->where('status', 1)
                ->firstOrFail();

            $address = MemberAddress::where('id', $addressId)
                ->where('user_id', $userId)
                ->firstOrFail();

            if (!$orderId) {
                $coach = CoachUser::where('id', $coachId)
                    ->where('state', 'enable')
                    ->where('auth_state', 'passed')
                    ->firstOrFail();
            }

            $project = Project::where('id', $projectId)
                ->where('state', 'enable')
                ->firstOrFail();

            // 创建订单
            $orderType = $orderId ? 'add_time' : 'normal';
            $amounts = $this->calculateOrderAmount($userId, $addressId, $coachId, $projectId, $project->agent_id, $useBalance);

            $order = new Order();
            $order->user_id = $userId;
            $order->project_id = $projectId;
            $order->address_id = $addressId;
            $order->coach_id = $coachId;
            $order->order_type = $orderType == 'normal' ? 0 : 1;
            $order->status = 0;
            $order->total_amount = $amounts['total_amount'];
            $order->balance_amount = $amounts['balance_amount'];
            $order->pay_amount = $amounts['pay_amount'];
            $order->coupon_amount = $amounts['coupon_amount'];
            $order->tip_amount = $amounts['tip_amount'];
            $order->project_amount = $amounts['project_amount'];
            $order->delivery_fee = $orderType == 'add_time' ? 0 : $amounts['delivery_fee'];
            $order->payment_type = $useBalance && $amounts['pay_amount'] == 0 ? 0 : 1;
            $order->save();

            // 创建订单历史
            if ($orderType == 'add_time') {
                OrderRecord::create([
                    'order_id' => $order->id,
                    'type' => 'add_time',
                    'user_id' => $userId
                ]);
            } else {
                OrderRecord::create([
                    'order_id' => $order->id,
                    'type' => 'create',
                    'user_id' => $userId
                ]);
            }

            // 余额支付处理
            if ($order->payment_type == 'balance') {
                $order->status = 'paid';
                $order->save();

                OrderRecord::create([
                    'order_id' => $order->id,
                    'type' => 'pay',
                    'user_id' => $userId
                ]);

                // CoachSchedule::create([
                //     'coach_id' => $coachId,
                //     'date' => date('Y-m-d'),
                //     'status' => 'busy'
                // ]);

                return $order->id;
            }

            // 微信支付处理
            // TODO: 调用支付接口

            return $order->id;
        });
    }

    /**
     * 加钟
     */
    public function addTime($userId, $orderId)
    {
        $order = Order::where('id', $orderId)
            ->where('user_id', $userId)
            ->firstOrFail();

        return $this->createOrder($userId, $order->project_id, $order->address_id, $order->coach_id, 0, $orderId);
    }

    /**
     * 指定技师
     */
    public function assignCoach($userId, $orderId, $coachId)
    {
        return DB::transaction(function() use ($userId, $orderId, $coachId) {
            // 参数校验
            $user = MemberUser::where('id', $userId)
                ->where('status', 'enable')
                ->firstOrFail();

            $order = Order::where('id', $orderId)
                ->where('user_id', $userId)
                ->whereIn('status', [0, 1, 6])
                ->firstOrFail();

            $coach = CoachUser::where('id', $coachId)
                ->where('state', 'enable')
                ->where('auth_state', 'passed')
                ->firstOrFail();

            // $schedule = CoachSchedule::where('coach_id', $coachId)
            //     ->where('date', date('Y-m-d'))
            //     ->where('status', 'free')
            //     ->firstOrFail();

            // 修改订单
            $order->coach_id = $coachId;
            if ($order->status == 'created') {
                $amounts = $this->calculateOrderAmount($userId, $order->address_id, $coachId, $order->project_id, $order->agent_id, $order->payment_type == 'balance');
                
                $order->total_amount = $amounts['total_amount'];
                $order->balance_amount = $amounts['balance_amount'];
                $order->pay_amount = $amounts['pay_amount'];
                $order->coupon_amount = $amounts['coupon_amount'];
                $order->tip_amount = $amounts['tip_amount'];
                $order->project_amount = $amounts['project_amount'];
                $order->delivery_fee = $amounts['delivery_fee'];

                if ($order->payment_type == 'balance') {
                    $order->status = 'paid';
                }
            }
            if ($order->status == 'paid') {
                $order->status = 'assigned';
            }
            $order->save();

            // 创建订单历史
            OrderRecord::create([
                'order_id' => $order->id,
                'type' => 'assigned',
                'user_id' => $userId,
                'coach_id' => $coachId
            ]);

            OrderRecord::create([
                'order_id' => $order->id,
                'type' => 'accepted',
                'user_id' => $userId,
                'coach_id' => $coachId,
                'remark' => '抢单成功'
            ]);

            // 更新抢单池
            OrderGrabRecord::where('order_id', $orderId)
                ->update(['status' => 'success', 'coach_id' => $coachId]);

            // 更新排班
            // $schedule->status = 'busy';
            // $schedule->save();

            return true;
        });
    }
} 