<?php

namespace App\Services;

use App\Models\BadDebts\BadDebt;
use App\Models\Orders\Client;
use App\Models\Orders\Order;
use App\Models\Tenants\ApprovalStep;
use App\Models\Tenants\Leave;
use App\Models\Tenants\Purchase;
use App\Models\Tenants\Schedule;
use App\Models\Tenants\Stock;
use Carbon\Carbon;

/**
 * CEO 대시보드 현황판(StatusBoard) 서비스
 *
 * 각 카테고리별 건수를 집계하여 현황판 데이터 제공
 */
class StatusBoardService extends Service
{
    /**
     * 현황판 전체 데이터 조회
     */
    public function summary(): array
    {
        $tenantId = $this->tenantId();
        $userId = $this->apiUserId();
        $today = Carbon::today();

        return [
            'items' => [
                $this->getOrdersStatus($tenantId, $today),
                $this->getBadDebtStatus($tenantId),
                $this->getSafetyStockStatus($tenantId),
                $this->getTaxDeadlineStatus($tenantId, $today),
                $this->getNewClientStatus($tenantId, $today),
                $this->getLeaveStatus($tenantId, $today),
                $this->getPurchaseStatus($tenantId),
                $this->getApprovalStatus($tenantId, $userId),
            ],
        ];
    }

    /**
     * 수주 현황 (오늘 신규 수주 건수)
     */
    private function getOrdersStatus(int $tenantId, Carbon $today): array
    {
        $count = Order::query()
            ->where('tenant_id', $tenantId)
            ->whereDate('created_at', $today)
            ->where('status_code', Order::STATUS_CONFIRMED) // 확정된 수주만
            ->count();

        return [
            'id' => 'orders',
            'label' => __('message.status_board.orders'),
            'count' => $count,
            'path' => '/sales/order-management-sales',
            'isHighlighted' => false,
        ];
    }

    /**
     * 채권 추심 현황 (추심 진행 중인 건수)
     */
    private function getBadDebtStatus(int $tenantId): array
    {
        $count = BadDebt::query()
            ->where('tenant_id', $tenantId)
            ->where('status', BadDebt::STATUS_COLLECTING) // 추심 진행 중
            ->where('is_active', true) // 활성 채권만 (목록 페이지와 일치)
            ->count();

        return [
            'id' => 'bad_debts',
            'label' => __('message.status_board.bad_debts'),
            'count' => $count,
            'path' => '/accounting/bad-debt-collection',
            'isHighlighted' => false,
        ];
    }

    /**
     * 안전 재고 현황 (안전재고 미달 품목 수)
     */
    private function getSafetyStockStatus(int $tenantId): array
    {
        $count = Stock::query()
            ->where('tenant_id', $tenantId)
            ->where('safety_stock', '>', 0) // 안전재고 설정된 품목만
            ->whereColumn('stock_qty', '<', 'safety_stock')
            ->count();

        $isHighlighted = $count > 0; // 미달 품목 있으면 강조

        return [
            'id' => 'safety_stock',
            'label' => __('message.status_board.safety_stock'),
            'count' => $count,
            'path' => '/material/stock-status',
            'isHighlighted' => $isHighlighted,
        ];
    }

    /**
     * 세금 신고 현황 (부가세 신고 D-day)
     *
     * Schedule 테이블에서 type='tax'인 가장 가까운 일정 조회
     * - 본사(tenant_id=NULL) 등록 글로벌 일정 + 테넌트 전용 일정 모두 포함
     */
    private function getTaxDeadlineStatus(int $tenantId, Carbon $today): array
    {
        // Schedule 테이블에서 가장 가까운 세금 신고 일정 조회
        $nextTaxSchedule = Schedule::query()
            ->forTenant($tenantId)
            ->active()
            ->tax()
            ->upcoming($today->format('Y-m-d'))
            ->first();

        if (! $nextTaxSchedule) {
            // 등록된 세금 일정이 없는 경우
            return [
                'id' => 'tax_deadline',
                'label' => __('message.status_board.tax_deadline'),
                'count' => __('message.status_board.tax_no_schedule'),
                'path' => '/accounting/tax',
                'isHighlighted' => false,
            ];
        }

        $deadline = $nextTaxSchedule->start_date;
        $daysUntil = $today->diffInDays($deadline, false);

        $countText = $daysUntil >= 0
            ? __('message.status_board.tax_d_day', ['days' => $daysUntil])
            : __('message.status_board.tax_overdue', ['days' => abs($daysUntil)]);

        return [
            'id' => 'tax_deadline',
            'label' => __('message.status_board.tax_deadline'),
            'count' => $countText,
            'path' => '/accounting/tax',
            'isHighlighted' => $daysUntil <= 7 && $daysUntil >= 0,
        ];
    }

    /**
     * 신규 업체 등록 현황 (최근 7일 신규 거래처)
     */
    private function getNewClientStatus(int $tenantId, Carbon $today): array
    {
        $count = Client::query()
            ->where('tenant_id', $tenantId)
            ->where('created_at', '>=', $today->copy()->subDays(7))
            ->count();

        return [
            'id' => 'new_clients',
            'label' => __('message.status_board.new_clients'),
            'count' => $count,
            'path' => '/accounting/vendors',
            'isHighlighted' => false,
        ];
    }

    /**
     * 연차 현황 (오늘 휴가 중인 인원)
     */
    private function getLeaveStatus(int $tenantId, Carbon $today): array
    {
        $count = Leave::query()
            ->where('tenant_id', $tenantId)
            ->where('status', 'approved')
            ->whereDate('start_date', '<=', $today)
            ->whereDate('end_date', '>=', $today)
            ->count();

        return [
            'id' => 'leaves',
            'label' => __('message.status_board.leaves'),
            'count' => $count,
            'path' => '/hr/vacation-management',
            'isHighlighted' => false,
        ];
    }

    /**
     * 발주 현황 (발주 대기 건수)
     */
    private function getPurchaseStatus(int $tenantId): array
    {
        $count = Purchase::query()
            ->where('tenant_id', $tenantId)
            ->where('status', 'draft') // 대기 중인 발주 (임시저장 상태)
            ->count();

        return [
            'id' => 'purchases',
            'label' => __('message.status_board.purchases'),
            'count' => $count,
            'path' => '/construction/order/order-management',
            'isHighlighted' => false,
        ];
    }

    /**
     * 결재 요청 현황 (나의 결재 대기 건수)
     */
    private function getApprovalStatus(int $tenantId, int $userId): array
    {
        $count = ApprovalStep::query()
            ->whereHas('approval', function ($query) use ($tenantId) {
                $query->where('tenant_id', $tenantId)
                    ->where('status', 'pending');
            })
            ->where('approver_id', $userId)
            ->where('status', 'pending')
            ->count();

        return [
            'id' => 'approvals',
            'label' => __('message.status_board.approvals'),
            'count' => $count,
            'path' => '/approval/inbox',
            'isHighlighted' => $count > 0,
        ];
    }
}
