package com.imdroid.beidou.controller;

import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.imdroid.beidou.common.HttpResult;
import com.imdroid.secapi.client.HttpResp;
import com.imdroid.secapi.client.RtcmClient;
import com.imdroid.secapi.dto.*;
import com.imdroid.secapi.utils.HexUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpSession;
import java.text.SimpleDateFormat;
import java.time.LocalDateTime;
import java.util.HashMap;

@Controller
public class CmdLineController extends BasicController{
    SimpleDateFormat dateFormat = new SimpleDateFormat("yy-MM-dd HH:mm:ss");
    @Autowired
    RtcmClient rtcmClient;
    @Autowired
    GnssMsgMapper msgMapper;
    @Autowired
    DeviceCmdMapper deviceCmdMapper;
    @Autowired
    DeviceCacheCmdMapper cacheCmdMapper;

    /**** 推送页面  *****/
    @RequestMapping("/page/cmd_line")
    public String gnssDevCfg(Model m, HttpSession session) {
        initModel(m, session);

        return "/page/cmd_line";
    }

    @RequestMapping("/page/table/frequent_cmd")
    public String frequentCmd(Model m, HttpSession session) {
        initModel(m, session);

        return "/page/table/frequent_cmd";
    }

    @RequestMapping("/page/table/q_cache_cmd")
    public String queryCacheCmd(Model m, HttpSession session) {
        initModel(m, session);

        return "/page/table/q_cache_cmd";
    }

    /****** 发送指令 *******/
    @PostMapping(value = "/gnss/config_cmd")
    @ResponseBody
    public HttpResult configCmd(HttpSession session,
            @RequestParam("tx_win") String cmd,
                            @RequestParam("device_id") String deviceId,
                            @RequestParam("cmd_type") int cmdType) {
        String sendCmd = cmd.replaceAll(" +","");
        short len = 0;
        int msgType;
        if(cmdType == 1){ // DTU,string format
            msgType = 0xD31A;
            len = (short) (sendCmd.length() + 5);
            sendCmd = "D31A"+ HexUtil.Short2HexString(len)+
                    HexUtil.Int2HexString(Integer.parseInt(deviceId))+
                    "01"+HexUtil.String2HexString(sendCmd);
        }
        else{ //hex format
            msgType = 0xD310+cmdType;
            len = (short) (sendCmd.length()/2+4);
            sendCmd = Integer.toHexString(msgType) + HexUtil.Short2HexString(len)+
                    HexUtil.Int2HexString(Integer.parseInt(deviceId))+sendCmd;
        }
        HttpResp<HashMap<String, Object>> rsp = rtcmClient.config(deviceId,sendCmd);

        String txInfo = "TX "+ dateFormat.format(System.currentTimeMillis())+
                " "+deviceId+" "+sendCmd;
        if(cmdType == 1) txInfo += "("+cmd+")";
        if(rsp.getCode() != HttpResp.HTTP_RSP_OK){
            txInfo += "\r\n" + rsp.getResponseMessage();
        }

        // 保存
        GnssMsg gnssMsg = new GnssMsg();
        gnssMsg.setTenantid(getTenantId(session));
        gnssMsg.setCreatetime(LocalDateTime.now());
        gnssMsg.setDeviceid(deviceId);
        gnssMsg.setMsgtype(msgType);
        gnssMsg.setMsglen((int) len);
        gnssMsg.setTx(true);
        if(cmd.length() >= 100) {
            cmd = cmd.substring(0, 100)+"...";
        }
        gnssMsg.setContent(cmd);
        msgMapper.insert(gnssMsg);

        return HttpResult.success(txInfo);
    }

    @PostMapping(value = "/gnss/cache_cmd")
    @ResponseBody
    public HttpResult cacheCmd(HttpSession session,
                                @RequestParam("tx_win") String cmd,
                                @RequestParam("device_id") String deviceId,
                                @RequestParam("cmd_type") int cmdType) {
        String sendCmd = cmd.replaceAll(" +","");
        short len = 0;
        int msgType;
        if(cmdType == 1){ // DTU,string format
            msgType = 0xD31A;
            len = (short) (sendCmd.length() + 5);
            sendCmd = "D31A"+ HexUtil.Short2HexString(len)+
                    HexUtil.Int2HexString(Integer.parseInt(deviceId))+
                    "01"+HexUtil.String2HexString(sendCmd);
        }
        else{ //hex format
            msgType = 0xD310+cmdType;
            len = (short) (sendCmd.length()/2+4);
            sendCmd = Integer.toHexString(msgType) + HexUtil.Short2HexString(len)+
                    HexUtil.Int2HexString(Integer.parseInt(deviceId))+sendCmd;
        }

        // 保存
        if(sendCmd.length() >= DeviceCacheCmd.MAX_CMD_LEN) {
            return HttpResult.fail("指令过长，不能超过325字节");
        }
        DeviceCacheCmd cacheCmd = new DeviceCacheCmd();
        cacheCmd.setDeviceid(deviceId);
        cacheCmd.setUpdatetime(LocalDateTime.now());
        cacheCmd.setType((short) cmdType);
        cacheCmd.setSyn(false);
        cacheCmd.setCmd(sendCmd);
        cacheCmd.setMsgtype(msgType);
        cacheCmdMapper.insert(cacheCmd);

        return HttpResult.success("OK");
    }

    @RequestMapping("/gnss/cmd/list")
    @ResponseBody
    public JSONObject listCmd(int page, int limit) {
        Page<DeviceCmd> pageable = new Page<>(page, limit);
        IPage<DeviceCmd> cs = deviceCmdMapper.selectPage(pageable, null);

        JSONObject jsonObject = new JSONObject();
        jsonObject.put("code", 0);
        jsonObject.put("msg", "");
        jsonObject.put("count", cs.getTotal());
        jsonObject.put("data", cs.getRecords());
        return jsonObject;
    }

    @RequestMapping("/gnss/cache_cmd/list")
    @ResponseBody
    public JSONObject listCacheCmd(int page, int limit) {
        Page<DeviceCacheCmd> pageable = new Page<>(page, limit);
        IPage<DeviceCacheCmd> cs = cacheCmdMapper.selectPage(pageable, null);

        JSONObject jsonObject = new JSONObject();
        jsonObject.put("code", 0);
        jsonObject.put("msg", "");
        jsonObject.put("count", cs.getTotal());
        jsonObject.put("data", cs.getRecords());
        return jsonObject;
    }

    @PostMapping("/gnss/cmd/add")
    @ResponseBody
    public String addCmd(@RequestBody JSONObject object) throws Exception {
        DeviceCmd deviceCmd = JSONObject.toJavaObject(object,DeviceCmd.class);
        int num = deviceCmdMapper.insert(deviceCmd);

        if (num == 0) {
            return HttpResult.failed();
        } else{
            return HttpResult.ok();
        }
    }

    @PostMapping("/gnss/cmd/delete")
    @ResponseBody
    public String deleteCmd(@RequestParam int del_id) throws Exception {
        int num = deviceCmdMapper.deleteById(del_id);
        if (num == 0) {
            return HttpResult.failed();
        } else return HttpResult.ok();
    }

    @PostMapping("/gnss/cache_cmd/delete")
    @ResponseBody
    public String deleteCacheCmd(@RequestParam int del_id) throws Exception {
        int num = cacheCmdMapper.deleteById(del_id);
        if (num == 0) {
            return HttpResult.failed();
        } else return HttpResult.ok();
    }
}
