import DeviceManager from "./DeviceManager";
import LinkManager from "./LinkManager";
import legitimacyCheck from "../../utils/legitimacyCheck";

var topologySample = {
  topologyKey: '',  //主键，字符串，唯一
  horizontalAxis: -1,       //x坐标,double
  verticalAxis: -1,       //y坐标,double
  topologyName: '',  //节点名称，字符串
  nodeType: -1,     //节点类型
  belongSubnet: '',   //所属子网，字符串
  status: ''    //拓扑图元状态，字符串
}

class TopologyMgrImplement {
  findTopologyByKey (topologyCollection, topologyKey) {
    return topologyCollection[topologyKey]
  }

  equalArray (a, b) {
    // 判断数组的长度
    if (a.length !== b.length) {
      return false
    } else {
      // 循环遍历数组的值进行比较
      for (let i = 0; i < a.length; i++) {
        if (JSON.stringify(a[i]) !== JSON.stringify(b[i])) {
          return false
        }
      }
      return true;
    }
  }

  //给linkList添加字段
  addFieldsToLinkList (topologyCollection,linkList) {
    for(var linkListKey in linkList){
      var e = linkList[linkListKey];
      ///采用filter过滤，返回links中startDeviceKey与node中topologyKey相等的节点作为源节点
      let sourceNode = this.topologyAsArray(topologyCollection).filter(function(n){
        if((n.elementKey !== undefined) && (n.elementKey !== null) && (n.elementKey !== '')){
          return n.elementKey === e.startDeviceKey;
        }
      })[0];
      ///采用filter过滤，返回links中endDeviceKey与node中topologyKey相等的节点作为目标节点
      let targetNode = this.topologyAsArray(topologyCollection).filter(function(n){
        if((n.elementKey !== undefined) && (n.elementKey !== null) && (n.elementKey !== '')){
          return n.elementKey === e.endDeviceKey;
        }
      })[0];
      ///根据过滤的结果对links 中的每条连接的 source 和 target 赋值
      e.source = sourceNode;
      e.target = targetNode;
    }

    return linkList
  }

  // 获取处理后的新的链路集合
  getNewLinkList(topologyCollection, linkList) {
    let linkListByPlanningDevice = {}
    let topologyMgr = TopologyManager(topologyCollection)
    let lingMgr = LinkManager(linkList)
    for (var linkKey in linkList) {
      var link = lingMgr.findLinkByKey(linkKey)
      var startDevice = topologyMgr.findTopologyByKey(link.startDeviceKey)
      var endDevice = topologyMgr.findTopologyByKey(link.endDeviceKey)
      if (typeof(startDevice) !== "undefined" && typeof(endDevice) !== "undefined") {
        linkListByPlanningDevice[linkKey] = link
      }
    }
    let linkListObject = this.addFieldsToLinkList(topologyCollection, linkListByPlanningDevice)
    linkListByPlanningDevice = this.topologyAsArray(linkListObject)
    //转换
    //新建一个二维数组
    let newLinkList = new Array();
    //外层循环1---循环整个链表
    for (var i = 0; i < linkListByPlanningDevice.length; i++) {
      //新建一个一维数组
      var subLinkList = new Array();
      var link = linkListByPlanningDevice[i];
      subLinkList.push(link);
      //内层循环1---循环整个链表
      for (var j = 0; j < linkListByPlanningDevice.length;j++) {
        //判断当前链接i 是否有兄弟链接，如果是，添加到一个一维数组里面。
        //此时兄弟链接与之同方向
        if (i != j && (link.startDeviceKey === linkListByPlanningDevice[j].startDeviceKey && link.endDeviceKey === linkListByPlanningDevice[j].endDeviceKey)) {
          subLinkList.push(linkListByPlanningDevice[j]);
        } else if (i != j && (link.startDeviceKey === linkListByPlanningDevice[j].endDeviceKey && link.endDeviceKey === linkListByPlanningDevice[j].startDeviceKey)) {
          subLinkList.push(linkListByPlanningDevice[j]);
        }
      }
      //判断二维数组是否为空，将第一个一维数组存放到二维数组里面。
      if (newLinkList.length === 0) {
        newLinkList.push(subLinkList);
      } else {
        var sameFlag = 0;
        //内层循环2---判断当前一维数组是否存在 二维数组里面。
        for (var k=0;k<newLinkList.length;k++) {
          /**
           * 使用sort给数组进行排序的时候，直接在原数组上进行排序，不会得到一个新的数组，改变了原来数组的顺序。
           * sort()，一般需要一个参数，参数是一个排序函数，可以使用现成的，也可以自己写。此处按照linkKey进行排序。
           */
          //给一维数组排序
          subLinkList.sort(function (a,b) {
            if (a.linkKey < b.linkKey) {return -1;}
            if (a.linkKey > b.linkKey) {return 1;}
          })
          //给二维数组中的一项一维数组排序
          newLinkList[k].sort(function (a,b) {
            if (a.linkKey < b.linkKey) {return -1;}
            if (a.linkKey > b.linkKey) {return 1;}
          })
          //比较排序后的两个数组，判断当前数组是否存在要加入的数组中。
          if (this.equalArray(subLinkList,newLinkList[k])) {
            sameFlag = 1;
          }
        }
        //将一维数组添加到二维数组。
        if (subLinkList.length!=0 && sameFlag === 0) {
          newLinkList.push(subLinkList);
        }
      }
    }
    return newLinkList;
  }

  handleRoutePathList (pathList, topologyCollection) {
    let newPathList = pathList
    let topologyMgr = TopologyManager(topologyCollection)
    for (var i = 0; i < pathList.length; i++) {
      let sourceTopology = topologyMgr.findTopologyByKey(pathList[i].srcDeviceId)
      let targetTopology = topologyMgr.findTopologyByKey(pathList[i].dstDeviceId)
      newPathList[i].source = sourceTopology
      newPathList[i].target = targetTopology
    }
    return newPathList
  }

  getRouteDeviceList (pathList, topologyCollection, point) {
    let routeTopologyList = []
    let topologyMgr = TopologyManager(topologyCollection)

    if (point.startDeviceId !== '') {
      let startTopology = $.extend(true, {}, topologyMgr.findTopologyByKey(point.startDeviceId))

      startTopology.routeType = '0'
      routeTopologyList.push(startTopology)
    }
    if (point.end1DeviceId !== '') {
      let end1Topology = $.extend(true, {}, topologyMgr.findTopologyByKey(point.end1DeviceId))
      if (routeTopologyList.indexOf(end1Topology) === -1) {
        end1Topology.routeType = '1'
      }
      routeTopologyList.push(end1Topology)
    }
    if (point.end2DeviceId !== '') {
      let end2Topology = $.extend(true, {}, topologyMgr.findTopologyByKey(point.end2DeviceId))
      if (routeTopologyList.indexOf(end2Topology) === -1) {
        end2Topology.routeType = '1'
      }
      routeTopologyList.push(end2Topology)
    }
    for (var i = 0; i < pathList.length; i++) {
      if (pathList[i].srcDeviceId === point.startDeviceId) {
        continue
      } else if (pathList[i].srcDeviceId === point.end1DeviceId || pathList[i].srcDeviceId === point.end2DeviceId) {
        continue
      } else if (pathList[i].srcDeviceId !== point.startDeviceId && pathList[i].srcDeviceId !== point.end1DeviceId && pathList[i].srcDeviceId !== point.end2DeviceId) {
        let topology = $.extend(true, {}, topologyMgr.findTopologyByKey(pathList[i].srcDeviceId))
        if (pathList[i].pathType === 'work') {
          topology.routeType = '2'
        } else if (pathList[i].pathType === 'protect') {
          topology.routeType = '3'
        }
        if (routeTopologyList.indexOf(topology) === -1) {
          routeTopologyList.push(topology)
        }
      }
    }
    let newRouteTopologyList = {}
    for (var j = 0; j < routeTopologyList.length; j++) {
      newRouteTopologyList[routeTopologyList[j].topologyKey] = routeTopologyList[j]
    }
    return newRouteTopologyList
  }

  // // 处理默认坐标值(0,0)
  // manageDefaultCoordinate (topologyCollection) {
  //   let coordinateX = 70
  //   let coordinateY = 70
  //   let column = 50
  //   let i = 0
  //   let j = 0
  //   for (var topologyKey in topologyCollection) {
  //     let topology = this.findTopologyByKey(topologyCollection, topologyKey)
  //     if (topology.verticalAxis === 0 && topology.horizontalAxis === 0) {
  //     // &&topology.horizontalAxis === 0
  //       topology.horizontalAxis = coordinateX * i
  //       topology.verticalAxis = coordinateY * j
  //       i++
  //       if (i === column) {
  //         j++
  //         i = 0
  //       }
  //     }
  //   }
  //   return topologyCollection
  // }

  getNewRouteLinkList (returnValue, topologyCollection) {
    var pathListWithNoRepeat = []

    //将returaValue中的pathList的内容去重
    for (var k = 0; k < returnValue.length; k++) {
      for (var i = 0, j = returnValue[k].pathList.length; i < j; i++) {
        if (pathListWithNoRepeat.indexOf(returnValue[k].pathList[i]) === -1) {
          pathListWithNoRepeat.push(returnValue[k].pathList[i])
        }
      }
    }

    //给去重后的list添加source target和bandwidth字段
    pathListWithNoRepeat = this.handleRoutePathList(pathListWithNoRepeat, topologyCollection)
    let bandwidth = 0
    let legCheck = legitimacyCheck()
    for (var n = 0; n < pathListWithNoRepeat.length; n++) {
      for (var m = 0; m < returnValue.length; m++) {
        for (var q = 0; q < returnValue[m].pathList.length; q++) {
          if (legCheck.compareObject(pathListWithNoRepeat[n], returnValue[m].pathList[q])) {
            bandwidth = bandwidth + returnValue[m].limitedBandwidth
          }
        }
        pathListWithNoRepeat[m].bandwidth = bandwidth.toString()
      }
    }

    let newReturnValue = []
    let point = []
    //寻找去重后的List有几对不同的srcDeviceId dstDeviceId
    for (var p = 0; p < pathListWithNoRepeat.length; p++) {
      let pointTest = {
        srcDeviceId: pathListWithNoRepeat[p].srcDeviceId,
        dstDeviceId: pathListWithNoRepeat[p].dstDeviceId
      }
      for (var r = 0; r <= point.length; r++) {
        if (legCheck.compareObject(point[r], pointTest)) {
          break
        } else if (r === point.length) {
          point.push(pointTest)
          break
        }
      }
    }

    //根据srcDeviceId dstDeviceId给去重后的list分组
    for (var pointTemp = 0; pointTemp < point.length; pointTemp++) {
      let partOfNewReturnValue = []
      for (var s = 0; s < pathListWithNoRepeat.length; s++) {
        if (pathListWithNoRepeat[s].srcDeviceId === point[pointTemp].srcDeviceId && pathListWithNoRepeat[s].dstDeviceId === point[pointTemp].dstDeviceId) {
          partOfNewReturnValue.push(pathListWithNoRepeat[s])
        }
      }
      newReturnValue.push(partOfNewReturnValue)
    }
    return newReturnValue
  }

  // 更新路由里的终点坐标
  updataElineRoutePathListByTopologyList (pathList, topologyList) {
    for (var i = 0; i < pathList.length; i++) {
      let sourceDevice = this.findTopologyByKey(topologyList, pathList[i].srcDeviceId)
      let targetDevice = this.findTopologyByKey(topologyList, pathList[i].dstDeviceId)

      pathList[i].source.horizontalAxis = sourceDevice.horizontalAxis
      pathList[i].source.verticalAxis = sourceDevice.verticalAxis
      pathList[i].target.horizontalAxis = targetDevice.horizontalAxis
      pathList[i].target.verticalAxis = targetDevice.verticalAxis
    }
    return pathList
  }

  topologyAsArray (topologyCollection) {
    return Object.values(topologyCollection)
  }

  // 处理topologyNode,将status字段舍弃，重新拼接字段
  handleTopologyToSave (topologyCollection) {
    let topologyNodeList = this.topologyAsArray(topologyCollection)
    var topologyNodeListStr = ''
    topologyNodeListStr += '['
    for (var i = 0; i < topologyNodeList.length; i++) {
      var topologyNodeTemp = topologyNodeList[i]
      if (topologyNodeTemp.belongSubet === undefined) {
        topologyNodeTemp.belongSubet = null
      }
      topologyNodeListStr = topologyNodeListStr + '{"topologyKey": "' + topologyNodeTemp.topologyKey + '", ' + '"elementKey": "' + topologyNodeTemp.elementKey + '", ' + '"topologyName": "' + topologyNodeTemp.topologyName + '", ' + '"nodeType": ' +
        topologyNodeTemp.nodeType + ', ' + '"belongSubnet": "' + topologyNodeTemp.belongSubet + '", ' + '"horizontalAxis": ' + topologyNodeTemp.horizontalAxis + ', ' + '"verticalAxis": ' + topologyNodeTemp.verticalAxis + ', ' +
        '"horizontalOffset": ' + topologyNodeTemp.horizontalOffset + ', ' + '"verticalOffset": ' + topologyNodeTemp.verticalOffset + '},'
    }
    // 去掉json字符串最后多加的" , "
    if(topologyNodeListStr.length !== 1){
      topologyNodeListStr = topologyNodeListStr.substring(0, topologyNodeListStr.length - 1)
    }
    topologyNodeListStr += ']'
    return topologyNodeListStr
  }
}

let implementMethods = new TopologyMgrImplement()

var staticMethods = {
  createTopologySample: function () {
    return Object.freeze(Object.assign({}, topologySample))
  }
}

function TopologyManager (topologyCollection, contextState = {}) {
  // 根据key值获取拓扑
  function findTopologyByKey (topologyKey) {
    return implementMethods.findTopologyByKey(topologyCollection, topologyKey)
  }

  // 获取处理后的新的链路集合
  function getNewLinkList (linkList) {
    return implementMethods.getNewLinkList(topologyCollection, linkList)
  }


  //根据topologyCollection向pathList添加起点和终点设备
  function handleRoutePathList (pathList) {
    return implementMethods.handleRoutePathList(pathList, topologyCollection)
  }

  //获取路由设备列表
  function getRouteDeviceList (pathList, point) {
    return implementMethods.getRouteDeviceList(pathList, topologyCollection, point)
  }

  // // 处理默认坐标值(0,0)
  // function manageDefaultCoordinate () {
  //   return implementMethods.manageDefaultCoordinate(topologyCollection)
  // }

  // 链路添加带宽和端点设备
  function getNewRouteLinkList (returnValue) {
    return implementMethods.getNewRouteLinkList(returnValue, topologyCollection)
  }

  // 根据topologyList更新路由的端点坐标
  function updataElineRoutePathListByTopologyList (pathList, topologyList) {
    return implementMethods.updataElineRoutePathListByTopologyList(pathList, topologyList)
  }

  // 将结构体转成数组
  function asArray () {
    return implementMethods.topologyAsArray(topologyCollection)
  }

  // 处理topologyNode,将status字段舍弃，重新拼接字段
  function handleTopologyToSave () {
    return implementMethods.handleTopologyToSave(topologyCollection)
  }

  return Object.freeze(Object.assign(
    {
      // 在此列出模型对象方法
      findTopologyByKey,
      getNewLinkList,
      handleRoutePathList,
      getRouteDeviceList,
      getNewRouteLinkList,
      updataElineRoutePathListByTopologyList,
      asArray,
      handleTopologyToSave,
      // manageDefaultCoordinate
    },
    staticMethods // 将静态模型方法注入到模型对象方法中
  ))
}

export default TopologyManager
