diff --git a/frontend/src/components/Base/Badge/BadgeComponent.jsx b/frontend/src/components/Base/Badge/BadgeComponent.jsx index 93e1b35..6fe85e5 100644 --- a/frontend/src/components/Base/Badge/BadgeComponent.jsx +++ b/frontend/src/components/Base/Badge/BadgeComponent.jsx @@ -1,9 +1,9 @@ import React from "react"; import { BadgeComponentStyled } from "./BadgeComponent.style"; -const BadgeComponent = ({ counter, position, top, left, right, bottom }) => { +const BadgeComponent = ({ counter,fontSize, position, top, left, right, bottom,bgcolor }) => { return ( - + {counter} ); diff --git a/frontend/src/components/Base/Badge/BadgeComponent.style.jsx b/frontend/src/components/Base/Badge/BadgeComponent.style.jsx index 471ad11..87c5cc8 100644 --- a/frontend/src/components/Base/Badge/BadgeComponent.style.jsx +++ b/frontend/src/components/Base/Badge/BadgeComponent.style.jsx @@ -15,8 +15,8 @@ export const BadgeComponentStyled = styled.span` object-fit: cover; width: 21px; height: 21px; - font-size: 16px; + font-size: ${({ fontSize }) => (fontSize ? fontSize : "16px")}; color: ${color.pricinpal.blanco}; - background-color: ${color.status.yes}; + background-color: ${({ bgcolor }) => (bgcolor ? bgcolor : color.status.yes)}; `; diff --git a/frontend/src/components/LoginComponents/LoginForm/Inputs/InputComponent.style.jsx b/frontend/src/components/LoginComponents/LoginForm/Inputs/InputComponent.style.jsx index 4e6c60d..613c3fc 100644 --- a/frontend/src/components/LoginComponents/LoginForm/Inputs/InputComponent.style.jsx +++ b/frontend/src/components/LoginComponents/LoginForm/Inputs/InputComponent.style.jsx @@ -3,7 +3,7 @@ import { color } from "../../../../style/varibles"; const InputComponentStyled = styled.input` width: 100%; - background: transparent; + background: ${color.complement.azulOscuro}; border: none; color: ${color.complement.azulCielo}; `; diff --git a/frontend/src/components/Ticket/Ticket.jsx b/frontend/src/components/Ticket/Ticket.jsx index 1f3d74c..929f648 100644 --- a/frontend/src/components/Ticket/Ticket.jsx +++ b/frontend/src/components/Ticket/Ticket.jsx @@ -88,13 +88,9 @@ const Ticket = () => { setDrawerOpen(false); }; - const style ={ - height: "fit-content", - width: "100%", - position: "relative", - } + return ( -
+
diff --git a/frontend/src/components/Ticket/Ticket.style.jsx b/frontend/src/components/Ticket/Ticket.style.jsx new file mode 100644 index 0000000..c6e12c9 --- /dev/null +++ b/frontend/src/components/Ticket/Ticket.style.jsx @@ -0,0 +1,7 @@ +import styled from "styled-components"; +import { color } from "../../style/varibles"; + +export const TicketStyled = styled.div` + width: 100%; + background-color: ${color.status.no}; +`; diff --git a/frontend/src/components/Ticket/TicketsManager/TicketsList/TicketListItem/TicketListItem.jsx b/frontend/src/components/Ticket/TicketsManager/TicketsList/TicketListItem/TicketListItem.jsx index ce86ef4..272817b 100644 --- a/frontend/src/components/Ticket/TicketsManager/TicketsList/TicketListItem/TicketListItem.jsx +++ b/frontend/src/components/Ticket/TicketsManager/TicketsList/TicketListItem/TicketListItem.jsx @@ -1,5 +1,5 @@ import React from "react"; -import {color} from "../../../../../style/varibles"; +import { color } from "../../../../../style/varibles"; import { useHistory } from "react-router-dom"; import { parseISO, format, isSameDay } from "date-fns"; @@ -8,7 +8,7 @@ import { i18n } from "../../../../../translate/i18n"; import api from "../../../../../services/api"; import { AuthContext } from "../../../../../context/Auth/AuthContext"; import toastError from "../../../../../errors/toastError"; -import Btn from "../../../../Base/Btn/Btn" +import Btn from "../../../../Base/Btn/Btn"; import { TicketDateStyled, TicketImgStyled, @@ -24,7 +24,6 @@ const TicketListItem = ({ tickets }) => { const [loading, setLoading] = React.useState(false); const isMounted = React.useRef(true); const { user } = React.useContext(AuthContext); - React.useEffect(() => { return () => { isMounted.current = false; @@ -32,7 +31,7 @@ const TicketListItem = ({ tickets }) => { }, []); const handleAcepptTicket = async (id) => { - setLoading(true) + setLoading(true); try { await api.put(`/tickets/${id}`, { status: "open", @@ -54,10 +53,14 @@ const TicketListItem = ({ tickets }) => { const handleSelectTicket = (id) => { history.push(`/tickets/${id}`); }; - if (loading) return ; + + return ( - - handleSelectTicket(tickets.id)}> + + handleSelectTicket(tickets.id)} + > {tickets.contact.profilePicUrl ? ( ) : ( @@ -86,7 +89,13 @@ const TicketListItem = ({ tickets }) => { )} {tickets.status === "pending" ? ( - + handleAcepptTicket(tickets.id)} + text="Aceitar" + bgcolor={color.complement.azulCielo} + fontcolor={color.pricinpal.blanco} + fontSize="12px" + /> ) : ( "" )} diff --git a/frontend/src/components/Ticket/TicketsManager/TicketsList/TicketsList.jsx b/frontend/src/components/Ticket/TicketsManager/TicketsList/TicketsList.jsx index d1bf84e..fb3b27b 100644 --- a/frontend/src/components/Ticket/TicketsManager/TicketsList/TicketsList.jsx +++ b/frontend/src/components/Ticket/TicketsManager/TicketsList/TicketsList.jsx @@ -2,6 +2,8 @@ import React from "react"; import openSocket from "socket.io-client"; +import LoadingScreen from "../../../LoadingScreen/LoadingScreen"; + import TicketListStyled from "./TicketsList.style"; import useTickets from "../../../../hooks/useTickets"; import TicketListItem from "../TicketsList/TicketListItem/TicketListItem"; @@ -94,10 +96,14 @@ const reducer = (state, action) => { return []; } }; -const TicketsList = ({ status, searchParam, showAll, selectedQueueIds, updateCount }) => { +const TicketsList = ({ status, searchParam, showAll, selectedQueueIds, updateCount, valueTab }) => { const [pageNumber, setPageNumber] = React.useState(1); const [ticketsList, dispatch] = React.useReducer(reducer, []); const { user } = React.useContext(AuthContext); + React.useEffect(() => { + dispatch({ type: "RESET" }); + setPageNumber(1); + }, [status, searchParam, dispatch, showAll, selectedQueueIds]); const { tickets, loading } = useTickets({ pageNumber, searchParam, @@ -105,10 +111,13 @@ const TicketsList = ({ status, searchParam, showAll, selectedQueueIds, updateCou showAll, queueIds: JSON.stringify(selectedQueueIds), }); + React.useEffect(() => { - dispatch({ type: "RESET" }); - setPageNumber(1); - }, [status, searchParam, dispatch, showAll, selectedQueueIds]); + if (typeof updateCount === "function") { + updateCount(ticketsList.length); + } + // eslint-disable-next-line react-hooks/exhaustive-deps + }, [ticketsList]); React.useEffect(() => { if (!status && !searchParam) return; @@ -116,7 +125,7 @@ const TicketsList = ({ status, searchParam, showAll, selectedQueueIds, updateCou type: "LOAD_TICKETS", payload: tickets, }); - }, [tickets, searchParam]); + }, [tickets, status, searchParam]); React.useEffect(() => { const socket = openSocket(process.env.REACT_APP_BACKEND_URL); @@ -162,6 +171,8 @@ const TicketsList = ({ status, searchParam, showAll, selectedQueueIds, updateCou socket.on("appMessage", (data) => { if (data.action === "create" && shouldUpdateTicket(data.ticket)) { + // console.log('((((((((((((((((((( DATA.MESSAGE: ', data.message) + dispatch({ type: "UPDATE_TICKET_UNREAD_MESSAGES", // payload: data.ticket, @@ -185,13 +196,16 @@ const TicketsList = ({ status, searchParam, showAll, selectedQueueIds, updateCou }, [status, showAll, user, selectedQueueIds]); if (loading) return ; - return ( - - {ticketsList.map((ticket) => ( - - ))} - - ); + + if (status === valueTab) + return ( + + {ticketsList.map((ticket) => ( + + ))} + + ); + return null; }; export default TicketsList; diff --git a/frontend/src/components/Ticket/TicketsManager/TicketsManager.jsx b/frontend/src/components/Ticket/TicketsManager/TicketsManager.jsx index ff74461..d971cf4 100644 --- a/frontend/src/components/Ticket/TicketsManager/TicketsManager.jsx +++ b/frontend/src/components/Ticket/TicketsManager/TicketsManager.jsx @@ -2,24 +2,25 @@ import React from "react"; import TicketsManagerStyled from "./TicketsManager.style"; import TicketsTabs from "./TicketsTabs/TicketsTabs"; + +import TicketSearch from "../TicketSearch/TicketSearch"; import TicketsList from "./TicketsList/TicketsList"; import NewTicketModal from "../../NewTicketModal"; -import useTickets from "../../../hooks/useTickets"; + import { AuthContext } from "../../../context/Auth/AuthContext"; -import TicketSearch from "../TicketSearch/TicketSearch"; const TicketsManager = () => { const [valueTab, setValueTab] = React.useState("open"); const [searchParam, setSearchParam] = React.useState(""); const [spinning, setSpinning] = React.useState(false); const [newTicketModalOpen, setNewTicketModalOpen] = React.useState(false); + const [openCount, setOpenCount] = React.useState(0); + const [pendingCount, setPendingCount] = React.useState(0); + const [closedCount, setClosedCount] = React.useState(0); const [showAllTickets, setShowAllTickets] = React.useState(false); const { user } = React.useContext(AuthContext); const userQueueIds = user.queues.map((q) => q.id); const [selectedQueueIds, setSelectedQueueIds] = React.useState(userQueueIds || []); - const { tickets } = useTickets({ - searchParam - }); let searchTimeout; const handleSearch = (e) => { @@ -47,23 +48,47 @@ const TicketsManager = () => { return ( - + + + setOpenCount(v)} showAll={showAllTickets} - status={valueTab} selectedQueueIds={selectedQueueIds} searchParam={searchParam} + valueTab={valueTab} /> + setPendingCount(v)} + selectedQueueIds={selectedQueueIds} + searchParam={searchParam} + valueTab={valueTab} + /> + setClosedCount(v)} + selectedQueueIds={selectedQueueIds} + searchParam={searchParam} + valueTab={valueTab} + /> + setNewTicketModalOpen(false)} /> + ); }; diff --git a/frontend/src/components/Ticket/TicketsManager/TicketsTabs/TicketsTab/TicketsTab.jsx b/frontend/src/components/Ticket/TicketsManager/TicketsTabs/TicketsTab/TicketsTab.jsx index dde8583..de62601 100644 --- a/frontend/src/components/Ticket/TicketsManager/TicketsTabs/TicketsTab/TicketsTab.jsx +++ b/frontend/src/components/Ticket/TicketsManager/TicketsTabs/TicketsTab/TicketsTab.jsx @@ -1,7 +1,10 @@ import React from "react"; import { TicketsTabStyled } from "./TicketsTab.style"; +import { color } from "../../../../../style/varibles"; -const TicketsTab = ({ text, id, setValueTab, valueTab }) => { +import BadgeComponent from "../../../../Base/Badge/BadgeComponent"; + +const TicketsTab = ({ text, id, setValueTab, valueTab, count }) => { const [active, setActive] = React.useState(false); const handleClick = ({ target }) => { @@ -11,6 +14,7 @@ const TicketsTab = ({ text, id, setValueTab, valueTab }) => { React.useEffect(() => { valueTab === id ? setActive(true) : setActive(false); }, [valueTab, id]); + return ( { className={active ? "active" : ""} > {text} + {id !== "open" ? ( + + ) : ( + "" + )} ); }; diff --git a/frontend/src/components/Ticket/TicketsManager/TicketsTabs/TicketsTabs.jsx b/frontend/src/components/Ticket/TicketsManager/TicketsTabs/TicketsTabs.jsx index c8a165a..1ede3af 100644 --- a/frontend/src/components/Ticket/TicketsManager/TicketsTabs/TicketsTabs.jsx +++ b/frontend/src/components/Ticket/TicketsManager/TicketsTabs/TicketsTabs.jsx @@ -1,16 +1,32 @@ import React from "react"; +import TicketsTab from "../TicketsTabs/TicketsTab/TicketsTab"; import { TicketTabsStyled } from "./TicketsTabs.style"; -import TicketsTab from "./TicketsTab/TicketsTab"; +const TicketsTabs = ({ setValueTab, valueTab, count }) => { -const TicketsTabs = ({ tickets, setValueTab, valueTab }) => { - - if (!setValueTab) return null; return ( - - - + + + ); }; diff --git a/frontend/src/pages/Report/index.js b/frontend/src/pages/Report/index.js index 9912cf2..88986fa 100644 --- a/frontend/src/pages/Report/index.js +++ b/frontend/src/pages/Report/index.js @@ -2,109 +2,97 @@ import React, { useState, useEffect, useReducer, useContext, useRef } from "reac import MainContainer from "../../components/MainContainer"; import api from "../../services/api"; import SelectField from "../../components/Report/SelectField"; -//import { data } from '../../components/Report/MTable/data'; -import DatePicker1 from '../../components/Report/DatePicker' -import DatePicker2 from '../../components/Report/DatePicker' +//import { data } from '../../components/Report/MTable/data'; +import DatePicker1 from "../../components/Report/DatePicker"; +import DatePicker2 from "../../components/Report/DatePicker"; import MTable from "../../components/Report/MTable"; -import PropTypes from 'prop-types'; -import Box from '@mui/material/Box'; +import PropTypes from "prop-types"; +import Box from "@mui/material/Box"; import { AuthContext } from "../../context/Auth/AuthContext"; import { Can } from "../../components/Can"; import { Button } from "@material-ui/core"; import ReportModal from "../../components/ReportModal"; -import MaterialTable from 'material-table'; +import MaterialTable from "material-table"; -import LogoutIcon from '@material-ui/icons/CancelOutlined'; +import LogoutIcon from "@material-ui/icons/CancelOutlined"; import { CSVLink } from "react-csv"; +import openSocket from "socket.io-client"; -import openSocket from "socket.io-client"; - -const report = [{ 'value': '1', 'label': 'Atendimento por atendentes' }, { 'value': '2', 'label': 'Usuários online/offline' }] +const report = [ + { value: "1", label: "Atendimento por atendentes" }, + { value: "2", label: "Usuários online/offline" }, +]; let columns = [ { - key: 'ticket.whatsapp.name', - label: 'Loja', - + key: "ticket.whatsapp.name", + label: "Loja", }, { - key: 'id', - label: 'id Mensagem', + key: "id", + label: "id Mensagem", }, { - key: 'ticket.id', - label: 'id Conversa', + key: "ticket.id", + label: "id Conversa", }, { - key: 'ticket.contact.name', - label: 'Cliente', + key: "ticket.contact.name", + label: "Cliente", }, { - key: 'ticket.user.name', - label: 'Atendente', + key: "ticket.user.name", + label: "Atendente", }, { - key: 'body', - label: 'Mensagem', + key: "body", + label: "Mensagem", }, { - key: 'fromMe', - label: 'Sentido', + key: "fromMe", + label: "Sentido", }, { - key: 'createdAt', - label: 'Criada', + key: "createdAt", + label: "Criada", }, { - key: 'ticket.contact.number', - label: 'Telefone cliente', + key: "ticket.contact.number", + label: "Telefone cliente", }, { - key: 'ticket.queue.name', - label: 'Fila', + key: "ticket.queue.name", + label: "Fila", }, { - key: 'ticket.status', - label: 'Status', + key: "ticket.status", + label: "Status", }, { - key: 'ticket.statusChatEnd', - label: 'Status de encerramento', - } - -] + key: "ticket.statusChatEnd", + label: "Status de encerramento", + }, +]; // - - - - - - - const reducerQ = (state, action) => { - - - - if (action.type === "DELETE_USER_STATUS") { - const userId = action.payload; //console.log('Entrou no delete user status userId: ', userId) const userIndex = state.findIndex((u) => `${u.id}` === `${userId}`); - // console.log('>>>>>>>>>>>>>>>>>>>>> userIndex: ', userIndex) + // console.log('>>>>>>>>>>>>>>>>>>>>> userIndex: ', userIndex) if (userIndex !== -1) { state.splice(userIndex, 1); @@ -113,115 +101,90 @@ const reducerQ = (state, action) => { return [...state]; } - - - if (action.type === 'LOAD_QUERY') { - - - const queries = action.payload - const newQueries = [] + if (action.type === "LOAD_QUERY") { + const queries = action.payload; + const newQueries = []; queries.forEach((query) => { - - const queryIndex = state.findIndex((q) => q.id === query.id) + const queryIndex = state.findIndex((q) => q.id === query.id); if (queryIndex !== -1) { - state[queryIndex] = query - } - else { - newQueries.push(query) + state[queryIndex] = query; + } else { + newQueries.push(query); } + }); - }) - - return [...state, ...newQueries] + return [...state, ...newQueries]; } - if (action.type === "UPDATE_STATUS_ONLINE") { + let onlineUser = action.payload; + let index = -1; - let onlineUser = action.payload - let index = -1 - - // console.log('sssssssssstate: ', state, ' | ONLINE USERS: onlineUser.userId ', onlineUser.userId) + // console.log('sssssssssstate: ', state, ' | ONLINE USERS: onlineUser.userId ', onlineUser.userId) if (onlineUser.sumOpen || onlineUser.sumClosed) { - index = state.findIndex((e) => ((onlineUser.sumOpen && e.id === onlineUser.sumOpen.userId) || (onlineUser.sumClosed && e.id === onlineUser.sumClosed.userId))) - } - else { - index = state.findIndex((e) => `${e.id}` === `${onlineUser.userId}`) + index = state.findIndex( + (e) => + (onlineUser.sumOpen && e.id === onlineUser.sumOpen.userId) || + (onlineUser.sumClosed && e.id === onlineUser.sumClosed.userId) + ); + } else { + index = state.findIndex((e) => `${e.id}` === `${onlineUser.userId}`); } - //console.log(' *********************** index: ', index) - - + //console.log(' *********************** index: ', index) if (index !== -1) { - - // console.log('ENTROU NO INDEX') - + // console.log('ENTROU NO INDEX') if (!("statusOnline" in state[index])) { - state[index].statusOnline = onlineUser + state[index].statusOnline = onlineUser; + } else if ("statusOnline" in state[index]) { + state[index].statusOnline["status"] = onlineUser.status; } - else if ("statusOnline" in state[index]) { - state[index].statusOnline['status'] = onlineUser.status - } - if ("onlineTime" in onlineUser) { - if ("sumOnlineTime" in state[index]) { - state[index].sumOnlineTime['sum'] = (onlineUser.onlineTime).split(" ")[1] - } - else if (!("sumOnlineTime" in state[index])) { - state[index].sumOnlineTime = { userId: onlineUser.userId, sum: (onlineUser.onlineTime).split(" ")[1] } + state[index].sumOnlineTime["sum"] = onlineUser.onlineTime.split(" ")[1]; + } else if (!("sumOnlineTime" in state[index])) { + state[index].sumOnlineTime = { + userId: onlineUser.userId, + sum: onlineUser.onlineTime.split(" ")[1], + }; } } - if (onlineUser.sumOpen) { - if ("sumOpen" in state[index]) { - // console.log(' >>>>>>>>>>>>>>>>>> sumOpen 1 | state[index].sumOpen["count"]: ', state[index].sumOpen['count'], ' | onlineUser.sumOpen.count: ', onlineUser.sumOpen.count) - state[index].sumOpen['count'] = onlineUser.sumOpen.count + // console.log(' >>>>>>>>>>>>>>>>>> sumOpen 1 | state[index].sumOpen["count"]: ', state[index].sumOpen['count'], ' | onlineUser.sumOpen.count: ', onlineUser.sumOpen.count) + state[index].sumOpen["count"] = onlineUser.sumOpen.count; } else if (!("sumOpen" in state[index])) { - // console.log(' >>>>>>>>>>>>>>>>>> sumOpen 1') - state[index].sumOpen = onlineUser.sumOpen + // console.log(' >>>>>>>>>>>>>>>>>> sumOpen 1') + state[index].sumOpen = onlineUser.sumOpen; } - } if (onlineUser.sumClosed) { - if ("sumClosed" in state[index]) { - // console.log(' >>>>>>>>>>>>>>>>>> sumClosed 1 | state[index].sumClosed["count"]: ', state[index].sumClosed['count'], ' | onlineUser.sumClosed.count: ', onlineUser.sumClosed.count) - state[index].sumClosed['count'] = onlineUser.sumClosed.count + // console.log(' >>>>>>>>>>>>>>>>>> sumClosed 1 | state[index].sumClosed["count"]: ', state[index].sumClosed['count'], ' | onlineUser.sumClosed.count: ', onlineUser.sumClosed.count) + state[index].sumClosed["count"] = onlineUser.sumClosed.count; } else if (!("sumClosed" in state[index])) { - // console.log(' >>>>>>>>>>>>>>>>>> sumOpen 1') - state[index].sumClosed = onlineUser.sumClosed + // console.log(' >>>>>>>>>>>>>>>>>> sumOpen 1') + state[index].sumClosed = onlineUser.sumClosed; } - } - - } - return [...state] - + return [...state]; } - - if (action.type === "RESET") { return []; } - -} - - +}; const reducer = (state, action) => { - if (action.type === "LOAD_USERS") { const users = action.payload; const newUsers = []; @@ -253,24 +216,20 @@ const reducer = (state, action) => { } }; - - - function Item(props) { const { sx, ...other } = props; return ( (theme.palette.mode === 'dark' ? '#101010' : '#fff'), - color: (theme) => (theme.palette.mode === 'dark' ? 'grey.300' : 'grey.800'), - border: '1px solid', - borderColor: (theme) => - theme.palette.mode === 'dark' ? 'grey.800' : 'grey.300', + bgcolor: (theme) => (theme.palette.mode === "dark" ? "#101010" : "#fff"), + color: (theme) => (theme.palette.mode === "dark" ? "grey.300" : "grey.800"), + border: "1px solid", + borderColor: (theme) => (theme.palette.mode === "dark" ? "grey.800" : "grey.300"), p: 1, m: 1, borderRadius: 2, - fontSize: '0.875rem', - fontWeight: '700', + fontSize: "0.875rem", + fontWeight: "700", ...sx, }} {...other} @@ -280,76 +239,64 @@ function Item(props) { Item.propTypes = { sx: PropTypes.oneOfType([ - PropTypes.arrayOf( - PropTypes.oneOfType([PropTypes.func, PropTypes.object, PropTypes.bool]), - ), + PropTypes.arrayOf(PropTypes.oneOfType([PropTypes.func, PropTypes.object, PropTypes.bool])), PropTypes.func, PropTypes.object, ]), }; - - let columnsData = [ - { title: 'Unidade', field: 'whatsapp.name' }, - { title: 'Atendente', field: 'user.name' }, - { title: 'Contato', field: 'contact.number' }, - { title: 'Nome', field: 'contact.name' }, - { title: 'Assunto', field: 'queue.name' }, + { title: "Unidade", field: "whatsapp.name" }, + { title: "Atendente", field: "user.name" }, + { title: "Contato", field: "contact.number" }, + { title: "Nome", field: "contact.name" }, + { title: "Assunto", field: "queue.name" }, - { title: 'Status', field: 'status' }, - - { title: 'Criado', field: 'createdAt' }, + { title: "Status", field: "status" }, + + { title: "Criado", field: "createdAt" }, //{title: 'Atualizado', field: 'updatedAt'}, - {title: 'Status de encerramento', field: 'statusChatEnd'}]; - + { title: "Status de encerramento", field: "statusChatEnd" }, +]; const Report = () => { - - const csvLink = useRef() + const csvLink = useRef(); const { user: userA } = useContext(AuthContext); - //-------- + //-------- const [searchParam] = useState(""); //const [loading, setLoading] = useState(false); - //const [hasMore, setHasMore] = useState(false); + //const [hasMore, setHasMore] = useState(false); const [pageNumber, setPageNumber] = useState(1); const [users, dispatch] = useReducer(reducer, []); - //const [columns, setColums] = useState([]) - const [startDate, setDatePicker1] = useState(new Date()) - const [endDate, setDatePicker2] = useState(new Date()) - const [userId, setUser] = useState(null) - const [query, dispatchQ] = useReducer(reducerQ, []) + //const [columns, setColums] = useState([]) + const [startDate, setDatePicker1] = useState(new Date()); + const [endDate, setDatePicker2] = useState(new Date()); + const [userId, setUser] = useState(null); + const [query, dispatchQ] = useReducer(reducerQ, []); - const [dataCSV, setDataCSV] = useState([]) + const [dataCSV, setDataCSV] = useState([]); const [isMount, setIsMount] = useState(true); - const [reportOption, setReport] = useState('1') - const [reporList,] = useState(report) - const [profile, setProfile] = useState('') + const [reportOption, setReport] = useState("1"); + const [reporList] = useState(report); + const [profile, setProfile] = useState(""); const [dataRows, setData] = useState([]); - - - useEffect(() => { dispatch({ type: "RESET" }); - dispatchQ({ type: "RESET" }) + dispatchQ({ type: "RESET" }); setPageNumber(1); }, [searchParam, profile]); - - useEffect(() => { - //setLoading(true); + //setLoading(true); const delayDebounceFn = setTimeout(() => { - const fetchUsers = async () => { try { - //console.log('profile: ', profile) const { data } = await api.get("/users/", { @@ -358,111 +305,87 @@ const Report = () => { dispatch({ type: "LOAD_USERS", payload: data.users }); //setHasMore(data.hasMore); - //setLoading(false); - - + //setLoading(false); } catch (err) { console.log(err); } }; fetchUsers(); - }, 500); return () => clearTimeout(delayDebounceFn); }, [searchParam, pageNumber, reportOption, profile]); - - useEffect(() => { - //setLoading(true); const delayDebounceFn = setTimeout(() => { - const fetchQueries = async () => { try { - - if (reportOption === '1') { - - const dataQuery = await api.get("/reports/", { params: { userId, startDate, endDate }, }); - dispatchQ({ type: "RESET" }) + if (reportOption === "1") { + const dataQuery = await api.get("/reports/", { + params: { userId, startDate, endDate }, + }); + dispatchQ({ type: "RESET" }); dispatchQ({ type: "LOAD_QUERY", payload: dataQuery.data }); //setLoading(false); - // console.log('dataQuery: ', dataQuery.data) + // console.log('dataQuery: ', dataQuery.data) - // console.log() - - } - else if (reportOption === '2') { - - const dataQuery = await api.get("/reports/user/services", { params: { userId, startDate, endDate }, }); - dispatchQ({ type: "RESET" }) + // console.log() + } else if (reportOption === "2") { + const dataQuery = await api.get("/reports/user/services", { + params: { userId, startDate, endDate }, + }); + dispatchQ({ type: "RESET" }); dispatchQ({ type: "LOAD_QUERY", payload: dataQuery.data }); //setLoading(false); - // console.log('REPORT 2 dataQuery : ', dataQuery.data) + // console.log('REPORT 2 dataQuery : ', dataQuery.data) //console.log() - } - } catch (err) { console.log(err); } }; fetchQueries(); - }, 500); return () => clearTimeout(delayDebounceFn); - }, [userId, startDate, endDate, reportOption]); - // Get from child 1 const datePicker1Value = (data) => { - - setDatePicker1(data) - } + setDatePicker1(data); + }; // Get from child 2 const datePicker2Value = (data) => { - - setDatePicker2(data) - } + setDatePicker2(data); + }; // Get from child 3 const textFieldSelectUser = (data) => { - - setUser(data) - } - - - + setUser(data); + }; // Get from report option const reportValue = (data) => { + setReport(data); - setReport(data) - - // console.log(' data: ', data) - } + // console.log(' data: ', data) + }; useEffect(() => { - - if (reportOption === '1') { - setProfile('') + if (reportOption === "1") { + setProfile(""); + } else if (reportOption === "2") { + setProfile("user"); } - else if (reportOption === '2') { - setProfile('user') - } - - }, [reportOption]) - + }, [reportOption]); // useEffect(() => { @@ -470,108 +393,87 @@ const Report = () => { // }, [query]) - - - // test del + // test del const handleCSVMessages = () => { - - // setLoading(true); + // setLoading(true); const fetchQueries = async () => { - try { + const dataQuery = await api.get("/reports/messages", { + params: { userId, startDate, endDate }, + }); - const dataQuery = await api.get("/reports/messages", { params: { userId, startDate, endDate }, }); - - // console.log('dataQuery messages: ', dataQuery.data) + // console.log('dataQuery messages: ', dataQuery.data) if (dataQuery.data.length > 0) { - let dataCSVFormat = dataQuery.data; for (var i = 0; i < dataCSVFormat.length; i++) { if (dataCSVFormat[i].fromMe) { - dataCSVFormat[i].fromMe = 'Atendente' - } - else { - dataCSVFormat[i].fromMe = 'Cliente' + dataCSVFormat[i].fromMe = "Atendente"; + } else { + dataCSVFormat[i].fromMe = "Cliente"; } } // console.log('dataCSVFormat: ', dataCSVFormat) - setDataCSV(dataCSVFormat) + setDataCSV(dataCSVFormat); setIsMount(false); // setDataCSV(dataQuery.data) } - // setLoading(false); - + // setLoading(false); } catch (err) { console.log(err); } }; fetchQueries(); - - } - - - - + }; useEffect(() => { - if (isMount) { return; } - csvLink.current.link.click() - + csvLink.current.link.click(); }, [dataCSV, isMount, csvLink]); - - - useEffect(() => { - - if (reportOption === '2') { - + if (reportOption === "2") { const socket = openSocket(process.env.REACT_APP_BACKEND_URL); socket.on("onlineStatus", (data) => { + // setLoading(true); - // setLoading(true); + let date = new Date().toLocaleDateString("pt-BR").split("/"); + let dateToday = `${date[2]}-${date[1]}-${date[0]}`; + // console.log('date: ', new Date(startDate).toLocaleDateString('pt-BR')) + // console.log('date2: ', startDate) - let date = new Date().toLocaleDateString('pt-BR').split('/') - let dateToday = `${date[2]}-${date[1]}-${date[0]}` - - // console.log('date: ', new Date(startDate).toLocaleDateString('pt-BR')) - // console.log('date2: ', startDate) - - - if (data.action === "logout" || (data.action === "update" && - ((`${startDate}` === `${endDate}`) && (`${endDate}` === `${dateToday}`) && (`${startDate}` === `${dateToday}`)))) { - + if ( + data.action === "logout" || + (data.action === "update" && + `${startDate}` === `${endDate}` && + `${endDate}` === `${dateToday}` && + `${startDate}` === `${dateToday}`) + ) { //console.log('UPDATE FROM ONLINE/OFFLINE LOGED USERS: ', data.userOnlineTime, ' | data.action : ', data.action) dispatchQ({ type: "UPDATE_STATUS_ONLINE", payload: data.userOnlineTime }); - - } - else if (data.action === "delete") { + } else if (data.action === "delete") { dispatchQ({ type: "DELETE_USER_STATUS", payload: data.userOnlineTime }); } // setLoading(false); - }); socket.on("user", (data) => { - if (data.action === "delete") { - // console.log(' entrou no delete user: ', data) + // console.log(' entrou no delete user: ', data) dispatch({ type: "DELETE_USER", payload: +data.userId }); } }); @@ -579,13 +481,9 @@ const Report = () => { return () => { socket.disconnect(); }; - } - - }, [reportOption, startDate, endDate]); - // const handleDeleteRows = (id) => { // let _data = [...dataRows]; @@ -593,69 +491,78 @@ const Report = () => { // _data.forEach(rd => { // _data = _data.filter(t => t.id !== id); // }); - // setData(_data); + // setData(_data); // }; - useEffect(() => { - - //if (!loading) { - + //if (!loading) { // setData(query.map(({ scheduleReminder, ...others }) => ( // { ...others, 'scheduleReminder': `${others.statusChatEndId}` === '3' ? 'Agendamento' : 'Lembrete' } // ))) // } - setData(query.map((column) => { return { ...column } })) - - }, [query]) + setData( + query.map((column) => { + return { ...column }; + }) + ); + }, [query]); const handleLogouOnlineUser = async (userId) => { try { await api.get(`/users/logout/${userId}`); //toast.success(("Desloged!")); - //handleDeleteRows(scheduleId) + //handleDeleteRows(scheduleId) } catch (err) { // toastError(err); } - - }; - return ( - ( - - + + + { + return { value: obj.id, label: obj.name }; + })} + /> + - { - return { 'value': obj.id, 'label': obj.name } - })} /> - - - - - + + + + + + + -
- - {reportOption === '1' && +
+ {reportOption === "1" && (
- @@ -663,170 +570,129 @@ const Report = () => { + filename={"Relatorio_detalhado_atendimento_atendentes.csv"} + target={"_blank"} + ref={csvLink} + />
- - } - - + )} - - - - - - - - - - {reportOption === '1' && - - + + {reportOption === "1" && ( + - } - {reportOption === '2' && - + table_title={"Atendimento por atendentes"} + /> + )} + {reportOption === "2" && ( imagem de perfil do whatsapp }, + { title: "Nome", field: "name", cellStyle: { whiteSpace: "nowrap" } }, + + { + title: "Status", + field: "statusOnline.status", + + cellStyle: (e, rowData) => { + if (rowData["statusOnline"] && rowData["statusOnline"].status) { + if (rowData["statusOnline"].status === "offline") { + return { color: "red" }; + } else if (rowData["statusOnline"].status === "online") { + return { color: "green" }; + } else if (rowData["statusOnline"].status === "logout...") { + return { color: "orange" }; + } else if (rowData["statusOnline"].status === "waiting...") { + return { color: "orange" }; + } + } + }, }, - }} - - title="Usuários online/offline" - columns={ - [ - - // { title: 'Foto', field: 'ticket.contact.profilePicUrl', render: rowData => imagem de perfil do whatsapp }, - { title: 'Nome', field: 'name', cellStyle: {whiteSpace: 'nowrap'}, }, - - { - title: 'Status', field: 'statusOnline.status', - - cellStyle: (e, rowData) => { - - if (rowData['statusOnline'] && rowData['statusOnline'].status) { - - if (rowData['statusOnline'].status === 'offline') { - - return { color: "red" }; - } - else if (rowData['statusOnline'].status === 'online') { - return { color: "green" }; - } - else if (rowData['statusOnline'].status === 'logout...') { - return { color: "orange" }; - } - else if (rowData['statusOnline'].status === 'waiting...') { - return { color: "orange" }; - } - } - - - }, - - }, - - { title: 'Tempo online', field: 'sumOnlineTime.sum' }, - { title: 'Data inicio', field: 'startDate' }, - { title: 'Data fim', field: 'endDate' }, - { title: 'Em atendimento', field: 'sumOpen.count' }, - { title: 'Finalizado', field: 'sumClosed.count' }, - - ] - } + { title: "Tempo online", field: "sumOnlineTime.sum" }, + { title: "Data inicio", field: "startDate" }, + { title: "Data fim", field: "endDate" }, + { title: "Em atendimento", field: "sumOpen.count" }, + { title: "Finalizado", field: "sumClosed.count" }, + ]} data={dataRows} // icons={tableIcons} actions={[ (rowData) => { - - if (rowData.statusOnline && - rowData.statusOnline['status'] && - rowData.statusOnline['status'] === 'online') { - - + if ( + rowData.statusOnline && + rowData.statusOnline["status"] && + rowData.statusOnline["status"] === "online" + ) { return { icon: LogoutIcon, - tooltip: 'deslogar', + tooltip: "deslogar", disable: false, onClick: (event, rowData) => { - - // console.log(' ROW DATA INFO: ', rowData, ' | rowData: ', rowData.id) - handleLogouOnlineUser(rowData.id) - } - } - - + // console.log(' ROW DATA INFO: ', rowData, ' | rowData: ', rowData.id) + handleLogouOnlineUser(rowData.id); + }, + }; } - } + }, ]} + options={{ + search: true, + selection: false, + paging: false, + padding: "dense", + sorting: true, + //loadingType: 'linear', + searchFieldStyle: { + width: 300, + }, + pageSize: 20, + headerStyle: { + position: "sticky", + top: "0", + }, + maxBodyHeight: "400px", - options={ - { - search: true, - selection: false, - paging: false, - padding: 'dense', - sorting: true, - //loadingType: 'linear', - searchFieldStyle: { - width: 300, - }, + rowStyle: { + fontSize: 14, + }, - pageSize: 20, - headerStyle: { - position: "sticky", - top: "0" - }, - maxBodyHeight: "400px", + // cellStyle: (rowData) => { + // return { + // fontSize: 12, + // color: "#fff", - rowStyle: { - fontSize: 14, - } - - - // cellStyle: (rowData) => { - // return { - // fontSize: 12, - // color: "#fff", - - // }; - // } - - - - - - - - }} + // }; + // } + }} /> - - } - + )} - - )} /> - ) + ); }; export default Report; + diff --git a/frontend/src/style/varibles.jsx b/frontend/src/style/varibles.jsx index 6fc6387..68e8e71 100644 --- a/frontend/src/style/varibles.jsx +++ b/frontend/src/style/varibles.jsx @@ -47,7 +47,7 @@ export const color = { status: { no: "#FF0000", yes: "#00BE1E", - warning: "#FFC700", + warning: "#ffc800c7", }, gradient: { bgOpacity: "#212f3cd7",