import React, { useState, useEffect, useReducer, useContext } from "react"

//import openSocket from "socket.io-client"
import { socket } from "../../services/socket"

import { makeStyles } from "@material-ui/core/styles"
import List from "@material-ui/core/List"
import Paper from "@material-ui/core/Paper"

import TicketListItem from "../TicketListItem"
import TicketsListSkeleton from "../TicketsListSkeleton"

import useTickets from "../../hooks/useTickets"
import { i18n } from "../../translate/i18n"
import { AuthContext } from "../../context/Auth/AuthContext"

import { SearchTicketContext } from "../../context/SearchTicket/SearchTicket"
import { Divider } from "@material-ui/core"
import { ticketsContext } from "../../context/TicketsProvider/TicketsProvider"

const useStyles = makeStyles(theme => ({
	ticketsListWrapper: {
		position: "relative",
		display: "flex",
		height: "100%",
		flexDirection: "column",
		overflow: "hidden",
		borderTopRightRadius: 0,
		borderBottomRightRadius: 0,
	},

	ticketsList: {
		flex: 1,
		overflowY: "scroll",
		...theme.scrollbarStyles,
		borderTop: "2px solid rgba(0, 0, 0, 0.12)",
	},

	ticketsListHeader: {
		color: "rgb(67, 83, 105)",
		zIndex: 2,
		backgroundColor: "white",
		borderBottom: "1px solid rgba(0, 0, 0, 0.12)",
		display: "flex",
		alignItems: "center",
		justifyContent: "space-between",
	},

	ticketsCount: {
		fontWeight: "normal",
		color: "rgb(104, 121, 146)",
		marginLeft: "8px",
		fontSize: "14px",
	},

	noTicketsText: {
		textAlign: "center",
		color: "rgb(104, 121, 146)",
		fontSize: "14px",
		lineHeight: "1.4",
	},

	noTicketsTitle: {
		textAlign: "center",
		fontSize: "16px",
		fontWeight: "600",
		margin: "0px",
	},

	noTicketsDiv: {
		display: "flex",
		height: "100px",
		margin: 40,
		flexDirection: "column",
		alignItems: "center",
		justifyContent: "center",
	},
}))

const reducer = (state, action) => {
	if (action.type === "LOAD_TICKETS") {
		const newTickets = action.payload


		newTickets.forEach(ticket => {

			const ticketIndex = state.findIndex(t => +t.id === +ticket.id)
			if (ticketIndex !== -1) {
				state[ticketIndex] = ticket
				if (+ticket.unreadMessages > 0) {
					state.unshift(state.splice(ticketIndex, 1)[0])
				}
			} else {
				state.push(ticket)
			}
		})

		return [...state]
	}

	if (action.type === "RESET_UNREAD") {
		const ticketId = action.payload

		const ticketIndex = state.findIndex(t => +t.id === +ticketId)



		if (ticketIndex !== -1) {
			state[ticketIndex].unreadMessages = 0
		}

		return [...state]
	}

	if (action.type === "UPDATE_TICKET") {
		const ticket = action.payload

		const ticketIndex = state.findIndex(t => +t.id === +ticket.id)

		if (ticketIndex !== -1) {
			state[ticketIndex] = ticket
		} else {
			state.unshift(ticket)
		}

		return [...state]
	}

	if (action.type === "UPDATE_TICKET_UNREAD_MESSAGES") {

		const message = action.payload.message

		const ticket = action.payload.ticket

		const ticketIndex = state.findIndex(t => +t.id === +ticket.id)

		if (ticketIndex !== -1) {





			if (!message.fromMe) {
				ticket.unreadMessages += 1
			}

			state[ticketIndex] = ticket
			state.unshift(state.splice(ticketIndex, 1)[0])

		} else {
			state.unshift(ticket)
		}

		return [...state]
	}

	if (action.type === "UPDATE_TICKET_CONTACT") {
		const contact = action.payload
		const ticketIndex = state.findIndex(t => +t.contactId === +contact.id)
		if (ticketIndex !== -1) {
			state[ticketIndex].contact = contact
		}
		return [...state]
	}

	if (action.type === "DELETE_TICKET") {
		const ticketId = action.payload
		const ticketIndex = state.findIndex(t => +t.id === +ticketId)
		if (ticketIndex !== -1) {
			state.splice(ticketIndex, 1)
		}

		return [...state]
	}

	if (action.type === "RESET") {
		return []
	}
}

const TicketsList = (props) => {
	const { status, searchParam, searchParamContent, showAll, selectedQueueIds, updateCount, style, tab } = props
	const classes = useStyles()
	const [pageNumber, setPageNumber] = useState(1)
	const [ticketsList, dispatch] = useReducer(reducer, [])
	const { user, setting, } = useContext(AuthContext)

	const { searchTicket } = useContext(SearchTicketContext)

	const [_remoteTicketsControll, setRemoteTicketsControll] = useState([])

	const [settings, setSettings] = useState([])

	useEffect(() => {
		setSettings(setting)
	}, [setting])
	const { setTickets } = useContext(ticketsContext)


	useEffect(() => {

		dispatch({ type: "RESET" })
		setPageNumber(1)

	}, [status, searchParam, searchParamContent, showAll, selectedQueueIds, searchTicket])

	let { tickets, hasMore, loading, remoteTicketsControll } = useTickets({
		pageNumber,
		searchParam,
		searchParamContent,
		status,
		showAll,
		queueIds: JSON.stringify(selectedQueueIds),
		tab,
		unlimited: status === 'open' ? "all" : "false"
	})


	useEffect(() => {
		setRemoteTicketsControll(remoteTicketsControll)
	}, [remoteTicketsControll])

	useEffect(() => {

		if (!status && !searchParam) return

		// if (searchParam) { 
		// 	
		// 	dispatch({ type: "RESET" });
		// }

		if ((searchParam && searchParam.trim().length > 0) &&
			(tickets && tickets.length === 0) &&
			pageNumber === 1) {
			dispatch({ type: "RESET" })
		}

		dispatch({ type: "LOAD_TICKETS", payload: tickets, })

	}, [tickets, status, searchParam, pageNumber])

	useEffect(() => {

		// if (tab=='search')return

		//const socket = openSocket(process.env.REACT_APP_BACKEND_URL)

		const shouldUpdateTicket = ticket =>
			(!ticket.userId || ticket.userId === user?.id || showAll) &&
			(!ticket.queueId || selectedQueueIds.indexOf(ticket.queueId) > -1)

		const notBelongsToUserQueues = ticket =>
			ticket.queueId && selectedQueueIds.indexOf(ticket.queueId) === -1

		const onConnectTicketList = () => {
			if (status) {
				socket.emit("joinTickets", status)
			} else {
				socket.emit("joinNotification")
			}
		}

		onConnectTicketList()

		socket.on("connect", onConnectTicketList)

		const onTicketTicketList = data => {

			if (data.action === "updateUnread") {

				if (tab === 'search' && data.ticket && data.ticket.status === 'pending') return

				dispatch({
					type: "RESET_UNREAD",
					payload: data.ticketId,
				})
			}

			if (data.action === "update" && shouldUpdateTicket(data.ticket)) {

				if (tab === 'search' && data.ticket && (data.ticket.status === 'pending' || data.ticket.status === 'closed')) return

				dispatch({
					type: "UPDATE_TICKET",
					payload: data.ticket,
				})
			}

			if (data.action === "update" && notBelongsToUserQueues(data.ticket)) {
				dispatch({ type: "DELETE_TICKET", payload: data.ticket.id })
			}

			if (data.action === "delete") {
				dispatch({ type: "DELETE_TICKET", payload: data.ticketId })
			}
		}

		socket.on("ticket", onTicketTicketList)

		const onAppMessageTicketList = data => {
			if (data.action === "create" && shouldUpdateTicket(data.ticket)) {


				if (tab === 'search') return

				dispatch({
					type: "UPDATE_TICKET_UNREAD_MESSAGES",
					// payload: data.ticket,
					payload: data,
				})
			}
		}

		socket.on("appMessage", onAppMessageTicketList)

		socket.on("contact", data => {
			if (data.action === "update") {
				dispatch({
					type: "UPDATE_TICKET_CONTACT",
					payload: data.contact,
				})
			}
		})


		socket.on('remoteTickesControll', (data) => {
			console.log('REMOTE TICKETS CONTROLL UPDATE 1: ', data.tickets)
			if (data.action === 'update') {
				setRemoteTicketsControll(data.tickets)
			}
		})

		const onSettingsTicketList = (data) => {
			if (data.action === 'update') {
				setSettings((prevState) => {
					const aux = [...prevState]
					const settingIndex = aux.findIndex((s) => s.key === data.setting.key)
					aux[settingIndex].value = data.setting.value
					return aux
				})
			}
		}

		socket.on('settings', onSettingsTicketList)

		return () => {
			socket.off("ticket", onTicketTicketList)
			socket.off('appMessage', onAppMessageTicketList);
			socket.removeAllListeners("contact")
			socket.off('connect', onConnectTicketList);
			socket.off('settings', onSettingsTicketList);
			socket.removeAllListeners('remoteTickesControll');
		}
	}, [status, showAll, user, selectedQueueIds, tab])

	useEffect(() => {

		if (typeof updateCount === "function") {
			updateCount(ticketsList.length)
		}
		if (ticketsList && status === "pending") {
			setTickets(ticketsList)
		}
		// else{
		// 	setTickets([])
		// }
		// eslint-disable-next-line react-hooks/exhaustive-deps
	}, [ticketsList])

	const loadMore = () => {
		setPageNumber(prevState => prevState + 1)
	}

	const handleScroll = e => {

		if (!hasMore || loading) return

		const { scrollTop, scrollHeight, clientHeight } = e.currentTarget

		if (scrollHeight - (scrollTop + 100) < clientHeight) {



			loadMore()
		}
	}

	return (
		<Paper className={classes.ticketsListWrapper} style={style}>
			<Paper
				square
				name="closed"
				elevation={0}
				className={classes.ticketsList}
				onScroll={handleScroll}
			>
				<List style={{ paddingTop: 0 }}>
					{ticketsList.length === 0 && !loading ? (
						<div className={classes.noTicketsDiv}>
							<span className={classes.noTicketsTitle}>
								{i18n.t("ticketsList.noTicketsTitle")}
							</span>
							<p className={classes.noTicketsText}>
								{i18n.t("ticketsList.noTicketsMessage")}
							</p>
						</div>
					) : (
						<>
							{ticketsList.map(ticket => (
								<TicketListItem ticket={ticket} key={ticket.id} remoteTicketsControll={_remoteTicketsControll} settings={settings} />
							))}
						</>
					)}
					{loading && <TicketsListSkeleton />}
				</List>
			</Paper>
		</Paper>
	)
}

export default TicketsList