package com.yc.ship.module.otc.controller.admin.store;

import com.yc.ship.framework.common.pojo.CommonResult;
import com.yc.ship.framework.common.pojo.PageParam;
import com.yc.ship.framework.common.pojo.PageResult;
import com.yc.ship.framework.common.util.object.BeanUtils;
import com.yc.ship.framework.excel.core.util.ExcelUtils;
import com.yc.ship.framework.operatelog.core.annotations.OperateLog;
import com.yc.ship.framework.tenant.core.aop.TenantIgnore;
import com.yc.ship.module.ota.api.OtaDistributorApi;
import com.yc.ship.module.ota.api.dto.DistributorRespDTO;
import com.yc.ship.module.otc.controller.admin.store.machine.SellerMachineRespVO;
import com.yc.ship.module.otc.controller.admin.store.machine.StoreMachineRespVO;
import com.yc.ship.module.otc.controller.admin.store.machineproduct.StoreMachineProductRespVO;
import com.yc.ship.module.otc.controller.admin.store.product.StoreProductRespVO;
import com.yc.ship.module.otc.controller.admin.store.user.StoreUserRespVO;
import com.yc.ship.module.otc.controller.admin.store.user.StoreUserSimpleRespVO;
import com.yc.ship.module.otc.controller.admin.store.vo.*;
import com.yc.ship.module.otc.controller.admin.storecard.vo.StoreCardRespVO;
import com.yc.ship.module.otc.convert.store.StoreProductConvert;
import com.yc.ship.module.otc.convert.store.StoreUserConvert;
import com.yc.ship.module.otc.dal.dataobject.store.*;
import com.yc.ship.module.otc.dal.dataobject.storecard.StoreCardDO;
import com.yc.ship.module.otc.enums.UseStatusEnum;
import com.yc.ship.module.otc.service.store.StoreService;
import com.yc.ship.module.otc.service.storecard.StoreCardService;
import com.yc.ship.module.system.api.user.AdminUserApi;
import com.yc.ship.module.system.api.user.dto.AdminUserRespDTO;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.apache.commons.lang3.StringUtils;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletResponse;
import javax.validation.Valid;
import java.io.IOException;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

import static com.yc.ship.framework.common.pojo.CommonResult.success;
import static com.yc.ship.framework.common.util.collection.CollectionUtils.convertList;
import static com.yc.ship.framework.operatelog.core.enums.OperateTypeEnum.EXPORT;

@Tag(name = "管理后台 - 旅行社门店")
@RestController
@RequestMapping("/otc/store")
@Validated
public class StoreController {

    @Resource
    private StoreService storeService;

    @Resource
    private StoreCardService storeCardService;

    @Resource
    private AdminUserApi adminUserApi;

    @Resource
    private OtaDistributorApi otaDistributorApi;

//    @Resource
//    private ProductApi productApi;

    @PostMapping("/create")
    @Operation(summary = "创建旅行社门店")
    @PreAuthorize("@ss.hasPermission('otc:store:create')")
    public CommonResult<Long> createStore(@Valid @RequestBody StoreSaveReqVO createReqVO) {
        return success(storeService.createStore(createReqVO));
    }

    @PutMapping("/update")
    @Operation(summary = "更新旅行社门店")
    @PreAuthorize("@ss.hasPermission('otc:store:update')")
    public CommonResult<Boolean> updateStore(@Valid @RequestBody StoreSaveReqVO updateReqVO) {
        storeService.updateStore(updateReqVO);
        return success(true);
    }

    @DeleteMapping("/delete")
    @Operation(summary = "删除旅行社门店")
    @Parameter(name = "id", description = "编号", required = true)
    @PreAuthorize("@ss.hasPermission('otc:store:delete')")
    public CommonResult<Boolean> deleteStore(@RequestParam("id") Long id) {
        storeService.deleteStore(id);
        return success(true);
    }

    @PostMapping("/audit")
    @Operation(summary = "门店审核")
//    @PreAuthorize("@ss.hasPermission('otc:store:audit')")
    public CommonResult<Long> auditStore(@Valid @RequestBody StoreAuditReqVO auditReqVO) {
        return success(storeService.auditStore(auditReqVO));
    }

    @GetMapping("/get")
    @Operation(summary = "获得旅行社门店")
    @Parameter(name = "id", description = "编号", required = true, example = "1024")
//    @PreAuthorize("@ss.hasPermission('otc:store:query')")
    public CommonResult<StoreRespVO> getStore(@RequestParam("id") Long id) {
        StoreDO store = storeService.getStore(id);
        StoreCardDO storeCardDO = storeCardService.getStoreCardByStoreId(id);
        StoreRespVO respVO = BeanUtils.toBean(store, StoreRespVO.class);
        respVO.setBalance(storeCardDO.getBalance());
        respVO.setBalanceType(storeCardDO.getBalanceType());
        respVO.setCreditType(storeCardDO.getCreditType());
        respVO.setCredit(storeCardDO.getCredit());
        StoreCardRespVO cardRespVO = BeanUtils.toBean(storeCardDO, StoreCardRespVO.class);
        respVO.setCardRespVO(cardRespVO);
        DistributorRespDTO distributor = otaDistributorApi.getDistributorById(store.getAgencyId());
        respVO.setAgencyName(distributor.getName());
        return success(respVO);
    }

    @GetMapping("/audit/get")
    @Operation(summary = "获得旅行社门店")
    @Parameter(name = "id", description = "编号", required = true, example = "1024")
    @TenantIgnore
//    @PreAuthorize("@ss.hasPermission('otc:store:query')")
    public CommonResult<StoreRespVO> getAuditStore(@RequestParam("id") Long id) {
        return getStore(id);
    }

    @GetMapping("/page")
    @Operation(summary = "获得旅行社门店分页")
//    @PreAuthorize("@ss.hasPermission('otc:store:query')")
    public CommonResult<PageResult<StoreRespVO>> getStorePage(@Valid StorePageReqVO pageReqVO) {
        PageResult<StoreDO> pageResult = storeService.getStorePage(pageReqVO);
        return success(BeanUtils.toBean(pageResult, StoreRespVO.class));
    }

    @GetMapping("/audit/page")
    @Operation(summary = "获得待审核旅行社门店分页")
//    @PreAuthorize("@ss.hasPermission('otc:store:query')")
    public CommonResult<PageResult<StoreRespVO>> getAuditStorePage(@Valid StoreAuditPageReqVO pageReqVO) {
        PageResult<StoreRespVO> pageResult = storeService.getAuditStorePage(pageReqVO);
        return success(pageResult);
    }

    @GetMapping("/export-excel")
    @Operation(summary = "导出旅行社门店 Excel")
    @PreAuthorize("@ss.hasPermission('otc:store:export')")
    @OperateLog(type = EXPORT,enable = false)
    public void exportStoreExcel(@Valid StorePageReqVO pageReqVO,
                                 HttpServletResponse response) throws IOException {
        pageReqVO.setPageSize(PageParam.PAGE_SIZE_NONE);
        List<StoreDO> list = storeService.getStorePage(pageReqVO).getList();
        // 导出 Excel
        ExcelUtils.write(response, "旅行社门店.xls", "数据", StoreRespVO.class,
                BeanUtils.toBean(list, StoreRespVO.class));
    }

    @PutMapping("/update-status")
    @Operation(summary = "修改用户状态")
    @PreAuthorize("@ss.hasPermission('otc:store:update')")
    public CommonResult<Boolean> updateStoreStatus(@Valid @RequestBody StoreSaveReqVO reqVO) {
        storeService.updateStoreStatus(reqVO.getId(), reqVO.getIsUse());
        return success(true);
    }

    @GetMapping({"/list-all-simple", "/simple-list"})
    @Operation(summary = "获取门店精简信息列表", description = "只包含被开启的门店，主要用于前端的下拉选项")
    public CommonResult<List<StoreSimpleRespVO>> getSimpleStoreList() {
        List<StoreDO> list = storeService.getStoreListByStatus(UseStatusEnum.ENABLE.getStatus());
        return success(BeanUtils.toBean(list, StoreSimpleRespVO.class));
    }

    @GetMapping({"/list-all-simple-new", "/simple-list-new"})
    @Operation(summary = "获取门店精简信息列表", description = "只包含被开启的门店，主要用于前端的下拉选项")
    public CommonResult<List<StoreSimpleRespVO>> getSimpleStoreListNew(StoreSimpleReqVO reqVO) {
        reqVO.setStatus(UseStatusEnum.ENABLE.getStatus());
        List<StoreDO> list = storeService.getStoreList(reqVO);
        return success(BeanUtils.toBean(list, StoreSimpleRespVO.class));
    }

    @GetMapping("/list-by-distributor")
    @Parameter(name = "distributorId", description = "旅行社id", required = true)
    @Operation(summary = "通过旅行社获取门店精简信息列表", description = "只包含被开启的门店，主要用于前端的下拉选项")
    public CommonResult<List<StoreSimpleRespVO>> getStoreListByDistributor(@RequestParam("distributorId") Long distributorId) {
        List<StoreDO> list = storeService.getStoreListByDistributor(distributorId);
        return success(BeanUtils.toBean(list, StoreSimpleRespVO.class));
    }

    // ==================== 子表（关联设备） ====================

    @GetMapping("/store-machine/page")
    @Operation(summary = "获得关联设备分页")
    @Parameter(name = "storeId", description = "门店ID")
//    @PreAuthorize("@ss.hasPermission('otc:store:query')")
    public CommonResult<PageResult<StoreMachineDO>> getStoreMachinePage(PageParam pageReqVO, @RequestParam("storeId") Long storeId) {
        return success(storeService.getStoreMachinePage(pageReqVO, storeId));
    }

    @PostMapping("/store-machine/create")
    @Operation(summary = "创建关联设备")
    @PreAuthorize("@ss.hasPermission('otc:store:create')")
    public CommonResult<Long> createStoreMachine(@Valid @RequestBody StoreMachineDO storeMachine) {
        return success(storeService.createStoreMachine(storeMachine));
    }

    @PutMapping("/store-machine/update")
    @Operation(summary = "更新关联设备")
    @PreAuthorize("@ss.hasPermission('otc:store:update')")
    public CommonResult<Boolean> updateStoreMachine(@Valid @RequestBody StoreMachineDO storeMachine) {
        storeService.updateStoreMachine(storeMachine);
        return success(true);
    }

    @DeleteMapping("/store-machine/delete")
    @Parameter(name = "id", description = "编号", required = true)
    @Operation(summary = "删除关联设备")
    @PreAuthorize("@ss.hasPermission('otc:store:delete')")
    public CommonResult<Boolean> deleteStoreMachine(@RequestParam("id") Long id) {
        storeService.deleteStoreMachine(id);
        return success(true);
    }

    @GetMapping("/store-machine/get")
    @Operation(summary = "获得关联设备")
    @Parameter(name = "id", description = "编号", required = true)
//    @PreAuthorize("@ss.hasPermission('otc:store:query')")
    public CommonResult<StoreMachineDO> getStoreMachine(@RequestParam("id") Long id) {
        return success(storeService.getStoreMachine(id));
    }

    @GetMapping({"/store-machine/list-all-simple", "/store-machine/simple-list"})
    @Operation(summary = "获取设备精简信息列表", description = "只包含被启用的设备，主要用于前端的下拉选项")
    public CommonResult<List<StoreMachineRespVO>> getSimpleSiteList(@RequestParam("machineType") String machineTypeStr) {
        Integer machineType = StringUtils.isBlank(machineTypeStr) ? null : Integer.parseInt(machineTypeStr);
        List<StoreMachineDO> list = storeService.getStoreMachineListByStatus(machineType);
        return success(BeanUtils.toBean(list, StoreMachineRespVO.class));
    }

    @GetMapping("/store-machine/seller-machine")
    @Operation(summary = "获得销售员关联设备")
    public CommonResult<List<SellerMachineRespVO>> getSellerMachine() {
        return success(storeService.getSellerMachine());
    }

    // ==================== 子表（门店账号关联） ====================

    @GetMapping("/store-user/page")
    @Operation(summary = "获得门店账号关联分页")
    @Parameter(name = "storeId", description = "门店ID")
//    @PreAuthorize("@ss.hasPermission('otc:store:query')")
    public CommonResult<PageResult<StoreUserRespVO>> getStoreUserPage(PageParam pageReqVO, @RequestParam("storeId") Long storeId) {
        PageResult<StoreUserDO> pageResult = storeService.getStoreUserPage(pageReqVO, storeId);
        Map<Long, AdminUserRespDTO> userMap = adminUserApi.getUserMap(
                convertList(pageResult.getList(), StoreUserDO::getUserId).stream().distinct().collect(Collectors.toList()));
        return success(new PageResult<>(StoreUserConvert.INSTANCE.convertList(pageResult.getList(), userMap),
                pageResult.getTotal()));
    }

    @PostMapping("/store-user/create")
    @Operation(summary = "创建门店账号关联")
    @PreAuthorize("@ss.hasPermission('otc:store:create')")
    public CommonResult<Long> createStoreUser(@Valid @RequestBody StoreUserDO storeUser) {
        return success(storeService.createStoreUser(storeUser));
    }

    @PutMapping("/store-user/update")
    @Operation(summary = "更新门店账号关联")
    @PreAuthorize("@ss.hasPermission('otc:store:update')")
    public CommonResult<Boolean> updateStoreUser(@Valid @RequestBody StoreUserDO storeUser) {
        storeService.updateStoreUser(storeUser);
        return success(true);
    }

    @DeleteMapping("/store-user/delete")
    @Parameter(name = "id", description = "编号", required = true)
    @Operation(summary = "删除门店账号关联")
    @PreAuthorize("@ss.hasPermission('otc:store:delete')")
    public CommonResult<Boolean> deleteStoreUser(@RequestParam("id") Long id,@RequestParam("storeId") Long storeId) {
        storeService.deleteStoreUserByUserId(id,storeId);
        return success(true);
    }


    @GetMapping("/store-user/get")
    @Operation(summary = "获得门店账号关联")
    @Parameter(name = "id", description = "编号", required = true)
    @PreAuthorize("@ss.hasPermission('otc:store:query')")
    public CommonResult<List<StoreUserDO>> getStoreUser(@RequestParam("storeId") Long storeId) {
        return success(storeService.getStoreUser(storeId));
    }

    @GetMapping({"/store-user/list-all-simple", "/store-user/simple-list"})
    @Operation(summary = "获取旅行社下所有门店账号精简信息列表", description = "只包含被开启的门店，主要用于前端的下拉选项")
    public CommonResult<List<StoreUserSimpleRespVO>> getSimpleStoreUserList() {
        List<StoreUserDO> list = storeService.getStoreUserList(0, null);
        Map<Long, AdminUserRespDTO> userMap = adminUserApi.getUserMap(
                convertList(list, StoreUserDO::getUserId).stream().distinct().collect(Collectors.toList()));
        List<StoreUserRespVO> respVOS = StoreUserConvert.INSTANCE.convertList(list, userMap);
        return success(BeanUtils.toBean(respVOS, StoreUserSimpleRespVO.class));
    }

// ==================== 子表（门店产品关联） ====================

//    @GetMapping("/store-product/page")
//    @Operation(summary = "获得门店产品关联分页")
//    @Parameter(name = "storeId", description = "门店ID")
//    @PreAuthorize("@ss.hasPermission('otc:store:query')")
//    public CommonResult<PageResult<StoreProductRespVO>> getStoreProductPage(PageParam pageReqVO, @RequestParam("storeId") Long storeId) {
//        PageResult<StoreProductDO> pageResult = storeService.getStoreProductPage(pageReqVO, storeId);
//        Map<Long, ProductSpuRespDTO> productMap = productApi.getProductMap(
//                convertList(pageResult.getList(), StoreProductDO::getProductId));
//        return success(new PageResult<>(StoreProductConvert.INSTANCE.convertList(pageResult.getList(), productMap),
//                pageResult.getTotal()));
//    }

    @PostMapping("/store-product/create")
    @Operation(summary = "创建门店产品关联")
    @PreAuthorize("@ss.hasPermission('otc:store:create')")
    public CommonResult<Long> createStoreProduct(@Valid @RequestBody StoreProductDO storeProduct) {
        return success(storeService.createStoreProduct(storeProduct));
    }

    @PutMapping("/store-product/update")
    @Operation(summary = "更新门店产品关联")
    @PreAuthorize("@ss.hasPermission('otc:store:update')")
    public CommonResult<Boolean> updateStoreProduct(@Valid @RequestBody StoreProductDO storeProduct) {
        storeService.updateStoreProduct(storeProduct);
        return success(true);
    }

    @DeleteMapping("/store-product/delete")
    @Parameter(name = "id", description = "编号", required = true)
    @Operation(summary = "删除门店产品关联")
    @PreAuthorize("@ss.hasPermission('otc:store:delete')")
    public CommonResult<Boolean> deleteStoreProduct(@RequestParam("id") Long id) {
        storeService.deleteStoreProduct(id);
        return success(true);
    }

//    @GetMapping("/store-product/get")
//    @Operation(summary = "获得门店产品关联")
//    @Parameter(name = "storeId", description = "编号", required = true)
//    @PreAuthorize("@ss.hasPermission('otc:store:query')")
//    public CommonResult<List<StoreProductRespVO>> getStoreProduct(@RequestParam("storeId") Long storeId) {
//        List<StoreProductRespVO> productRespVOS = productApi.storeProductlist(storeId).getData();
//        return success(BeanUtils.toBean(productRespVOS, StoreProductRespVO.class));
//    }

    // ==================== 子表（门店设备产品关联） ====================

    @PostMapping("/store-machine-product/create")
    @Operation(summary = "创建门店设备关联")
    @PreAuthorize("@ss.hasPermission('otc:store:create')")
    public CommonResult<Long> createAgencyStoreMachineProduct(@Valid @RequestBody StoreMachineProductDO storeMachineProduct) {
        return success(storeService.createStoreMachineProduct(storeMachineProduct));
    }

    @PutMapping("/store-machine-product/update")
    @Operation(summary = "更新门店设备关联")
    @PreAuthorize("@ss.hasPermission('otc:store:update')")
    public CommonResult<Boolean> updateAgencyStoreMachineProduct(@Valid @RequestBody StoreMachineProductDO storeMachineProduct) {
        storeService.updateStoreMachineProduct(storeMachineProduct);
        return success(true);
    }

    @DeleteMapping("/store-machine-product/delete")
    @Operation(summary = "删除门店设备关联")
    @Parameter(name = "id", description = "编号", required = true)
    @PreAuthorize("@ss.hasPermission('otc:store:delete')")
    public CommonResult<Boolean> deleteAgencyStoreMachineProduct(@RequestParam("id") Long id) {
        storeService.deleteStoreMachineProduct(id);
        return success(true);
    }

    @GetMapping("/store-machine-product/get")
    @Operation(summary = "获得门店设备关联")
    @Parameter(name = "storeId", description = "编号", required = true, example = "1024")
    @PreAuthorize("@ss.hasPermission('otc:store:query')")
    public CommonResult<List<StoreMachineProductRespVO>> getAgencyStoreMachineProduct(@RequestParam("storeId") Long storeId, @RequestParam("machineId") Long machineId) {
        List<StoreMachineProductDO> list = storeService.getStoreMachineProduct(storeId, machineId);
        return success(BeanUtils.toBean(list, StoreMachineProductRespVO.class));
    }

    @PostMapping("/change-plat-credit")
    @Operation(summary = "变更平台授信额度")
    public CommonResult<Long> changePlatCredit(@Valid @RequestBody StorePlatCreditSaveReqVO reqVO) {
        return success(storeService.changePlatCredit(reqVO));
    }

    @GetMapping("/queryStoreCreditAndBalance")
    @Parameter(name = "whetherShow", description = "当门店授信和预付款为共享时是否显示旅行社的余额（1-是，0-否）")
    @Operation(summary = "查询门店授信和预付款余额")
    public CommonResult<?> queryStoreCreditAndBalance(@RequestParam("whetherShow") Integer whetherShow){
        return success(storeService.queryStoreCreditAndBalance(whetherShow));
    }
}
