import WebSocketService from '@/domain/services/WebSocketService.js'
import { WebSocket, Server } from 'mock-socket'
import DeviceStateSocketApi from '@/api/websocketApis/DeviceStateSocketApi'
import Vue from "vue";
import {WS_ADD,WS_ADD_SUCCESS,
  WS_MODIFY_INIT,WS_MODIFY,WS_MODIFY_SUCCESS,
  WS_DELETE_INIT,WS_DELETE,WS_DELETE_SUCCESS,
  PANIC_MSG} from "../../../../mock/websocket/wsSubnetServiceMock";

describe('SubnetWebSocketService', () => {
  const fakeURL = 'ws://localhost:8080'
  var mockServer = null
  var websocketSvc = null

  before(function () {
    // 设置WebSocket为mock-socket提供的WebSocket，以便能够使用假数据测试
    global.WebSocket = WebSocket
  })

  after(function () {
    // 恢复WebSocket为jsdom提供的WebSocket对象
    global.WebSocket = window.WebSocket
  })

  beforeEach(function () {
    mockServer = new Server(fakeURL)
    mockServer.on('connection', function (socket) {
      console.log('server connected')
      socket.on('message', function (data) {
        let msg = JSON.parse(data)
        console.log('server try to respond to', msg)
        if (msg === '0') {
          socket.send(JSON.stringify(WS_ADD))
          console.log('server is sending message:', WS_ADD)
        } else if(msg === '1'){
          socket.send(JSON.stringify(WS_DELETE))
          console.log('server is sending message:', WS_DELETE)
        }else if(msg === '2'){
          socket.send(JSON.stringify(WS_MODIFY))
          console.log('server is sending message:', WS_MODIFY)
        }else {
          socket.send(JSON.stringify(PANIC_MSG))
          console.log('server is panic')
        }
      })
    })
    websocketSvc = WebSocketService(DeviceStateSocketApi, {URL: fakeURL})
  })

  it('should open', function (done) {
    const WAIT_FINISH_TIME = 100
    const WAIT_SOCKE_OPEN_TIME = 50

    websocketSvc.open()
    expect(websocketSvc.isConnecting()).to.be.true

    setTimeout(() => {
      expect(websocketSvc.isOpen()).to.be.true
    }, WAIT_SOCKE_OPEN_TIME)

    // 延迟结束本测试
    setTimeout(() => {
      mockServer.stop(done)
    }, WAIT_FINISH_TIME)
  })

  it('should AddSubnet', function (done) {
    const WAIT_FINISH_TIME = 100
    const WAIT_RECEIVE_MSG_TIME = 50

    // subscribe message bark
    let barkMessages = {}
    websocketSvc.subscribe(DeviceStateSocketApi.MsgType.ADD_SUBNET, barkMessages, (returnObject) => {
      Vue.set(barkMessages,returnObject.subnetKey,returnObject);
    });

    // socket打开时发送消息
    websocketSvc.subscribeToOpen(this, function () {
      websocketSvc.send('0')
    })

    // open the socket and send bark to receive bark message
    websocketSvc.open()

    setTimeout(() => {
      // expect(barkMessages).to.have.lengthOf(1)
      // console.log('client received message: ', barkMessages[0])
      expect(barkMessages).to.deep.equal(WS_ADD_SUCCESS)
    }, WAIT_RECEIVE_MSG_TIME)

    // 延迟结束本测试
    setTimeout(() => {
      mockServer.stop(done)
    }, WAIT_FINISH_TIME)
  })

  it('should DeleteSubnet', function (done) {
    const WAIT_FINISH_TIME = 100
    const WAIT_RECEIVE_MSG_TIME = 50

    // subscribe message bark
    let barkMessages = WS_DELETE_INIT
    websocketSvc.subscribe(DeviceStateSocketApi.MsgType.DELETE_SUBNET, barkMessages, (returnObject) => {
      for(let i = 0;i<returnObject.length;i++){
        let subnetkey = returnObject[i];
        Vue.delete(barkMessages,subnetkey);
      }
    });

    // socket打开时发送消息
    websocketSvc.subscribeToOpen(this, function () {
      websocketSvc.send('1')
    })

    // open the socket and send bark to receive bark message
    websocketSvc.open()

    setTimeout(() => {
      // expect(barkMessages).to.have.lengthOf(1)
      // console.log('client received message: ', barkMessages[0])
      expect(barkMessages).to.deep.equal(WS_DELETE_SUCCESS)
    }, WAIT_RECEIVE_MSG_TIME)

    // 延迟结束本测试
    setTimeout(() => {
      mockServer.stop(done)
    }, WAIT_FINISH_TIME)
  })

  it('should ModifySubnet', function (done) {
    const WAIT_FINISH_TIME = 100
    const WAIT_RECEIVE_MSG_TIME = 50

    // subscribe message bark
    let barkMessages = WS_MODIFY_INIT
    websocketSvc.subscribe(DeviceStateSocketApi.MsgType.MODIFY_SUBNET, barkMessages, (returnObject) => {
      let subnetKey = returnObject.subnetKey;
      //更新子网集合
      barkMessages[subnetKey].subnetName = returnObject.subnetName;
      barkMessages[subnetKey].domain = returnObject.domain;
    });

    // socket打开时发送消息
    websocketSvc.subscribeToOpen(this, function () {
      websocketSvc.send('2')
    })

    // open the socket and send bark to receive bark message
    websocketSvc.open()

    setTimeout(() => {
      // expect(barkMessages).to.have.lengthOf(1)
      // console.log('client received message: ', barkMessages[0])
      expect(barkMessages).to.deep.equal(WS_MODIFY_SUCCESS)
    }, WAIT_RECEIVE_MSG_TIME)

    // 延迟结束本测试
    setTimeout(() => {
      mockServer.stop(done)
    }, WAIT_FINISH_TIME)
  })
})
