package com.ghy.web.controller.worker;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.ghy.common.core.controller.BaseController;
import com.ghy.common.core.domain.AjaxResult;
import com.ghy.common.core.page.TableDataInfo;
import com.ghy.common.enums.GoodsStatus;
import com.ghy.common.enums.WorkerStatus;
import com.ghy.common.enums.WorkerType;
import com.ghy.common.utils.CacheUtils;
import com.ghy.common.utils.ExceptionUtil;
import com.ghy.common.utils.StringUtils;
import com.ghy.goods.domain.Goods;
import com.ghy.goods.domain.GoodsCategory;
import com.ghy.goods.service.GoodsCategoryService;
import com.ghy.goods.service.GoodsService;
import com.ghy.system.domain.SysArea;
import com.ghy.system.service.ISysAreaService;
import com.ghy.web.pojo.vo.WorkerListRequest;
import com.ghy.web.pojo.vo.WorkerListResponse;
import com.ghy.web.pojo.vo.WorkerSettledRequest;
import com.ghy.worker.domain.Worker;
import com.ghy.worker.domain.WorkerArea;
import com.ghy.worker.domain.WorkerBank;
import com.ghy.worker.domain.WorkerGoodsCategory;
import com.ghy.worker.service.*;
import com.github.pagehelper.PageInfo;
import org.apache.commons.collections.CollectionUtils;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.apache.shiro.util.Assert;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @author clunt
 * 师傅端Controller
 */
@Controller
@RequestMapping("/worker")
public class WorkerController extends BaseController {

    private String prefix = "worker";

    @Autowired
    private WorkerService workerService;

    @Autowired
    private WorkerAreaService workerAreaService;

    @Autowired
    private WorkerGoodsCategoryService workerGoodsCategoryService;

    @Autowired
    private WorkerSpecialSkillService specialSkillService;

    @Autowired
    private GoodsService goodsService;

    @Autowired
    private GoodsCategoryService goodsCategoryService;

    @Autowired
    private WorkerBankService workerBankService;

    @Autowired
    private ISysAreaService sysAreaService;

    @RequiresPermissions("worker:worker:view")
    @GetMapping()
    public String worker(){
        return prefix + "/worker";
    }

    @PostMapping("/login")
    @ResponseBody
    public AjaxResult login(@RequestBody Worker worker){
        try {
            Assert.notNull(worker.getPhone(), "手机号码为空");
            List<Worker> workerList = workerService.getWorkByPhoneAndPwd(worker);
            if(workerList.size() > 0){
                Worker loginWorker = workerList.get(0);
                // 检查师傅状态：0=生效,1=冻结,2=删除
                if(loginWorker.getStatus() == WorkerStatus.DELETED.getCode()){
                    return AjaxResult.error("账户已被删除，无法登录!");
                }
                // 检查登录状态：0=允许登录,1=禁止登录
                if(loginWorker.getLoginStatus() != null && loginWorker.getLoginStatus() == 1){
                    return AjaxResult.error("账户登录已被禁用，无法登录!");
                }
                return AjaxResult.success(loginWorker);
            }else {
                return AjaxResult.error("用户名或密码错误!");
            }
        }catch (Exception e){
            e.printStackTrace();
            logger.error(ExceptionUtil.getExceptionMessage(e));
            return AjaxResult.error("登陆失败!");
        }
    }

    @PostMapping("/register")
    @ResponseBody
    public AjaxResult register(@RequestBody Worker request){
        try {
            logger.info("注册师傅信息:{}", request);
            if (CacheUtils.get(request.getPhone()) == null){
                return AjaxResult.error("验证码无效!");
            }
            // 验证码校验正确
            if(CacheUtils.get(request.getPhone()).toString().equals(request.getRegisterCode())){
                logger.info("验证码信息:{}", CacheUtils.get(request.getPhone()));
                int result = workerService.updateWorker(request);
                if(result > 0){
                    CacheUtils.remove(request.getPhone());
                    return AjaxResult.success("注册成功!");
                }else {
                    return AjaxResult.error("注册失败!");
                }
            }else {
                return AjaxResult.error("验证码错误!");
            }
        }catch (Exception e){
            e.printStackTrace();
            logger.error(ExceptionUtil.getExceptionMessage(e));
            return AjaxResult.error(e.getMessage());
        }
    }

//    @RequiresPermissions("worker:worker:list")
    @PostMapping("/list")
    @ResponseBody
    public TableDataInfo list(WorkerListRequest workerListRequest)
    {
        List<WorkerListResponse> resList = new ArrayList<WorkerListResponse>();

        try {
            // 查询满足区域条件的师傅区域记录
            List<Long> workerIdsByArea = new ArrayList<>();
            if(workerListRequest.getAreaId() != null){
                WorkerArea workerArea = new WorkerArea();
                workerArea.setDistrictId(workerListRequest.getAreaId());
                // 如果有省市区的查询条件,需要构建完整的区域查询条件
                boolean flag = StringUtils.isNotEmpty(workerListRequest.getDistrictId()) || StringUtils.isNotEmpty(workerListRequest.getProvinceId())
                        || StringUtils.isNotEmpty(workerListRequest.getCityId()) || StringUtils.isNotEmpty(workerListRequest.getStreetId());
                if(flag){
                    workerArea.setDistrictId(null);
                }
                if(StringUtils.isNotEmpty(workerListRequest.getDistrictId())){
                    workerArea.setDistrictId(Long.valueOf(workerListRequest.getDistrictId()));
                }
                if(StringUtils.isNotEmpty(workerListRequest.getProvinceId())) {
                    workerArea.setProvinceId(Long.valueOf(workerListRequest.getProvinceId()));
                }
                if(StringUtils.isNotEmpty(workerListRequest.getCityId())) {
                    workerArea.setCityId(Long.valueOf(workerListRequest.getCityId()));
                }
                if(StringUtils.isNotEmpty(workerListRequest.getStreetId())) {
                    workerArea.setStreetId(Long.valueOf(workerListRequest.getStreetId()));
                }
                List<WorkerArea> workerAreaList = workerAreaService.getWorkerAreaList(workerArea);
                workerIdsByArea = workerAreaList.stream()
                    .map(WorkerArea::getWorkerId)
                    .collect(Collectors.toList());
            }

            // 查询满足技能条件的师傅技能记录
            List<Long> workerIdsByCategory = new ArrayList<>();
            WorkerGoodsCategory workerGoodsCategory = new WorkerGoodsCategory();
            if(workerListRequest.getGoodsCategoryId() != null){
                workerGoodsCategory.setGoodsCategoryId(workerListRequest.getGoodsCategoryId());
            }
            // 如果选择了上级类目但未选择最终类目,则查询该类目下所有子类目
            if(StringUtils.isNotEmpty(workerListRequest.getCategoryLevel1())
                    && StringUtils.isEmpty(workerListRequest.getCategoryLevel2()) && workerListRequest.getGoodsCategoryId() == null) {
                // 1. 先查找二级类目
                GoodsCategory param = new GoodsCategory();
                param.setParentCategoryId(Long.valueOf(workerListRequest.getCategoryLevel1()));
                List<GoodsCategory> secondCategories = goodsCategoryService.selectGoodsCategoryList(param);

                // 2. 用二级类目查找三级类目
                List<String> categoryIds = new ArrayList<>();
                for (GoodsCategory secondCategory : secondCategories) {
                    param.setParentCategoryId(secondCategory.getGoodsCategoryId());
                    List<GoodsCategory> thirdCategories = goodsCategoryService.selectGoodsCategoryList(param);
                    categoryIds.addAll(thirdCategories.stream()
                            .map(x->x.getGoodsCategoryId().toString())
                            .collect(Collectors.toList()));
                }
                workerGoodsCategory.setCategoryIds(categoryIds);
            }
            // 如果选择了二级类目但未选择三级类目
            else if(StringUtils.isNotEmpty(workerListRequest.getCategoryLevel2())
                    && workerListRequest.getGoodsCategoryId() == null) {
                GoodsCategory param = new GoodsCategory();
                param.setParentCategoryId(Long.valueOf(workerListRequest.getCategoryLevel2()));
                List<GoodsCategory> subCategories = goodsCategoryService.selectGoodsCategoryList(param);
                List<String> categoryIds = subCategories.stream()
                        .map(x->x.getGoodsCategoryId().toString())
                        .collect(Collectors.toList());
                workerGoodsCategory.setCategoryIds(categoryIds);
            }
            if(CollectionUtils.isNotEmpty(workerGoodsCategory.getCategoryIds()) || workerGoodsCategory.getGoodsCategoryId() != null){
                List<WorkerGoodsCategory> workerGoodsCategoryList = workerGoodsCategoryService.getWorkerGoodsCategory(workerGoodsCategory);
                workerIdsByCategory = workerGoodsCategoryList.stream()
                        .map(WorkerGoodsCategory::getWorkerId)
                        .collect(Collectors.toList());
            }

            // 两个list中的workerid取交集
            List<Long> resWorkerIds = new ArrayList<>();
            if(!workerIdsByArea.isEmpty() && !workerIdsByCategory.isEmpty()) {
                resWorkerIds.addAll(CollectionUtils.intersection(workerIdsByArea, workerIdsByCategory));
            } else if(!workerIdsByArea.isEmpty()) {
                resWorkerIds.addAll(workerIdsByArea);
            } else if(!workerIdsByCategory.isEmpty()) {
                resWorkerIds.addAll(workerIdsByCategory);
            }

            if (!resWorkerIds.isEmpty() || 
                workerListRequest.getAreaId() != null || 
                workerListRequest.getGoodsCategoryId() != null) {
                // 有查询条件但无匹配结果时直接返回空列表
                if(resWorkerIds.isEmpty()) {
                    return getDataTable(resList);
                }
            }

            startPage();
            Worker worker = new Worker();
            worker.setWorkerIds(CollectionUtils.isNotEmpty(resWorkerIds) ? resWorkerIds : null);
            worker.setKeyWords(workerListRequest.getWorkerName());
            if(StringUtils.isNotEmpty(workerListRequest.getWorkerPhone())){
                worker.setPhone(workerListRequest.getWorkerPhone());
            }
            if(this.getSysUser().getDept().getParentId() != 101){
                worker.setDeptId(this.getSysUser().getDept().getParentId());
            }
            List<Worker> list = workerService.getWorkList(worker);
            TableDataInfo dataTable = getDataTable(list);
            list.forEach(w -> {
                Goods goods = new Goods();
                goods.setWorkerId(w.getWorkerId());
                goods.setStatus(Integer.valueOf(GoodsStatus.OK.getCode()));
                WorkerListResponse workerListResponse = JSONObject.parseObject(JSON.toJSONString(w), WorkerListResponse.class);
                workerListResponse.setGoodsList(goodsService.selectGoodsList(goods));
                workerListResponse.setWorkerAreas(workerAreaService.getByWorker(w.getWorkerId()));
                workerListResponse.setGoodsCategories(workerGoodsCategoryService.getByWorker(w.getWorkerId()));
                workerListResponse.setSpecialSkills(specialSkillService.getByWorker(w.getWorkerId()));
                resList.add(workerListResponse);

            });
            TableDataInfo rspData = new TableDataInfo();
            rspData.setCode(0);
            rspData.setRows(resList);
            rspData.setTotal(dataTable.getTotal());
            return rspData;
        } catch (Exception e) {
            e.printStackTrace();
            logger.error(ExceptionUtil.getExceptionMessage(e));
            return getDataTable(new ArrayList<>());
        }
    }

    @PostMapping("/app/list")
    @ResponseBody
    public TableDataInfo appList(@RequestBody WorkerListRequest workerListRequest)
    {
        List<WorkerListResponse> resList = new ArrayList<WorkerListResponse>();
        // 查询参数
        Worker worker = new Worker();

        try {
            // 查询满足区域条件的师傅区域记录
            worker.setDistrictId(workerListRequest.getAreaId());
            worker.setDistrictIds(workerListRequest.getAreaIds());
            // 查询需要排除的区
            if (workerListRequest.getExceptParentAreaId() != null) {
                SysArea areaParams = new SysArea();
                areaParams.setParentCode(workerListRequest.getExceptParentAreaId().toString());
                List<SysArea> exceptAreaList = sysAreaService.selectSysAreaList(areaParams);
                List<Long> exceptAreaIds = exceptAreaList.stream().map(SysArea::getAreaId).collect(Collectors.toList());
                worker.setExceptDistrictIds(exceptAreaIds);
            }
//            WorkerArea workerArea = new WorkerArea();
//            workerArea.setDistrictId(workerListRequest.getAreaId());
//            List<WorkerArea> workerAreaList = workerAreaService.getWorkerAreaList(workerArea);
//            List<Long> workerIdsByArea = workerAreaList.stream().map(WorkerArea::getWorkerId).collect(Collectors.toList());
            // 查询满足技能条件的师傅技能记录
//            WorkerGoodsCategory workerGoodsCategory = new WorkerGoodsCategory();
            // 判断类目id是否为第三级，不是的话需要找到所有符合条件的第三级类目id作为新的条件
            if (workerListRequest.getGoodsCategoryId() != null) {
                GoodsCategory goodsCategory = goodsCategoryService.selectById(workerListRequest.getGoodsCategoryId());
                if (goodsCategory.getLevel() == 0) {
                    worker.setGoodsCategoryId(null);
                } else if (goodsCategory.getLevel() == 1) {
                    GoodsCategory params = new GoodsCategory();
                    params.setParentCategoryId(goodsCategory.getGoodsCategoryId());
                    List<GoodsCategory> secondCategories = goodsCategoryService.selectGoodsCategoryList(params);
                    List<Long> secondCategoryIds = secondCategories.stream().map(GoodsCategory::getGoodsCategoryId).collect(Collectors.toList());
                    List<Long> thirdCategoryIds = new ArrayList<Long>();
                    secondCategoryIds.forEach(id -> {
                        params.setParentCategoryId(id);
                        List<GoodsCategory> thirdCategories = goodsCategoryService.selectGoodsCategoryList(params);
                        thirdCategoryIds.addAll(thirdCategories.stream().map(GoodsCategory::getGoodsCategoryId).collect(Collectors.toList()));
                    });
                    worker.setGoodsCategoryId(null);
                    worker.setGoodsCategoryIds(thirdCategoryIds);
                } else if (goodsCategory.getLevel() == 2) {
                    GoodsCategory params = new GoodsCategory();
                    params.setParentCategoryId(goodsCategory.getGoodsCategoryId());
                    List<GoodsCategory> filteredCategory = goodsCategoryService.selectGoodsCategoryList(params);
                    List<Long> filteredCategoryIds = filteredCategory.stream().map(GoodsCategory::getGoodsCategoryId).collect(Collectors.toList());
                    worker.setGoodsCategoryId(null);
                    worker.setGoodsCategoryIds(filteredCategoryIds);
                } else {
                    worker.setGoodsCategoryId(workerListRequest.getGoodsCategoryId());
                }
            }
//            List<WorkerGoodsCategory> workerGoodsCategoryList = workerGoodsCategoryService.getWorkerGoodsCategory(workerGoodsCategory);
//            List<Long> workerIdsByCategory = workerGoodsCategoryList.stream().map(WorkerGoodsCategory::getWorkerId).collect(Collectors.toList());
            // 两个list中的workerid取交集
//            List<Long> resWorkerIds = new ArrayList<>(CollectionUtils.intersection(workerIdsByArea, workerIdsByCategory));

//            if (CollectionUtils.isEmpty(resWorkerIds)) {
//                // 交集不存在的情况直接返回空list
//                return getDataTable(resList);
//            }

            startPage();
//            worker.setWorkerIds(CollectionUtils.isNotEmpty(resWorkerIds) ? resWorkerIds : null);
            worker.setName(workerListRequest.getWorkerName());
            worker.setStatus(0);
            List<Worker> list = workerService.getWorkList(worker);
            list.forEach(w -> {
                Goods goods = new Goods();
                goods.setWorkerId(w.getWorkerId());
                goods.setStatus(Integer.valueOf(GoodsStatus.OK.getCode()));
                WorkerListResponse workerListResponse = JSONObject.parseObject(JSON.toJSONString(w), WorkerListResponse.class);
                workerListResponse.setGoodsList(goodsService.selectGoodsList(goods));
                if (workerListRequest.isJustShowCurWorkerArea()) {
                    workerListResponse.setWorkerAreas(workerAreaService.getWorkerAreaList(new WorkerArea(){{
                        setWorkerId(w.getWorkerId());
                        setDistrictId(worker.getDistrictId());
                        setDistrictIds(worker.getDistrictIds());
                    }}));
                } else {
                    List<WorkerArea> workerAreas = workerAreaService.getByWorker(w.getWorkerId());
                    if(workerAreas.size() > 10){
                        workerListResponse.setWorkerAreas(workerAreas.subList(0,10));
                    }else {
                        workerListResponse.setWorkerAreas(workerAreas);
                    }
                }
                workerListResponse.setGoodsCategories(workerGoodsCategoryService.getByWorker(w.getWorkerId()));
                workerListResponse.setSpecialSkills(specialSkillService.getByWorker(w.getWorkerId()));
                resList.add(workerListResponse);
            });
        } catch (Exception e) {
            e.printStackTrace();
            logger.error(ExceptionUtil.getExceptionMessage(e));
        }

        return getDataTable(resList);
    }

    @PostMapping("/getDetailById")
    @ResponseBody
    public AjaxResult getDetailById(@RequestBody WorkerListRequest workerListRequest)
    {
        WorkerListResponse workerListResponse = new WorkerListResponse();

        try {
            Assert.notNull(workerListRequest.getWorkerId(), "Worker id can not be null");

            Worker worker = workerService.selectById(workerListRequest.getWorkerId());
            Goods goods = new Goods();
            goods.setWorkerId(workerListRequest.getWorkerId());
            goods.setStatus(Integer.valueOf(GoodsStatus.OK.getCode()));
            workerListResponse = JSONObject.parseObject(JSON.toJSONString(worker), WorkerListResponse.class);
            workerListResponse.setGoodsList(goodsService.selectGoodsList(goods));
            workerListResponse.setWorkerAreas(workerAreaService.getByWorker(worker.getWorkerId()));
            workerListResponse.setGoodsCategories(workerGoodsCategoryService.getByWorker(worker.getWorkerId()));
            workerListResponse.setSpecialSkills(specialSkillService.getByWorker(worker.getWorkerId()));
        } catch (Exception e) {
            e.printStackTrace();
            logger.error(ExceptionUtil.getExceptionMessage(e));
            return AjaxResult.error(e.getMessage());
        }

        return AjaxResult.success(workerListResponse);
    }

    @PostMapping("/update")
    @ResponseBody
    public AjaxResult updateWorker(@RequestBody Worker worker){
        try {
            workerService.updateWorker(worker);
            return AjaxResult.success("修改成功");
        }catch (Exception e){
            logger.error(ExceptionUtil.getExceptionMessage(e));
            return AjaxResult.error(e.getMessage());
        }
    }

    @PostMapping("/changeStatus")
    @ResponseBody
    public AjaxResult changeStatus(Worker worker){
        try {
            workerService.updateWorker(worker);
            return AjaxResult.success("修改成功");
        }catch (Exception e){
            logger.error(ExceptionUtil.getExceptionMessage(e));
            return AjaxResult.error(e.getMessage());
        }
    }

    @PostMapping("/changeLoginStatus")
    @ResponseBody
    public AjaxResult changeLoginStatus(Worker worker){
        try {
            workerService.updateWorker(worker);
            return AjaxResult.success("登录状态修改成功");
        }catch (Exception e){
            logger.error(ExceptionUtil.getExceptionMessage(e));
            return AjaxResult.error(e.getMessage());
        }
    }

    @PostMapping("/settled")
    @ResponseBody
    @Transactional(rollbackFor = Exception.class)
    public  AjaxResult settled(@RequestBody WorkerSettledRequest request) {
        // 入驻服务区域信息持久化（类型1）
        workerAreaService.updateWorkerAreaByType(request.getWorkerId(), request.getWorkerAreas(), 1);
        
        // 入驻商品区域信息持久化（类型2）
        workerAreaService.updateWorkerAreaByType(request.getWorkerId(), request.getWorkerGoodsAreas(), 2);
        
        // 入驻服务类目信息持久化（类型1）
        if (request.getServiceCategories() != null && !request.getServiceCategories().isEmpty()) {
            // 使用对象数组方式
            workerGoodsCategoryService.updateWorkerGoodsCategoryByType(request.getWorkerId(), request.getServiceCategories(), 1);
        } else if (request.getServiceCategoryIds() != null && !request.getServiceCategoryIds().isEmpty()) {
            // 使用ID数组方式（兼容旧版本）
            List<WorkerGoodsCategory> serviceCategories = request.getServiceCategoryIds().stream()
                .map(id -> {
                    WorkerGoodsCategory category = new WorkerGoodsCategory();
                    category.setGoodsCategoryId(id);
                    return category;
                }).collect(Collectors.toList());
            workerGoodsCategoryService.updateWorkerGoodsCategoryByType(request.getWorkerId(), serviceCategories, 1);
        }
        
        // 入驻商品类目信息持久化（类型2）
        if (request.getGoodsCategories() != null && !request.getGoodsCategories().isEmpty()) {
            // 使用对象数组方式
            workerGoodsCategoryService.updateWorkerGoodsCategoryByType(request.getWorkerId(), request.getGoodsCategories(), 2);
        } else if (request.getGoodsCategoryIds() != null && !request.getGoodsCategoryIds().isEmpty()) {
            // 使用ID数组方式（兼容旧版本）
            List<WorkerGoodsCategory> goodsCategories = request.getGoodsCategoryIds().stream()
                .map(id -> {
                    WorkerGoodsCategory category = new WorkerGoodsCategory();
                    category.setGoodsCategoryId(id);
                    return category;
                }).collect(Collectors.toList());
            workerGoodsCategoryService.updateWorkerGoodsCategoryByType(request.getWorkerId(), goodsCategories, 2);
        }
        
        // 更新师傅入驻类型为服务商
        Worker worker = new Worker();
        worker.setWorkerId(request.getWorkerId());
        worker.setType(WorkerType.SP.getCode());
        workerService.updateWorker(worker);
        
        return AjaxResult.success("保存成功");
    }

    /**
     * 通过师傅ID获取师傅详情
     * @param workerId 师傅ID
     * @return 师傅实体对象
     */
    @GetMapping("/detail/{workerId}")
    @ResponseBody
    public AjaxResult getWorkerDetailById(@PathVariable("workerId") Long workerId) {
        try {
            // 参数校验
            if (workerId == null) {
                return AjaxResult.error("师傅ID不能为空");
            }

            // 查询师傅基本信息
            Worker worker = workerService.selectById(workerId);
            if (worker == null) {
                return AjaxResult.error("师傅不存在");
            }

            return AjaxResult.success(worker);
        } catch (Exception e) {
            logger.error("获取师傅详情失败: " + ExceptionUtil.getExceptionMessage(e));
            return AjaxResult.error("获取师傅详情失败: " + e.getMessage());
        }
    }

    /**
     * 删除师傅（软删除）
     */
    @RequiresPermissions("worker:worker:remove")
    @PostMapping("/remove")
    @ResponseBody
    public AjaxResult remove(String ids) {
        try {
            return toAjax(workerService.deleteWorkerByIds(ids));
        } catch (Exception e) {
            logger.error(ExceptionUtil.getExceptionMessage(e));
            return AjaxResult.error("删除失败: " + e.getMessage());
        }
    }
}
