//
//  OrderAPI.swift
//  suixinkan
//

import Foundation

@MainActor
/// 订单模块 API，对齐 Android `NetworkApi` 订单区域。
final class OrderAPI {
    private let client: APIClient

    init(client: APIClient) {
        self.client = client
    }

    func photographerOrderList(
        scenicId: Int,
        page: Int,
        pageSize: Int = OrderListQueryBuilder.photographerPageSize,
        orderStatus: Int = 0,
        startTime: String? = nil,
        endTime: String? = nil,
        userPhone: String? = nil,
        isRefined: Int = 0
    ) async throws -> OrderListResponse<OrderEntity> {
        var items: [URLQueryItem] = [
            URLQueryItem(name: "scenic_id", value: String(scenicId)),
            URLQueryItem(name: "page", value: String(page)),
            URLQueryItem(name: "page_size", value: String(pageSize)),
        ]
        if let orderStatus = OrderListQueryBuilder.orderStatusQuery(tabIndex: orderStatus) {
            items.append(URLQueryItem(name: "order_status", value: orderStatus))
        }
        if let startTime, !startTime.isEmpty { items.append(URLQueryItem(name: "start_time", value: startTime)) }
        if let endTime, !endTime.isEmpty { items.append(URLQueryItem(name: "end_time", value: endTime)) }
        if let userPhone, !userPhone.isEmpty { items.append(URLQueryItem(name: "user_phone", value: userPhone)) }
        if let isRefined = OrderListQueryBuilder.isRefinedQuery(rTabIndex: isRefined) {
            items.append(URLQueryItem(name: "is_refined", value: String(isRefined)))
        }
        return try await client.send(
            APIRequest(method: .get, path: "/api/yf-handset-app/photog/order/listv2", queryItems: items)
        )
    }

    func scenicAdminOrderList(
        scenicId: Int,
        page: Int,
        pageSize: Int = OrderListQueryBuilder.photographerPageSize,
        orderStatus: Int = 0,
        startTime: String? = nil,
        endTime: String? = nil,
        userPhone: String? = nil,
        isRefined: Int = 0
    ) async throws -> OrderListResponse<OrderEntity> {
        var items: [URLQueryItem] = [
            URLQueryItem(name: "scenic_id", value: String(scenicId)),
            URLQueryItem(name: "page", value: String(page)),
            URLQueryItem(name: "page_size", value: String(pageSize)),
        ]
        if let orderStatus = OrderListQueryBuilder.orderStatusQuery(tabIndex: orderStatus) {
            items.append(URLQueryItem(name: "order_status", value: orderStatus))
        }
        if let startTime, !startTime.isEmpty { items.append(URLQueryItem(name: "start_time", value: startTime)) }
        if let endTime, !endTime.isEmpty { items.append(URLQueryItem(name: "end_time", value: endTime)) }
        if let userPhone, !userPhone.isEmpty { items.append(URLQueryItem(name: "user_phone", value: userPhone)) }
        if let isRefined = OrderListQueryBuilder.isRefinedQuery(rTabIndex: isRefined) {
            items.append(URLQueryItem(name: "is_refined", value: String(isRefined)))
        }
        return try await client.send(
            APIRequest(method: .get, path: "/api/app/scenic-admin/order/list", queryItems: items)
        )
    }

    func storeOrderList(
        storeId: Int?,
        page: Int,
        pageSize: Int = OrderListQueryBuilder.storePageSize,
        userPhone: String? = nil,
        orderStatus: Int? = nil,
        orderType: Int? = nil,
        startTime: String? = nil,
        endTime: String? = nil
    ) async throws -> StoreOrderListData {
        var items: [URLQueryItem] = [
            URLQueryItem(name: "page", value: String(page)),
            URLQueryItem(name: "page_size", value: String(pageSize)),
        ]
        if let storeId { items.append(URLQueryItem(name: "store_id", value: String(storeId))) }
        if let userPhone, !userPhone.isEmpty { items.append(URLQueryItem(name: "user_phone", value: userPhone)) }
        if let orderStatus { items.append(URLQueryItem(name: "order_status", value: String(orderStatus))) }
        if let orderType { items.append(URLQueryItem(name: "order_type", value: String(orderType))) }
        if let startTime, !startTime.isEmpty { items.append(URLQueryItem(name: "start_time", value: startTime)) }
        if let endTime, !endTime.isEmpty { items.append(URLQueryItem(name: "end_time", value: endTime)) }
        return try await client.send(
            APIRequest(method: .get, path: "/api/app/store/order/list", queryItems: items)
        )
    }

    func orderCheckIn(jsonBody: String) async throws -> OrderSignInResponse {
        try await client.sendRawJSON(
            method: .post,
            path: "/api/yf-handset-app/photog/order/check-in",
            jsonBody: jsonBody
        )
    }

    func orderVerify(jsonBody: String) async throws -> WriteOffOrderResponse {
        try await client.sendRawJSON(
            method: .post,
            path: "/api/yf-handset-app/photog/order/order-verify",
            jsonBody: jsonBody
        )
    }

    func multiTravelScenicSpotList(orderNumber: String, lat: Double, lng: Double) async throws -> MultiTravelScenicSpotListResponse {
        try await client.send(
            APIRequest(
                method: .get,
                path: "/api/yf-handset-app/photog/order/multi-travel/scenic-spot-list",
                queryItems: [
                    URLQueryItem(name: "order_number", value: orderNumber),
                    URLQueryItem(name: "lat", value: String(lat)),
                    URLQueryItem(name: "lng", value: String(lng)),
                ]
            )
        )
    }

    func multiTravelOrderVerify(_ request: MultiTravelOrderVerifyRequest) async throws -> OrderSignInResponse {
        try await client.send(
            APIRequest(
                method: .post,
                path: "/api/yf-handset-app/photog/order/multi-travel/order-verify",
                body: request
            )
        )
    }

    func cancelOrder(_ request: CancelRequest) async throws {
        let _: EmptyPayload = try await client.send(
            APIRequest(method: .post, path: "/api/yf-handset-app/photog/order/cancel", body: request)
        )
    }

    func refundOrder(_ request: OrderRefundRequest) async throws {
        let _: EmptyPayload = try await client.send(
            APIRequest(method: .post, path: "/api/yf-handset-app/photog/order/refund", body: request)
        )
    }

    func giftRetouch(_ request: SendGiftRequest) async throws {
        let _: EmptyPayload = try await client.send(
            APIRequest(method: .post, path: "/api/yf-handset-app/photog/order/gift-retouch", body: request)
        )
    }

    func updateRefined(orderNumber: String, isRefined: Int) async throws {
        let _: EmptyPayload = try await client.send(
            APIRequest(
                method: .post,
                path: "/api/yf-handset-app/photog/order/refined",
                queryItems: [
                    URLQueryItem(name: "order_number", value: orderNumber),
                    URLQueryItem(name: "is_refined", value: String(isRefined)),
                ]
            )
        )
    }

    func cooperativeSalers(storeId: String?, page: String = "1", pageSize: String = "50") async throws -> CooperativeSalerListResponse {
        var items = [
            URLQueryItem(name: "page", value: page),
            URLQueryItem(name: "page_size", value: pageSize),
        ]
        if let storeId { items.append(URLQueryItem(name: "store_id", value: storeId)) }
        return try await client.send(
            APIRequest(method: .get, path: "/api/yf-handset-app/photog/cooperative-salers", queryItems: items)
        )
    }

    func referralOrders(saleUserId: String, page: String = "1", pageSize: String = "50") async throws -> ReferralOrderListResponse {
        try await client.send(
            APIRequest(
                method: .get,
                path: "/api/yf-handset-app/photog/sale-user/referral-orders",
                queryItems: [
                    URLQueryItem(name: "sale_user_id", value: saleUserId),
                    URLQueryItem(name: "page", value: page),
                    URLQueryItem(name: "page_size", value: pageSize),
                ]
            )
        )
    }

    func bindReferralOrder(orderNumber: String, referralOrderNo: String) async throws {
        let _: EmptyPayload = try await client.send(
            APIRequest(
                method: .post,
                path: "/api/yf-handset-app/photog/sale-user/bind-referral-order",
                queryItems: [
                    URLQueryItem(name: "order_number", value: orderNumber),
                    URLQueryItem(name: "referral_order_no", value: referralOrderNo),
                ]
            )
        )
    }

    func referralLeads(page: String = "1", pageSize: String = "10") async throws -> OrderListResponse<ReferralLeadEntity> {
        try await client.send(
            APIRequest(
                method: .get,
                path: "/api/yf-handset-app/photog/sale-user/referral-leads",
                queryItems: [
                    URLQueryItem(name: "page", value: page),
                    URLQueryItem(name: "page_size", value: pageSize),
                ]
            )
        )
    }

    func acquisitionOrders(keyword: String? = nil, page: String = "1", pageSize: String = "10") async throws -> OrderListResponse<AcquisitionOrderEntity> {
        var items = [
            URLQueryItem(name: "page", value: page),
            URLQueryItem(name: "page_size", value: pageSize),
        ]
        if let keyword, !keyword.isEmpty {
            items.append(URLQueryItem(name: "keyword", value: keyword))
        }
        return try await client.send(
            APIRequest(
                method: .get,
                path: "/api/yf-handset-app/photog/sale-user/acquisition-orders",
                queryItems: items
            )
        )
    }

    func saleUserInviteInfo(saleUserId: String) async throws -> SaleUserInviteInfoResponse {
        try await client.send(
            APIRequest(
                method: .get,
                path: "/api/yf-handset-app/photog/sale-user/invite-info",
                queryItems: [URLQueryItem(name: "sale_user_id", value: saleUserId)]
            )
        )
    }

    func saleUserAcceptBind(saleUserId: Int, commissionRate: Int) async throws {
        let _: EmptyPayload = try await client.send(
            APIRequest(
                method: .post,
                path: "/api/yf-handset-app/photog/sale-user/accept-bind",
                queryItems: [
                    URLQueryItem(name: "sale_user_id", value: String(saleUserId)),
                    URLQueryItem(name: "commission_rate", value: String(commissionRate)),
                ]
            )
        )
    }

    func saleUserUpdateRemark(saleUserId: Int, photogRemarkName: String) async throws {
        let _: EmptyPayload = try await client.send(
            APIRequest(
                method: .post,
                path: "/api/yf-handset-app/photog/sale-user/update-remark",
                body: SaleUserUpdateRemarkRequest(saleUserId: saleUserId, photogRemarkName: photogRemarkName)
            )
        )
    }

    func saleUserCommissionRateSendSmsCode(phone: String) async throws {
        let _: EmptyPayload = try await client.send(
            APIRequest(
                method: .post,
                path: "/api/yf-handset-app/photog/sale-user/commission-rate/send-sms-code",
                body: SaleUserCommissionRateSmsRequest(phone: phone)
            )
        )
    }

    func saleUserUpdateCommissionRate(saleUserId: Int, commissionRate: Int, smsCode: String) async throws -> CooperativeSalerEntity {
        try await client.send(
            APIRequest(
                method: .post,
                path: "/api/yf-handset-app/photog/sale-user/commission-rate",
                body: SaleUserCommissionRateUpdateRequest(
                    saleUserId: saleUserId,
                    commissionRate: commissionRate,
                    smsCode: smsCode
                )
            )
        )
    }

    /// 获取指定获客员的分成比例修改记录。
    func saleUserCommissionRateLogs(
        saleUserId: Int,
        page: Int = 1,
        pageSize: Int = 10
    ) async throws -> CommissionRateLogListResponse {
        guard saleUserId > 0 else {
            throw APIError.networkFailed("获客员信息无效")
        }
        return try await client.send(
            APIRequest(
                method: .get,
                path: "/api/yf-handset-app/photog/sale-user/commission-rate/logs",
                queryItems: [
                    URLQueryItem(name: "sale_user_id", value: String(saleUserId)),
                    URLQueryItem(name: "page", value: String(max(1, page))),
                    URLQueryItem(name: "page_size", value: String(min(max(1, pageSize), 50))),
                ]
            )
        )
    }

    func shootHistory(orderNumber: String) async throws -> MultiTravelShootHistoryResponse {
        try await client.send(
            APIRequest(
                method: .get,
                path: "/api/yf-handset-app/photog/order/multi-travel/shoot-history",
                queryItems: [URLQueryItem(name: "order_number", value: orderNumber)]
            )
        )
    }

    func storeOrderVerify(_ request: StoreOrderVerifyRequest) async throws -> WriteOffOrderResponse {
        try await client.send(
            APIRequest(method: .post, path: "/api/app/store/order/order-verify", body: request)
        )
    }

    func storeOrderRefund(_ request: StoreOrderRefundRequest) async throws {
        let _: EmptyPayload = try await client.send(
            APIRequest(method: .post, path: "/api/app/store/order/refund", body: request)
        )
    }

    func storeOrderDetail(storeId: Int, orderNumber: String) async throws -> StoreOrderDetailData {
        try await client.send(
            APIRequest(
                method: .get,
                path: "/api/app/store/order/detail",
                queryItems: [
                    URLQueryItem(name: "store_id", value: String(storeId)),
                    URLQueryItem(name: "order_number", value: orderNumber),
                ]
            )
        )
    }
}
