import {
  ProtocolRequest,
  ProtocolResponse,
  ProtocolEncoder,
  PacketBody,
  PacketBodyValue,
  ProtocolDecoder,
  ProtocolMessage,
  ProtocolNotification,
  decodeProtocolMessage
} from '@ucap-webmessenger/protocol';

export interface UpdateRequest extends ProtocolRequest {
  /** 대화방SEQ(s) */
  roomSeq: string;
  /** 대화방제목(s) */
  roomName: string;
  /** 알람여부(y) */
  receiveAlarm: boolean;
  /** 동기화여부(s) */
  syncAll: boolean;
}

export interface UpdateResponse extends ProtocolResponse {
  /** 대화방SEQ(s) */
  roomSeq: string;
  /** 대화방제목(s) */
  roomName: string;
  /** 알람여부(y) */
  receiveAlarm: boolean;
  /** 동기화여부(s) */
  syncAll: boolean;
}

export interface UpdateNotification extends ProtocolNotification {
  /** 대화방SEQ(s) */
  roomSeq: string;
  /** 대화방제목(s) */
  roomName: string;
  /** 알람여부(y) */
  receiveAlarm: boolean;
  /** 동기화여부(s) */
  syncAll: boolean;
}

export const encodeUpdate: ProtocolEncoder<UpdateRequest> = (
  req: UpdateRequest
) => {
  const bodyList: PacketBody[] = [];

  bodyList.push({ type: PacketBodyValue.String, value: req.roomSeq });
  bodyList.push({ type: PacketBodyValue.String, value: req.roomName });
  bodyList.push({
    type: PacketBodyValue.String,
    value: req.receiveAlarm ? 'Y' : 'N'
  });
  bodyList.push({
    type: PacketBodyValue.String,
    value: req.syncAll ? 'Y' : 'N'
  });
  return bodyList;
};

export const decodeUpdate: ProtocolDecoder<UpdateResponse> = (
  message: ProtocolMessage
) => {
  return decodeProtocolMessage(message, {
    roomSeq: message.bodyList[0],
    roomName: message.bodyList[1],
    receiveAlarm: message.bodyList[2] === 'Y' ? true : false,
    syncAll: message.bodyList[3] === 'Y' ? true : false
  } as UpdateResponse);
};

export const decodeUpdateNotification: ProtocolDecoder<UpdateNotification> = (
  message: ProtocolMessage
) => {
  return decodeProtocolMessage(message, {
    roomSeq: message.bodyList[0],
    roomName: message.bodyList[1],
    receiveAlarm: message.bodyList[2] === 'Y' ? true : false,
    syncAll: message.bodyList[3] === 'Y' ? true : false
  } as UpdateNotification);
};

export interface UpdateTimerSetRequest extends ProtocolRequest {
  // 대화방SEQ(s)
  roomSeq: string;
  // 타이머시간(n)
  timerInterval: number;
}

export interface UpdateTimerSetResponse extends ProtocolResponse {
  // 대화방SEQ(s)
  roomSeq: string;
  // 타이머시간(n)
  timerInterval: number;
}

export const encodeUpdateTimerSet: ProtocolEncoder<UpdateTimerSetRequest> = (
  req: UpdateTimerSetRequest
) => {
  const bodyList: PacketBody[] = [];

  bodyList.push({ type: PacketBodyValue.String, value: req.roomSeq });
  bodyList.push({ type: PacketBodyValue.Integer, value: req.timerInterval });
  return bodyList;
};

export const decodeUpdateTimerSet: ProtocolDecoder<UpdateTimerSetResponse> = (
  message: ProtocolMessage
) => {
  return decodeProtocolMessage(message, {
    roomSeq: message.bodyList[0],
    timerInterval: message.bodyList[1] || 0
  } as UpdateTimerSetResponse);
};

export interface UpdateFontRequest extends ProtocolRequest {
  // 대화방SEQ(s)
  roomSeq: string;
  // 폰트색(s) cf)0x000000 형태의 스트링
  fontColor: string;
  // sender사용자SEQ(n)
  senderSeq: number;
}

export interface UpdateFontResponse extends ProtocolResponse {
  // 대화방SEQ(s)
  roomSeq: string;
  // 폰트색(s) cf)0x000000 형태의 스트링
  fontColor: string;
  // sender사용자SEQ(n)
  senderSeq: number;
}

export interface UpdateFontNotification extends ProtocolNotification {
  // 대화방SEQ(s)
  roomSeq: string;
  // 폰트색(s) cf)0x000000 형태의 스트링
  fontColor: string;
  // sender사용자SEQ(n)
  senderSeq: number;
}

export const encodeUpdateFont: ProtocolEncoder<UpdateFontRequest> = (
  req: UpdateFontRequest
) => {
  const bodyList: PacketBody[] = [];

  bodyList.push({ type: PacketBodyValue.String, value: req.roomSeq });
  bodyList.push({ type: PacketBodyValue.String, value: req.fontColor });
  bodyList.push({ type: PacketBodyValue.Integer, value: req.senderSeq });
  return bodyList;
};

export const decodeUpdateFont: ProtocolDecoder<UpdateFontResponse> = (
  message: ProtocolMessage
) => {
  return decodeProtocolMessage(message, {
    roomSeq: message.bodyList[0],
    fontColor: message.bodyList[1],
    senderSeq: message.bodyList[2]
  } as UpdateFontResponse);
};

export const decodeUpdateFontNotification: ProtocolDecoder<
  UpdateFontNotification
> = (message: ProtocolMessage) => {
  return decodeProtocolMessage(message, {
    roomSeq: message.bodyList[0],
    fontColor: message.bodyList[1],
    senderSeq: message.bodyList[2]
  } as UpdateFontNotification);
};
