package com.boco.nbd.wios.manage.controller;

import cn.hutool.core.lang.Assert;
import cn.hutool.core.util.StrUtil;
import com.boco.nbd.cams.core.constant.CamsConstant;
import com.boco.nbd.cams.core.constant.MessageConstant;
import com.boco.nbd.wios.manage.contants.WiosConstant;
import com.boco.nbd.wios.manage.entity.bo.SingleSaveQuery2;
import com.boco.nbd.wios.manage.entity.dto.*;
import com.boco.nbd.wios.manage.service.impl.WarehouseService;
import com.boco.nbd.wios.manage.util.NumberUtil;
import com.ihidea.component.api.v2.BaseResponse;
import com.ihidea.core.support.exception.ServiceException;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.*;
import springfox.documentation.annotations.ApiIgnore;

import javax.servlet.http.HttpServletRequest;
import java.nio.charset.StandardCharsets;
import java.util.Base64;
import java.util.List;

/**
 * 仓库管理接口
 *
 * @Author 吉日木图
 * @Date 2022/6/23 16:39
 */

@RestController
@RequestMapping("api")
@Api(tags = "仓库管理接口")
@Slf4j
public class WarehouseController {

    @Value("${sap.username}")
    private String sapUsername;
    @Value("${sap.password}")
    private String sapPassword;

    @Autowired
    private WarehouseService warehouseService;


    /**
     * 添加/修改仓库
     *
     * @param entity
     * @return
     */
    @PostMapping(value = "warehouse/save")
    @ApiOperation(value = "添加/修改仓库")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "accountId", value = "账户id", dataType = "String", paramType = "query", required = false),
            @ApiImplicitParam(name = "appkey", value = "appkey", dataType = "String", paramType = "query", required = false),
            @ApiImplicitParam(name = "warehouseAttribution", value = "仓库归属 1:CAMS 2:安装服务商", dataType = "String", paramType = "query", required = true),
    })
    public BaseResponse<Void> add(WarehouseSaveQuery entity) {
        warehouseService.saveWarehouse(entity);
        return new BaseResponse<>();
    }


    /**
     * 新增/修改仓库等级
     *
     * @param warehouseLevenSaveQuery
     * @return
     */
    @PostMapping(value = "warehouselevel/save")
    @ApiOperation(value = "新增/修改仓库等级")
    public BaseResponse<Void> saveWarehouseLevel(WarehouseLevenSaveQuery warehouseLevenSaveQuery) {
        if (warehouseLevenSaveQuery.getName().length() > WiosConstant.MAX_WAREHOUSE_NAME_LENGTH) {
            throw new ServiceException("名称过长");
        }
        warehouseService.saveWarehouseLevel(warehouseLevenSaveQuery);
        return new BaseResponse<>();
    }

    /**
     * 查询仓库
     *
     * @param warehouseQuery2
     * @return
     */
    @GetMapping(value = "warehouse/all")
    @ApiOperation(value = "查询仓库")
    public BaseResponse<List<WarehouseDTO2>> qryWarehouseList(WarehouseQuery2 warehouseQuery2) {
        warehouseQuery2.setIsWarehousePage(1);
        List<WarehouseDTO2> list = warehouseService.qryWarehouseDetailList(warehouseQuery2);
        return new BaseResponse<List<WarehouseDTO2>>(list);
    }
    /**
     * 查询仓库不分页
     *
     * @param warehouseQuery2
     * @return
     */
    @GetMapping(value = "warehouse/allNoPage")
    @ApiOperation(value = "查询仓库")
    public BaseResponse<List<WarehouseDTO2>> qryWarehouseListNoPage(WarehouseQuery2 warehouseQuery2) {
        warehouseQuery2.setIsWarehousePage(2);
        List<WarehouseDTO2> list = warehouseService.qryWarehouseDetailList(warehouseQuery2);
        return new BaseResponse<List<WarehouseDTO2>>(list);
    }


    /**
     * 查询仓库等级
     *
     * @param name
     * @param serviceProvider
     * @param parentId
     * @return
     */
    @GetMapping(value = "warehouselevel/all")
    @ApiOperation(value = "查询仓库等级")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "serviceProvider", value = "服务商id", dataType = "String", paramType = "query", required = false),
            @ApiImplicitParam(name = "parentId", value = "父级id", dataType = "String", paramType = "query", required = false),
            @ApiImplicitParam(name = "name", value = "名称", dataType = "String", paramType = "query", required = false),})
    public BaseResponse<List<WarehouseLevelDTO2>> qryWarehouseLevel(String serviceProvider, Integer parentId, String name) {
        List<WarehouseLevelDTO2> list = warehouseService.qryWarehouseLevel(serviceProvider, parentId, name);
        return new BaseResponse<List<WarehouseLevelDTO2>>(list);
    }


    /**
     * 查询仓库等级详情
     *
     * @param id
     * @return
     */
    @GetMapping(value = "warehouselevel/detail")
    @ApiOperation(value = "查询仓库等级详情")
    @ApiImplicitParams({@ApiImplicitParam(name = "id", value = "主键id", dataType = "int", paramType = "query", required = false),})
    public BaseResponse<WarehouseLevenDTO> qryWarehouseLevelDetail(Integer id) {
        WarehouseLevenDTO qryLevelDetail = warehouseService.qryLevelDetail(id);
        return new BaseResponse<WarehouseLevenDTO>(qryLevelDetail);
    }


    /**
     * 新增调拨单
     *
     * @param singleSaveQuery
     * @return
     */
    @PostMapping(value = "single/save")
    @ApiOperation(value = "新增调拨单")
    public BaseResponse<Void> saveSingle(SingleSaveQuery2 singleSaveQuery) {
        warehouseService.saveSingle(singleSaveQuery);
        return new BaseResponse<Void>();
    }

    /**
     * 查询调拨单
     *
     * @param singleQuery
     * @return
     */
    @GetMapping(value = "single/all")
    @ApiOperation(value = "查询调拨单")
    public BaseResponse<List<SingleDTO>> saveSingle(SingleQuery singleQuery) {
        List<SingleDTO> list = warehouseService.qrySingal(singleQuery);
        return new BaseResponse<List<SingleDTO>>(list);
    }


    /**
     * 查询单据物料
     *
     * @param singleId
     * @param page
     * @param pagecount
     * @return
     */
    @GetMapping(value = "singleMaterials/all")
    @ApiOperation(value = "查询单据物料")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "singleId", value = "单据id", dataType = "String", paramType = "query", required = true),
            @ApiImplicitParam(name = "page", value = "页码", dataType = "int", paramType = "query", required = true),
            @ApiImplicitParam(name = "pagecount", value = "一页显示数量", dataType = "int", paramType = "query", required = true),
    })
    public BaseResponse<List<SingleMaterialsDTO>> qrySingleMaterialsBySingleId(String singleId, Integer page, Integer pagecount) {
        List<SingleMaterialsDTO> list = warehouseService.qrySingleMaterialsBySingleId(singleId, page, pagecount);
        return new BaseResponse<List<SingleMaterialsDTO>>(list);
    }


    /**
     * 新增物料
     *
     * @param materialsListQueryJson
     * @return
     */
    @PostMapping(value = "materials/add")
    @ApiOperation(value = "新增物料")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "materialsListQueryJson", value = "物料json", dataType = "String", paramType = "query", required = true),})
    public BaseResponse<Void> saveMaterials(String materialsListQueryJson) {
        Assert.notNull(materialsListQueryJson, MessageConstant.MISSING_PARAM);
        warehouseService.saveMaterials(materialsListQueryJson);
        return new BaseResponse<>();
    }

    @PostMapping(value = "sap/materials/add")
    @ApiOperation(value = "SAP新增物料")
    public BaseResponse<Void> sapSaveMaterials(@RequestBody MaterialsSaveQuery materialsSaveQuery, HttpServletRequest request) {
        String authorization = request.getHeader("authorization");
        if (StrUtil.isBlank(authorization)) {
            throw new ServiceException(403, "权限不足");
        }
        byte[] encode = Base64.getEncoder().encode((sapUsername + ":" + sapPassword).getBytes(StandardCharsets.UTF_8));
        if (!authorization.equals(WiosConstant.AUTHORIZATION_FLAG + new String(encode))) {
            throw new ServiceException(403, "权限不足");
        }

        Assert.notNull(materialsSaveQuery.getMaterialsCode(), "缺少物料编码");
        Assert.notNull(materialsSaveQuery.getMaterialsName(), "缺少物料名称");
        Assert.notNull(materialsSaveQuery.getRegularModel(), "缺少规则型号");
        Assert.notNull(materialsSaveQuery.getUnit(), "缺少单位");
        Assert.notNull(materialsSaveQuery.getType(), "缺少类别");
        warehouseService.saveMaterials(materialsSaveQuery);
        return new BaseResponse<>();
    }

    /**
     * 更新物料
     *
     * @param materialsSaveQuery
     * @return
     */
    @PostMapping(value = "materials/update")
    @ApiOperation(value = "更新物料")
    public BaseResponse<Void> saveMaterials(MaterialsSaveQuery materialsSaveQuery) {
        Assert.notNull(materialsSaveQuery.getId(), MessageConstant.MISSING_PARAM);
        warehouseService.updateMaterial(materialsSaveQuery);
        return new BaseResponse<>();
    }

    /**
     * 查询物料
     *
     * @param materialsQuery
     * @return
     */
    @GetMapping(value = "materials/all")
    @ApiOperation(value = "查询物料")
    public BaseResponse<List<MaterialsDTO>> qryMaterials(MaterialsQuery materialsQuery) {
        List<MaterialsDTO> list = warehouseService.qryMaterials(materialsQuery);
        return new BaseResponse<>(list);
    }

    /**
     * 删除物料
     *
     * @param materialsId
     * @return
     */
    @PostMapping(value = "materials/delete")
    @ApiOperation(value = "删除物料物料")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "materialsId", value = "物料id", dataType = "String", paramType = "query", required = true),
    })
    public BaseResponse<Void> delMaterials(String materialsId) {
        Assert.notNull(materialsId, MessageConstant.MISSING_PARAM);
        warehouseService.delMaterials(materialsId);
        return new BaseResponse<>();
    }

    /**
     * 删除仓库
     *
     * @param id
     * @return
     */
    @PostMapping(value = "warehouse/delById")
    @ApiOperation(value = "删除仓库")
    @ApiImplicitParams({@ApiImplicitParam(name = "id", value = "仓库id", dataType = "String", paramType = "query", required = true),})
    public BaseResponse<Void> delWarehouseById(String id) {
        Assert.notNull(id,MessageConstant.MISSING_PARAM);
        warehouseService.delWarehouseById(id);
        return new BaseResponse<>();
    }

    /**
     * 删除仓库等级
     *
     * @param id
     * @return
     */
    @PostMapping(value = "warehouselevel/delById")
    @ApiOperation(value = "删除仓库等级")
    @ApiImplicitParams({@ApiImplicitParam(name = "id", value = "仓库等级id", dataType = "int", paramType = "query", required = true),})
    public BaseResponse<Void> delWarehouseById(Integer id) {
        Assert.notNull(id, MessageConstant.MISSING_PARAM);
        warehouseService.delWarehouseLevelById(id);
        return new BaseResponse<>();
    }

    /**
     * 仓库启用/禁用
     *
     * @param id
     * @param enable
     * @return
     */
    @PostMapping(value = "warehouse/updateEnable")
    @ApiOperation(value = "仓库启用/禁用")
    @ApiImplicitParams({@ApiImplicitParam(name = "id", value = "仓库id", dataType = "String", paramType = "query", required = true),
            @ApiImplicitParam(name = "enable", value = "0:禁用 1:启用", dataType = "int", paramType = "query", required = true),})
    public BaseResponse<Void> delWarehouseById(String id, Integer enable) {
        Assert.notNull(id, MessageConstant.MISSING_PARAM);
        Assert.notNull(enable, MessageConstant.MISSING_PARAM);
        warehouseService.updateEnable(id, enable);
        return new BaseResponse<>();
    }

    /**
     * 组装查询数据
     *
     * @param id
     * @return
     */
    @GetMapping(value = "warehouse/combineSelectorData")
    @ApiOperation(value = "组装查询数据")
    @ApiImplicitParams({@ApiImplicitParam(name = "id", value = "仓库等级id", dataType = "int", paramType = "query", required = false),
            @ApiImplicitParam(name = "type", value = "类型 1:只显示总仓", dataType = "int", paramType = "query", required = false),})
    public BaseResponse<List<WarehouseSelectorData>> combineSelectorData(Integer id, Integer type) {
        List<WarehouseSelectorData> list = warehouseService.combineSelectorData(id, type);
        return new BaseResponse<List<WarehouseSelectorData>>(list);
    }

    /**
     * 查询库存物料
     *
     * @param materialsQuery
     * @return
     */
    @GetMapping(value = "materials/stock/all")
    @ApiOperation(value = "查询库存物料")
    public BaseResponse<List<MaterialsDTO>> qryStockMaterials(MaterialsQuery materialsQuery) {
        List<MaterialsDTO> list = warehouseService.qryStockMaterials(materialsQuery);
        // id唯一 给前端用的
        for (MaterialsDTO dto : list) {
            dto.setId(dto.getId() + CamsConstant.UNDER_LINE + NumberUtil.getRandomNumbers(5));
        }
        return new BaseResponse<List<MaterialsDTO>>(list);
    }


}