| /*eslint-disable*/ | /*eslint-disable*/ | ||||
| import React, { useState, useEffect } from "react"; | import React, { useState, useEffect } from "react"; | ||||
| import io from "socket.io-client"; | |||||
| import { Router } from "react-router-dom"; | import { Router } from "react-router-dom"; | ||||
| import { Helmet } from "react-helmet-async"; | import { Helmet } from "react-helmet-async"; | ||||
| import i18next from "i18next"; | import i18next from "i18next"; | ||||
| import GlobalStyle from "./components/Styles/globalStyles"; | import GlobalStyle from "./components/Styles/globalStyles"; | ||||
| import { ToastContainer } from "react-toastify"; | import { ToastContainer } from "react-toastify"; | ||||
| import "react-toastify/dist/ReactToastify.css"; | import "react-toastify/dist/ReactToastify.css"; | ||||
| import { socketInit } from "./socket/socket"; | |||||
| import { useSelector } from "react-redux"; | |||||
| import { selectUserId } from "./store/selectors/loginSelectors"; | |||||
| const URL = "https://trampa-api-test.dilig.net"; | |||||
| const socket2 = io("https://trampa-api-test.dilig.net", { autoConnect: true, reconnectionAttempts: 5 }); | |||||
| const socket = io("https://trampa-api-test.dilig.net", { | |||||
| autoConnect: true, | |||||
| transports: ["websocket"], | |||||
| reconnectionAttempts: 5, | |||||
| }); | |||||
| const socket4 = io("https://trampa-api-test.dilig.net", { autoConnect: true, reconnectionAttempts: 5 }); | |||||
| const socket3 = io("https://trampa-api-test.dilig.net", { | |||||
| autoConnect: true, | |||||
| transports: ["websocket"], | |||||
| reconnectionAttempts: 5, | |||||
| }); | |||||
| const App = () => { | const App = () => { | ||||
| console.log(socket); | |||||
| console.log(socket2); | |||||
| const userId = useSelector(selectUserId); | |||||
| const [isConnected, setIsConnected] = useState(socket.connected); | |||||
| const [lastPong, setLastPong] = useState(null); | |||||
| console.log(); | |||||
| useEffect(() => { | |||||
| socket.auth = { | |||||
| // userId: "62de57c6dff6f986e43d14ec", | |||||
| userId: "62ff762554ec55060e3a456b", | |||||
| sessionID: localStorage.getItem("sessionID"), | |||||
| }; | |||||
| socket.on("connect", (client) => { | |||||
| console.log("client: ", client); | |||||
| setIsConnected(true); | |||||
| }); | |||||
| socket2.on("connect", (client) => { | |||||
| console.log("client: ", client); | |||||
| setIsConnected(true); | |||||
| }); | |||||
| socket3.on("connect", (client) => { | |||||
| console.log("client: ", client); | |||||
| setIsConnected(true); | |||||
| }); | |||||
| socket4.on("connect", (client) => { | |||||
| console.log("client: ", client); | |||||
| setIsConnected(true); | |||||
| }); | |||||
| socket.on("session", ({ sessionID, userID }) => { | |||||
| localStorage.setItem("sessionID", sessionID); | |||||
| localStorage.setItem("userID", userID); | |||||
| console.log("sessionID: ", sessionID); | |||||
| console.log("userID: ", userID); | |||||
| }); | |||||
| // socket.on("connect_error", (err) => { | |||||
| // console.log(err); | |||||
| // }); | |||||
| socketInit(userId); | |||||
| socket.on("connection", (client) => { | |||||
| console.log(client); | |||||
| }); | |||||
| socket.on("disconnect", () => { | |||||
| setIsConnected(false); | |||||
| }); | |||||
| // socket.on("user disconnected", (userID) => { | |||||
| // console.log(userID); | |||||
| // }); | |||||
| // // socket.on('emit', (client) => { | |||||
| // // console.log(client); | |||||
| // // }) | |||||
| // socket.on("sokkk", (clg) => { | |||||
| // console.log(clg); | |||||
| // }); | |||||
| // // socket.onAny((event, ...args) => { | |||||
| // // console.log(event, args); | |||||
| // // }); | |||||
| // socket.on("povratna", (data) => { | |||||
| // console.log(data); | |||||
| // }); | |||||
| // socket.on("private_message", (data) => { | |||||
| // console.log(data); | |||||
| // }); | |||||
| // // socket.open; | |||||
| // socket.on("pong", () => { | |||||
| // setLastPong(new Date().toISOString()); | |||||
| // }); | |||||
| // // socket.connect(); | |||||
| return () => { | |||||
| socket.off("connect"); | |||||
| socket.off("disconnect"); | |||||
| socket.off("pong"); | |||||
| socket.off("reconnection_attempt") | |||||
| }; | |||||
| }, []); | |||||
| const handleClick = () => { | |||||
| // socket.connect(); | |||||
| // socket.emit("sokkk 2", "sock"); | |||||
| // socket.emit("sock") | |||||
| }; | |||||
| const sendPing = () => { | |||||
| socket.emit("private_message", { | |||||
| text: "Probica", | |||||
| // toUserId: "62de5844dff6f986e43d14f6", | |||||
| toUserId: "62de57c6dff6f986e43d14ec", | |||||
| chatId: "62eb8424632e1112ef467750", | |||||
| }); | |||||
| }; | |||||
| const disconnect = () => { | |||||
| // socket.disconnect(); | |||||
| socket.disconnect(); | |||||
| }; | |||||
| return ( | return ( | ||||
| <Router history={history}> | <Router history={history}> | ||||
| <Helmet> | <Helmet> | ||||
| <Header /> | <Header /> | ||||
| <GlobalStyle /> | <GlobalStyle /> | ||||
| <ToastContainer /> | <ToastContainer /> | ||||
| {/* <div style={{ position: "relative", top: "100px", left: "400px" }}> | |||||
| <p>Connected: {"" + isConnected}</p> | |||||
| <br /> | |||||
| <p>Last pong: {lastPong || "-"}</p> | |||||
| <br /> | |||||
| <button onClick={sendPing}>Send ping</button> | |||||
| <br /> | |||||
| <button onClick={disconnect}>Disconnect</button> | |||||
| </div> */} | |||||
| <AppRoutes /> | <AppRoutes /> | ||||
| </StyledEngineProvider> | </StyledEngineProvider> | ||||
| </Router> | </Router> |
| import OfferLocation from "./OfferLocation/OfferLocation"; | import OfferLocation from "./OfferLocation/OfferLocation"; | ||||
| import ChatCommands from "./ChatCommands/ChatCommands"; | import ChatCommands from "./ChatCommands/ChatCommands"; | ||||
| import useIsMobile from "../../../hooks/useIsMobile"; | import useIsMobile from "../../../hooks/useIsMobile"; | ||||
| import { getImageUrl, variants } from "../../../util/helpers/imageUrlGetter"; | |||||
| const ChatCard = (props) => { | const ChatCard = (props) => { | ||||
| const history = useHistory(); | const history = useHistory(); | ||||
| > | > | ||||
| <Col> | <Col> | ||||
| <UserImgWrapper> | <UserImgWrapper> | ||||
| <UserImage src={chat?.interlocutorData?.image} /> | |||||
| {/* <UserImage src={chat?.interlocutorData?.image} /> */} | |||||
| <UserImage src={getImageUrl(chat?.interlocutorData?.image, variants.chatCard, isMobile)} /> | |||||
| </UserImgWrapper> | </UserImgWrapper> | ||||
| <ChatInfo> | <ChatInfo> |
| } from "./LittleOfferDetails.styled"; | } from "./LittleOfferDetails.styled"; | ||||
| import { useTranslation } from "react-i18next"; | import { useTranslation } from "react-i18next"; | ||||
| import { Col } from "../ChatCard.styled"; | import { Col } from "../ChatCard.styled"; | ||||
| import { getImageUrl, variants } from "../../../../util/helpers/imageUrlGetter"; | |||||
| import useIsMobile from "../../../../hooks/useIsMobile"; | |||||
| const LittleOfferDetails = (props) => { | const LittleOfferDetails = (props) => { | ||||
| const chat = props.chat; | const chat = props.chat; | ||||
| const { t } = useTranslation(); | const { t } = useTranslation(); | ||||
| const { isMobile } = useIsMobile(); | |||||
| return ( | return ( | ||||
| <Col mobileDisappear> | <Col mobileDisappear> | ||||
| <ChatOffer> | <ChatOffer> | ||||
| <OfferImgWrapper> | <OfferImgWrapper> | ||||
| <OfferImage src={chat?.offerData?.firstImage} /> | |||||
| {/* <OfferImage src={chat?.offerData?.firstImage} /> */} | |||||
| <OfferImage | |||||
| src={getImageUrl( | |||||
| chat?.offerData?.firstImage, | |||||
| variants.offerCard, | |||||
| isMobile | |||||
| )} | |||||
| /> | |||||
| </OfferImgWrapper> | </OfferImgWrapper> | ||||
| <OfferCardContainer> | <OfferCardContainer> | ||||
| <OfferText>{t("messages.cardProduct")}</OfferText> | <OfferText>{t("messages.cardProduct")}</OfferText> |
| .filter((img) => img !== undefined) | .filter((img) => img !== undefined) | ||||
| .map((img) => | .map((img) => | ||||
| img | img | ||||
| .replace("data:image/jpg;base64,", "") | |||||
| .replace("data:image/jpeg;base64,", "") | |||||
| .replace("data:image/png;base64,", "") | |||||
| // .replace("data:image/jpg;base64,", "") | |||||
| // .replace("data:image/jpeg;base64,", "") | |||||
| // .replace("data:image/png;base64,", "") | |||||
| ); | ); | ||||
| const offerData = { | const offerData = { |
| import { useTranslation } from "react-i18next"; | import { useTranslation } from "react-i18next"; | ||||
| import useScreenDimensions from "../../../../hooks/useScreenDimensions"; | import useScreenDimensions from "../../../../hooks/useScreenDimensions"; | ||||
| import { formatDateLocale } from "../../../../util/helpers/dateHelpers"; | import { formatDateLocale } from "../../../../util/helpers/dateHelpers"; | ||||
| import useIsMobile from "../../../../hooks/useIsMobile"; | |||||
| import { getImageUrl, variants } from "../../../../util/helpers/imageUrlGetter"; | |||||
| const OfferDetails = (props) => { | const OfferDetails = (props) => { | ||||
| const offer = props.offer; | const offer = props.offer; | ||||
| const { t } = useTranslation(); | const { t } = useTranslation(); | ||||
| const dimension = useScreenDimensions(); | const dimension = useScreenDimensions(); | ||||
| const { isMobile } = useIsMobile(); | |||||
| const date = formatDateLocale(new Date(offer?.offer?._created)); | const date = formatDateLocale(new Date(offer?.offer?._created)); | ||||
| return ( | return ( | ||||
| <Details | <Details | ||||
| > | > | ||||
| {dimension.width < 600 || !props.singleOffer ? ( | {dimension.width < 600 || !props.singleOffer ? ( | ||||
| <ScrollerHorizontal> | <ScrollerHorizontal> | ||||
| {offer?.offer?.images?.map((item) => { | |||||
| return <OfferImage src={item} key={item} />; | |||||
| })} | |||||
| {offer?.offer?.images?.map((item) => ( | |||||
| <OfferImage | |||||
| src={getImageUrl(item, variants.offerCard, isMobile)} | |||||
| key={item} | |||||
| /> | |||||
| ))} | |||||
| </ScrollerHorizontal> | </ScrollerHorizontal> | ||||
| ) : ( | ) : ( | ||||
| <ScrollerVertical> | <ScrollerVertical> | ||||
| {offer?.offer?.images?.map((item) => { | |||||
| return <OfferImage src={item} key={item} />; | |||||
| })} | |||||
| {offer?.offer?.images?.map((item) => ( | |||||
| <OfferImage | |||||
| src={getImageUrl(item, variants.offerCard, isMobile)} | |||||
| key={item} | |||||
| /> | |||||
| ))} | |||||
| </ScrollerVertical> | </ScrollerVertical> | ||||
| )} | )} | ||||
| <OfferInfoContainer singleOffer={props.singleOffer}> | <OfferInfoContainer singleOffer={props.singleOffer}> |
| import React from 'react' | |||||
| import PropTypes from 'prop-types' | |||||
| import { LittleOfferCardContainer, OfferCategory, OfferCategoryIcon, OfferDetails, OfferImage, OfferName, OfferSwapsIcon, OfferSwapsIconContainer } from './LittleOfferCard.styled' | |||||
| import React from "react"; | |||||
| import PropTypes from "prop-types"; | |||||
| import { | |||||
| LittleOfferCardContainer, | |||||
| OfferCategory, | |||||
| OfferCategoryIcon, | |||||
| OfferDetails, | |||||
| OfferImage, | |||||
| OfferName, | |||||
| OfferSwapsIcon, | |||||
| OfferSwapsIconContainer, | |||||
| } from "./LittleOfferCard.styled"; | |||||
| import useIsMobile from "../../../hooks/useIsMobile"; | |||||
| import { getImageUrl, variants } from "../../../util/helpers/imageUrlGetter"; | |||||
| const LittleOfferCard = (props) => { | const LittleOfferCard = (props) => { | ||||
| return ( | |||||
| <LittleOfferCardContainer> | |||||
| <OfferImage src={props.image} /> | |||||
| <OfferDetails> | |||||
| <OfferName>{props.name}</OfferName> | |||||
| <OfferCategory> | |||||
| <OfferCategoryIcon /> | |||||
| {props.categoryName}</OfferCategory> | |||||
| </OfferDetails> | |||||
| <OfferSwapsIconContainer> | |||||
| <OfferSwapsIcon /> | |||||
| </OfferSwapsIconContainer> | |||||
| </LittleOfferCardContainer> | |||||
| ) | |||||
| } | |||||
| const { isMobile } = useIsMobile(); | |||||
| return ( | |||||
| <LittleOfferCardContainer> | |||||
| {/* <OfferImage src={props.image} /> */} | |||||
| <OfferImage | |||||
| src={getImageUrl(props.image, variants.reviewCard, isMobile)} | |||||
| /> | |||||
| <OfferDetails> | |||||
| <OfferName>{props.name}</OfferName> | |||||
| <OfferCategory> | |||||
| <OfferCategoryIcon /> | |||||
| {props.categoryName} | |||||
| </OfferCategory> | |||||
| </OfferDetails> | |||||
| <OfferSwapsIconContainer> | |||||
| <OfferSwapsIcon /> | |||||
| </OfferSwapsIconContainer> | |||||
| </LittleOfferCardContainer> | |||||
| ); | |||||
| }; | |||||
| LittleOfferCard.propTypes = { | LittleOfferCard.propTypes = { | ||||
| image: PropTypes.string, | |||||
| name: PropTypes.string, | |||||
| categoryName: PropTypes.string, | |||||
| } | |||||
| image: PropTypes.string, | |||||
| name: PropTypes.string, | |||||
| categoryName: PropTypes.string, | |||||
| }; | |||||
| export default LittleOfferCard | |||||
| export default LittleOfferCard; |
| ProfileImage, | ProfileImage, | ||||
| } from "./MessageCard.styled"; | } from "./MessageCard.styled"; | ||||
| import { formatDateTime } from "../../../util/helpers/dateHelpers"; | import { formatDateTime } from "../../../util/helpers/dateHelpers"; | ||||
| import useIsMobile from "../../../hooks/useIsMobile"; | |||||
| import { getImageUrl, variants } from "../../../util/helpers/imageUrlGetter"; | |||||
| const MessageCard = (props) => { | const MessageCard = (props) => { | ||||
| const message = props.message; | const message = props.message; | ||||
| const { isMobile } = useIsMobile(); | |||||
| const dateString = formatDateTime(new Date(message._created)); | const dateString = formatDateTime(new Date(message._created)); | ||||
| return ( | return ( | ||||
| <MessageCardContainer isMyMessage={props.isMyMessage}> | <MessageCardContainer isMyMessage={props.isMyMessage}> | ||||
| <ProfileImage src={props.image} /> | |||||
| {/* <ProfileImage src={props.image} /> */} | |||||
| <ProfileImage | |||||
| src={getImageUrl(props.image, variants.chatMessage, isMobile)} | |||||
| /> | |||||
| <MessageContent isMyMessage={props.isMyMessage}> | <MessageContent isMyMessage={props.isMyMessage}> | ||||
| <MessageText isMyMessage={props.isMyMessage}> | <MessageText isMyMessage={props.isMyMessage}> | ||||
| {props.message.text} | {props.message.text} |
| } from "./MiniChatCard.styled"; | } from "./MiniChatCard.styled"; | ||||
| import { useTranslation } from "react-i18next"; | import { useTranslation } from "react-i18next"; | ||||
| import { useHistory } from "react-router-dom"; | import { useHistory } from "react-router-dom"; | ||||
| import useIsMobile from "../../../hooks/useIsMobile"; | |||||
| import { getImageUrl, variants } from "../../../util/helpers/imageUrlGetter"; | |||||
| const MiniChatCard = (props) => { | const MiniChatCard = (props) => { | ||||
| const { t } = useTranslation(); | const { t } = useTranslation(); | ||||
| const history = useHistory(); | const history = useHistory(); | ||||
| const { isMobile } = useIsMobile(); | |||||
| const changeChat = () => { | const changeChat = () => { | ||||
| history.push(`/messages/${props?.chat?.chat?._id}`); | history.push(`/messages/${props?.chat?.chat?._id}`); | ||||
| }; | }; | ||||
| return ( | return ( | ||||
| <MiniChatCardContainer selected={props.selected} onClick={changeChat}> | <MiniChatCardContainer selected={props.selected} onClick={changeChat}> | ||||
| <ProfileImage src={props?.chat?.interlocutorData?.image} /> | |||||
| {/* <ProfileImage src={props?.chat?.interlocutorData?.image} /> */} | |||||
| <ProfileImage | |||||
| src={getImageUrl( | |||||
| props?.chat?.interlocutorData?.image, | |||||
| variants.chatCard, | |||||
| isMobile | |||||
| )} | |||||
| /> | |||||
| <ProfileDetails> | <ProfileDetails> | ||||
| <ProfileName selected={props.selected}> | <ProfileName selected={props.selected}> | ||||
| {props?.chat?.interlocutorData?.name} | {props?.chat?.interlocutorData?.name} |
| } from "../../../../store/actions/offers/offersActions"; | } from "../../../../store/actions/offers/offersActions"; | ||||
| import { useTranslation, Trans } from "react-i18next"; | import { useTranslation, Trans } from "react-i18next"; | ||||
| import { useHistory } from "react-router-dom"; | import { useHistory } from "react-router-dom"; | ||||
| import useIsMobile from "../../../../hooks/useIsMobile"; | |||||
| import { getImageUrl, variants } from "../../../../util/helpers/imageUrlGetter"; | |||||
| const DeleteOffer = (props) => { | const DeleteOffer = (props) => { | ||||
| const dispatch = useDispatch(); | const dispatch = useDispatch(); | ||||
| const { t } = useTranslation(); | const { t } = useTranslation(); | ||||
| const history = useHistory(); | const history = useHistory(); | ||||
| const userId = props.offer.userId; | const userId = props.offer.userId; | ||||
| const { isMobile } = useIsMobile(); | |||||
| const offerId = props.offer._id; | const offerId = props.offer._id; | ||||
| const closeDeleteModalHandler = () => { | const closeDeleteModalHandler = () => { | ||||
| props.closeModalHandler(); | props.closeModalHandler(); | ||||
| <DeleteOfferContainer> | <DeleteOfferContainer> | ||||
| <OfferInfo> | <OfferInfo> | ||||
| <OfferImageContainer> | <OfferImageContainer> | ||||
| <OfferImage src={props.offer.images[0]} /> | |||||
| {/* <OfferImage src={props.offer.images[0]} /> */} | |||||
| <OfferImage | |||||
| src={getImageUrl( | |||||
| props.offer.images[0], | |||||
| variants.deleteChat, | |||||
| isMobile | |||||
| )} | |||||
| /> | |||||
| </OfferImageContainer> | </OfferImageContainer> | ||||
| <OfferDescription> | <OfferDescription> | ||||
| <OfferDescriptionTitle>{props.offer.name}</OfferDescriptionTitle> | <OfferDescriptionTitle>{props.offer.name}</OfferDescriptionTitle> |
| import CreateOffer from "../CreateOfferCard/CreateOffer"; | import CreateOffer from "../CreateOfferCard/CreateOffer"; | ||||
| import { useSelector } from "react-redux"; | import { useSelector } from "react-redux"; | ||||
| import { selectUserId } from "../../../store/selectors/loginSelectors"; | import { selectUserId } from "../../../store/selectors/loginSelectors"; | ||||
| import useIsMobile from "../../../hooks/useIsMobile"; | |||||
| import { getImageUrl, variants } from "../../../util/helpers/imageUrlGetter"; | |||||
| const OfferCard = (props) => { | const OfferCard = (props) => { | ||||
| const [deleteOfferModal, setDeleteOfferModal] = useState(false); | const [deleteOfferModal, setDeleteOfferModal] = useState(false); | ||||
| const [editOfferModal, setEditOfferModal] = useState(false); | const [editOfferModal, setEditOfferModal] = useState(false); | ||||
| const history = useHistory(); | const history = useHistory(); | ||||
| const userId = useSelector(selectUserId); | const userId = useSelector(selectUserId); | ||||
| const { isMobile } = useIsMobile(); | |||||
| const routeToItem = (itemId) => { | const routeToItem = (itemId) => { | ||||
| history.push(`/proizvodi/${itemId}`); | history.push(`/proizvodi/${itemId}`); | ||||
| <OfferFlexContainer vertical={props.vertical}> | <OfferFlexContainer vertical={props.vertical}> | ||||
| <OfferImageContainer vertical={props.vertical}> | <OfferImageContainer vertical={props.vertical}> | ||||
| <OfferImage | <OfferImage | ||||
| src={props?.offer?.images ? props?.offer?.images[0] : ""} | |||||
| src={ | |||||
| props?.offer?.images | |||||
| ? getImageUrl( | |||||
| props?.offer?.images[0], | |||||
| variants.offerCard, | |||||
| isMobile | |||||
| ) | |||||
| : "" | |||||
| } | |||||
| vertical={props.vertical} | vertical={props.vertical} | ||||
| ></OfferImage> | ></OfferImage> | ||||
| </OfferImageContainer> | </OfferImageContainer> |
| import { ListItem } from "@mui/material"; | import { ListItem } from "@mui/material"; | ||||
| import selectedTheme from "../../../themes"; | import selectedTheme from "../../../themes"; | ||||
| import { useTranslation } from "react-i18next"; | import { useTranslation } from "react-i18next"; | ||||
| import useIsMobile from "../../../hooks/useIsMobile"; | |||||
| import { getImageUrl, variants } from "../../../util/helpers/imageUrlGetter"; | |||||
| const UserReviewsCard = (props) => { | const UserReviewsCard = (props) => { | ||||
| const { t } = useTranslation(); | const { t } = useTranslation(); | ||||
| const {isMobile} = useIsMobile() | |||||
| const review = useMemo(() => { | const review = useMemo(() => { | ||||
| if (props.givingReview) { | if (props.givingReview) { | ||||
| <ReviewContainer key={review?.image}> | <ReviewContainer key={review?.image}> | ||||
| <ListItem alignItems="flex-start" sx={{ alignItems: "center", mt: 2 }}> | <ListItem alignItems="flex-start" sx={{ alignItems: "center", mt: 2 }}> | ||||
| <ProfileImageContainer> | <ProfileImageContainer> | ||||
| <ProfileImage alt={review?.name} src={review?.image} /> | |||||
| {/* <ProfileImage alt={review?.name} src={review?.image} /> */} | |||||
| <ProfileImage src={getImageUrl(review?.image, variants.reviewCard, isMobile)} /> | |||||
| </ProfileImageContainer> | </ProfileImageContainer> | ||||
| <ProfileName sx={{ color: selectedTheme.primaryPurple }}> | <ProfileName sx={{ color: selectedTheme.primaryPurple }}> | ||||
| <b>{review?.name}</b> | <b>{review?.name}</b> |
| import { useTranslation } from "react-i18next"; | import { useTranslation } from "react-i18next"; | ||||
| import { useDispatch, useSelector } from "react-redux"; | import { useDispatch, useSelector } from "react-redux"; | ||||
| import { selectLatestChats } from "../../store/selectors/chatSelectors"; | import { selectLatestChats } from "../../store/selectors/chatSelectors"; | ||||
| import { fetchChats } from "../../store/actions/chat/chatActions"; | |||||
| import { addNewMessage, fetchChats } from "../../store/actions/chat/chatActions"; | |||||
| import useSorting from "../../hooks/useOffers/useSorting"; | import useSorting from "../../hooks/useOffers/useSorting"; | ||||
| import { addMesageListener, removeMessageListener } from "../../socket/socket"; | |||||
| export const DownArrow = (props) => { | export const DownArrow = (props) => { | ||||
| <IconStyled {...props}> | <IconStyled {...props}> | ||||
| dispatch(fetchChats()); | dispatch(fetchChats()); | ||||
| }, []); | }, []); | ||||
| useEffect(() => { | |||||
| addMesageListener((data) => { | |||||
| dispatch(addNewMessage({ | |||||
| _id: data.chatId, | |||||
| message: data.message | |||||
| })) | |||||
| }); | |||||
| return () => removeMessageListener(); | |||||
| }, []) | |||||
| useEffect(() => { | useEffect(() => { | ||||
| setSortOption(sorting.selectedSortOption); | setSortOption(sorting.selectedSortOption); | ||||
| }, [sorting.selectedSortOption]); | }, [sorting.selectedSortOption]); |
| import DirectChatHeader from "./DirectChatHeader/DirectChatHeader"; | import DirectChatHeader from "./DirectChatHeader/DirectChatHeader"; | ||||
| import { useDispatch, useSelector } from "react-redux"; | import { useDispatch, useSelector } from "react-redux"; | ||||
| import { useLocation, useRouteMatch } from "react-router-dom"; | import { useLocation, useRouteMatch } from "react-router-dom"; | ||||
| import { fetchOneChat, setOneChat } from "../../store/actions/chat/chatActions"; | |||||
| import { addNewMessage, fetchOneChat, setOneChat } from "../../store/actions/chat/chatActions"; | |||||
| import { selectSelectedChat } from "../../store/selectors/chatSelectors"; | import { selectSelectedChat } from "../../store/selectors/chatSelectors"; | ||||
| import DirectChatContent from "./DirectChatContent/DirectChatContent"; | import DirectChatContent from "./DirectChatContent/DirectChatContent"; | ||||
| import { selectOffer } from "../../store/selectors/offersSelectors"; | import { selectOffer } from "../../store/selectors/offersSelectors"; | ||||
| import SkeletonDirectChat from "./SkeletonDirectChat/SkeletonDirectChat"; | import SkeletonDirectChat from "./SkeletonDirectChat/SkeletonDirectChat"; | ||||
| import { selectIsLoadingByActionType } from "../../store/selectors/loadingSelectors"; | import { selectIsLoadingByActionType } from "../../store/selectors/loadingSelectors"; | ||||
| import { CHAT_SCOPE } from "../../store/actions/chat/chatActionConstants"; | import { CHAT_SCOPE } from "../../store/actions/chat/chatActionConstants"; | ||||
| import { selectUserId } from "../../store/selectors/loginSelectors"; | |||||
| import { addMesageListener, removeMessageListener } from "../../socket/socket"; | |||||
| const DirectChat = () => { | const DirectChat = () => { | ||||
| const chat = useSelector(selectSelectedChat); | const chat = useSelector(selectSelectedChat); | ||||
| const routeMatch = useRouteMatch(); | const routeMatch = useRouteMatch(); | ||||
| const location = useLocation(); | const location = useLocation(); | ||||
| const dispatch = useDispatch(); | const dispatch = useDispatch(); | ||||
| const userId = useSelector(selectUserId); | |||||
| const isLoadingDirectChat = useSelector( | const isLoadingDirectChat = useSelector( | ||||
| selectIsLoadingByActionType(CHAT_SCOPE) | selectIsLoadingByActionType(CHAT_SCOPE) | ||||
| ); | ); | ||||
| }, [chat, location.state]); | }, [chat, location.state]); | ||||
| const interlocutorObject = useMemo(() => { | const interlocutorObject = useMemo(() => { | ||||
| console.log("offer", offer); | |||||
| console.log("chat", chat); | |||||
| if (location?.state?.offerId) { | if (location?.state?.offerId) { | ||||
| return { | return { | ||||
| image: offer?.companyData?.image, | image: offer?.companyData?.image, | ||||
| name: offer?.companyData?.company?.name, | name: offer?.companyData?.company?.name, | ||||
| location: offer?.companyData?.company?.contacts?.location, | location: offer?.companyData?.company?.contacts?.location, | ||||
| userId: offer?.offer?.userId | |||||
| }; | }; | ||||
| } | } | ||||
| return chat?.interlocutor; | |||||
| return { | |||||
| ...chat?.interlocutor, | |||||
| userId: chat?.chat?.participants[0] === userId ? chat?.chat?.participants[1] : chat?.chat?.participants[0] | |||||
| }; | |||||
| }, [chat, location.state, offer]); | }, [chat, location.state, offer]); | ||||
| useEffect(() => { | useEffect(() => { | ||||
| } | } | ||||
| }, [routeMatch.params.idChat, location.state?.offerId]); | }, [routeMatch.params.idChat, location.state?.offerId]); | ||||
| useEffect(() => { | |||||
| addMesageListener((data) => { | |||||
| dispatch(addNewMessage({ | |||||
| _id: data.chatId, | |||||
| message: data.message | |||||
| })) | |||||
| }); | |||||
| return () => removeMessageListener(); | |||||
| }, []) | |||||
| const refreshChat = () => { | const refreshChat = () => { | ||||
| if (routeMatch.params.idChat === "newMessage") { | if (routeMatch.params.idChat === "newMessage") { | ||||
| dispatch(fetchOneOffer(location.state.offerId)); | dispatch(fetchOneOffer(location.state.offerId)); |
| props.refreshChat(); | props.refreshChat(); | ||||
| }; | }; | ||||
| useEffect(() => { | useEffect(() => { | ||||
| const offsetBottom = | |||||
| messagesRef.current?.offsetTop + messagesRef.current?.offsetHeight; | |||||
| messagesRef.current?.scrollTo({ top: offsetBottom, behaviour: "smooth" }); | |||||
| console.dir(messagesRef.current) | |||||
| // const offsetBottom = | |||||
| // messagesRef.current?.offsetTop + messagesRef.current?.offsetHeight; | |||||
| messagesRef.current?.scrollTo({ top: messagesRef.current.scrollHeight, behaviour: "smooth" }); | |||||
| }, [messages]); | }, [messages]); | ||||
| return ( | return ( | ||||
| <> | <> | ||||
| ? myProfileImage | ? myProfileImage | ||||
| : interlucatorProfileImage; | : interlucatorProfileImage; | ||||
| return ( | return ( | ||||
| <MessageContainer key={item?._id}> | |||||
| <MessageContainer key={item?._id || item?._created}> | |||||
| <MessageCard | <MessageCard | ||||
| message={item} | message={item} | ||||
| image={image} | image={image} | ||||
| <DirectChatNewMessage | <DirectChatNewMessage | ||||
| chatId={props?.chat?._id} | chatId={props?.chat?._id} | ||||
| refreshChat={handleRefresh} | refreshChat={handleRefresh} | ||||
| interlucator={props.interlucator} | |||||
| /> | /> | ||||
| </DirectChatContentContainer> | </DirectChatContentContainer> | ||||
| )} | )} |
| } from "./DirectChatContentHeader.styled"; | } from "./DirectChatContentHeader.styled"; | ||||
| import PopoverComponent from "../../../Popovers/PopoverComponent"; | import PopoverComponent from "../../../Popovers/PopoverComponent"; | ||||
| import PhonePopover from "../../../Popovers/PhonePopover/PhonePopover"; | import PhonePopover from "../../../Popovers/PhonePopover/PhonePopover"; | ||||
| import { getImageUrl, variants } from "../../../../util/helpers/imageUrlGetter"; | |||||
| import useIsMobile from "../../../../hooks/useIsMobile"; | |||||
| const DirectChatContentHeader = (props) => { | const DirectChatContentHeader = (props) => { | ||||
| const [showPhonePopover, setShowPhonePopover] = useState(false); | const [showPhonePopover, setShowPhonePopover] = useState(false); | ||||
| const [phonePopoverAnchorEl, setPhonePopoverAnchorEl] = useState(null); | const [phonePopoverAnchorEl, setPhonePopoverAnchorEl] = useState(null); | ||||
| const { isMobile } = useIsMobile(); | |||||
| const togglePhonePopover = (event) => { | const togglePhonePopover = (event) => { | ||||
| console.log(event); | |||||
| setShowPhonePopover(true); | |||||
| setPhonePopoverAnchorEl(event.currentTarget); | |||||
| } | |||||
| console.log(event); | |||||
| setShowPhonePopover(true); | |||||
| setPhonePopoverAnchorEl(event.currentTarget); | |||||
| }; | |||||
| return ( | return ( | ||||
| <DirectChatContentHeaderContainer> | <DirectChatContentHeaderContainer> | ||||
| <DirectChatContentHeaderFlexContainer> | <DirectChatContentHeaderFlexContainer> | ||||
| <ProfileImage src={props?.interlucator?.image} /> | |||||
| {/* <ProfileImage src={props?.interlucator?.image} /> */} | |||||
| <ProfileImage | |||||
| src={getImageUrl( | |||||
| props?.interlucator?.image, | |||||
| variants.chatHeader, | |||||
| isMobile | |||||
| )} | |||||
| /> | |||||
| <ProfileDetails> | <ProfileDetails> | ||||
| <ProfileName>{props?.interlucator?.name}</ProfileName> | <ProfileName>{props?.interlucator?.name}</ProfileName> | ||||
| <ProfileLocation> | <ProfileLocation> |
| import { useTranslation } from "react-i18next"; | import { useTranslation } from "react-i18next"; | ||||
| import selectedTheme from "../../../themes"; | import selectedTheme from "../../../themes"; | ||||
| import { useDispatch } from "react-redux"; | import { useDispatch } from "react-redux"; | ||||
| // import { | |||||
| // fetchChats, | |||||
| // startNewChat, | |||||
| // } from "../../../store/actions/chat/chatActions"; | |||||
| // import { useHistory, useLocation } from "react-router-dom"; | |||||
| import { sendMessage } from "../../../socket/socket"; | |||||
| import { useSelector } from "react-redux"; | |||||
| import { selectUserId } from "../../../store/selectors/loginSelectors"; | |||||
| import { | import { | ||||
| addNewMessage, | |||||
| fetchChats, | fetchChats, | ||||
| sendMessage, | |||||
| startNewChat, | startNewChat, | ||||
| } from "../../../store/actions/chat/chatActions"; | } from "../../../store/actions/chat/chatActions"; | ||||
| import { useHistory, useLocation } from "react-router-dom"; | import { useHistory, useLocation } from "react-router-dom"; | ||||
| // import { selectUserId } from "../../../store/selectors/loginSelectors"; | |||||
| const DirectChatNewMessage = (props) => { | const DirectChatNewMessage = (props) => { | ||||
| const [typedValue, setTypedValue] = useState(""); | const [typedValue, setTypedValue] = useState(""); | ||||
| const [isFocused, setIsFocused] = useState(false); | const [isFocused, setIsFocused] = useState(false); | ||||
| console.log(props); | |||||
| const dispatch = useDispatch(); | const dispatch = useDispatch(); | ||||
| const { t } = useTranslation(); | const { t } = useTranslation(); | ||||
| const location = useLocation(); | const location = useLocation(); | ||||
| const history = useHistory(); | const history = useHistory(); | ||||
| const handleApiResponseSuccess = () => { | |||||
| props.refreshChat(); | |||||
| }; | |||||
| // const handleApiResponseSuccess = () => { | |||||
| // props.refreshChat(); | |||||
| // }; | |||||
| const userId = useSelector(selectUserId); | |||||
| const handleSend = useCallback(() => { | const handleSend = useCallback(() => { | ||||
| if (location.state?.offerId) { | |||||
| initiateNewChat(typedValue); | |||||
| } else { | |||||
| // if (location.state?.offerId) { | |||||
| // initiateNewChat(typedValue); | |||||
| // } else { | |||||
| // dispatch( | |||||
| // sendMessage({ | |||||
| // message: typedValue, | |||||
| // chatId: props.chatId, | |||||
| // handleApiResponseSuccess, | |||||
| // }) | |||||
| // ); | |||||
| // } | |||||
| console.log(props.chatId, typedValue, props.interlucator.userId); | |||||
| if (props.chatId) { | |||||
| sendMessage(props.chatId, userId, typedValue, props.interlucator.userId); | |||||
| dispatch( | dispatch( | ||||
| sendMessage({ | |||||
| message: typedValue, | |||||
| chatId: props.chatId, | |||||
| handleApiResponseSuccess, | |||||
| addNewMessage({ | |||||
| _id: props.chatId, | |||||
| message: { | |||||
| userId, | |||||
| text: typedValue, | |||||
| _created: new Date().toISOString(), | |||||
| }, | |||||
| }) | }) | ||||
| ); | ); | ||||
| } else { | |||||
| initiateNewChat(typedValue); | |||||
| } | } | ||||
| // socket.emit("private_message", { | |||||
| // chatId: props.chatId, | |||||
| // receiverUserId: props.interlucator.userId, | |||||
| // message: typedValue | |||||
| // // message: { | |||||
| // // userId: userId, | |||||
| // // text: typedValue, | |||||
| // // receiverUserId: props.interlucator.userId | |||||
| // // } | |||||
| // }) | |||||
| setTypedValue(""); | setTypedValue(""); | ||||
| }, [typedValue]); | |||||
| }, [typedValue, props.chatId, userId, props.interlucator.userId]); | |||||
| const handleMessageSendSuccess = (newChatId) => { | const handleMessageSendSuccess = (newChatId) => { | ||||
| history.replace(`${newChatId}`); | history.replace(`${newChatId}`); | ||||
| dispatch(fetchChats()); | dispatch(fetchChats()); | ||||
| children: PropTypes.node, | children: PropTypes.node, | ||||
| chatId: PropTypes.any, | chatId: PropTypes.any, | ||||
| refreshChat: PropTypes.func, | refreshChat: PropTypes.func, | ||||
| interlucator: PropTypes.any, | |||||
| }; | }; | ||||
| export default DirectChatNewMessage; | export default DirectChatNewMessage; |
| color: selectedTheme.primaryPurple, | color: selectedTheme.primaryPurple, | ||||
| }} | }} | ||||
| > | > | ||||
| <Badge badgeContent={3} color="primary"> | |||||
| <Badge color="primary"> | |||||
| <MailIcon /> | <MailIcon /> | ||||
| </Badge> | </Badge> | ||||
| </IconButton> | </IconButton> |
| import { IconButton } from "../Buttons/IconButton/IconButton"; | import { IconButton } from "../Buttons/IconButton/IconButton"; | ||||
| import { ReactComponent as EditIcon } from "../../assets/images/svg/edit.svg"; | import { ReactComponent as EditIcon } from "../../assets/images/svg/edit.svg"; | ||||
| import { ReactComponent as TrashIcon } from "../../assets/images/svg/trash.svg"; | import { ReactComponent as TrashIcon } from "../../assets/images/svg/trash.svg"; | ||||
| import { getImageUrl, variants } from "../../util/helpers/imageUrlGetter"; | |||||
| const ImagePicker = (props) => { | const ImagePicker = (props) => { | ||||
| const fileInputRef = useRef(null); | const fileInputRef = useRef(null); | ||||
| const [isEditing, setIsEditing] = useState(false); | const [isEditing, setIsEditing] = useState(false); | ||||
| useEffect(() => { | useEffect(() => { | ||||
| if (props.image) | |||||
| setImage(props.image); | |||||
| }, [props.image]); | |||||
| let listener = useCallback((event) => { | |||||
| if (imageRef.current) { | |||||
| if (imageRef.current.contains(event.target)) { | |||||
| setIsEditing(true); | |||||
| if (props.image) { | |||||
| if (typeof props.image === 'string') { | |||||
| setImage(getImageUrl(props.image, variants.offerCard)) | |||||
| } else { | } else { | ||||
| setIsEditing(false); | |||||
| handleImage(props.image); | |||||
| } | } | ||||
| } | } | ||||
| }, [imageRef.current]) | |||||
| }, [props.image]); | |||||
| let listener = useCallback( | |||||
| (event) => { | |||||
| if (imageRef.current) { | |||||
| if (imageRef.current.contains(event.target)) { | |||||
| setIsEditing(true); | |||||
| } else { | |||||
| setIsEditing(false); | |||||
| } | |||||
| } | |||||
| }, | |||||
| [imageRef.current] | |||||
| ); | |||||
| useEffect(() => { | useEffect(() => { | ||||
| window.addEventListener("click", listener); | window.addEventListener("click", listener); | ||||
| return () => window.removeEventListener("click", listener); | return () => window.removeEventListener("click", listener); | ||||
| fileInputRef.current.value = ""; | fileInputRef.current.value = ""; | ||||
| fileInputRef.current.click(); | fileInputRef.current.click(); | ||||
| }; | }; | ||||
| const handleImage = (event) => { | |||||
| const handleImage = (file) => { | |||||
| let reader = new FileReader(); | let reader = new FileReader(); | ||||
| reader.readAsDataURL(event.target.files[0]); | |||||
| reader.readAsDataURL(file); | |||||
| // reader.readAsBinaryString(file); | |||||
| reader.onload = () => { | reader.onload = () => { | ||||
| if (props.setImage) props.setImage(reader.result); | |||||
| if (props.setImage) props.setImage(file); | |||||
| console.log(reader.result); | |||||
| setImage(reader.result); | setImage(reader.result); | ||||
| }; | }; | ||||
| reader.onerror = (error) => { | reader.onerror = (error) => { | ||||
| className={props.className} | className={props.className} | ||||
| onClick={!image ? handleChange : () => {}} | onClick={!image ? handleChange : () => {}} | ||||
| hasImage={props.image} | hasImage={props.image} | ||||
| component="form" | |||||
| > | > | ||||
| <AddFile type="file" ref={fileInputRef} onInput={handleImage} accept=".jpg, .jpeg, .png" /> | |||||
| <AddFile | |||||
| type="file" | |||||
| ref={fileInputRef} | |||||
| onInput={(event) => handleImage(event.target.files[0])} | |||||
| accept=".jpg, .jpeg, .png" | |||||
| formEncType="multipart/form-data" | |||||
| /> | |||||
| {image ? ( | {image ? ( | ||||
| <React.Fragment> | <React.Fragment> | ||||
| <ImageUploaded src={image} draggable={false} ref={imageRef} /> | <ImageUploaded src={image} draggable={false} ref={imageRef} /> |
| import StatisticDetails from "./StatisticDetails/StatisticDetails"; | import StatisticDetails from "./StatisticDetails/StatisticDetails"; | ||||
| import PIBDetail from "./OfferDetail/PIB/PIBDetail"; | import PIBDetail from "./OfferDetail/PIB/PIBDetail"; | ||||
| import CategoryDetail from "./OfferDetail/Category/CategoryDetail"; | import CategoryDetail from "./OfferDetail/Category/CategoryDetail"; | ||||
| import useIsMobile from "../../../hooks/useIsMobile"; | |||||
| import { getImageUrl, variants } from "../../../util/helpers/imageUrlGetter"; | |||||
| const ItemDetailsHeaderCard = (props) => { | const ItemDetailsHeaderCard = (props) => { | ||||
| const history = useHistory(); | const history = useHistory(); | ||||
| const chats = useSelector(selectLatestChats); | const chats = useSelector(selectLatestChats); | ||||
| const offer = props.offer; | const offer = props.offer; | ||||
| const userId = useSelector(selectUserId); | const userId = useSelector(selectUserId); | ||||
| const { isMobile } = useIsMobile(); | |||||
| const handleGoProfile = () => { | const handleGoProfile = () => { | ||||
| history.push(`/profile/${offer?.offer?.userId}`); | history.push(`/profile/${offer?.offer?.userId}`); | ||||
| halfwidth={props.halfwidth ? 1 : 0} | halfwidth={props.halfwidth ? 1 : 0} | ||||
| > | > | ||||
| <HeaderTop> | <HeaderTop> | ||||
| <OfferImage src={offer?.companyData?.image} /> | |||||
| {/* <OfferImage src={offer?.companyData?.image} /> */} | |||||
| <OfferImage | |||||
| src={getImageUrl( | |||||
| offer?.companyData?.image, | |||||
| variants.profileImage, | |||||
| isMobile | |||||
| )} | |||||
| /> | |||||
| <OfferDetails> | <OfferDetails> | ||||
| <OfferTitle isMyProfile={props.isMyProfile} onClick={handleGoProfile}> | <OfferTitle isMyProfile={props.isMyProfile} onClick={handleGoProfile}> | ||||
| {offer?.companyData?.company?.name} | {offer?.companyData?.company?.name} |
| align-items: center; | align-items: center; | ||||
| justify-content: center; | justify-content: center; | ||||
| height: 70vh; | height: 70vh; | ||||
| text-align: center; | |||||
| `; | `; | ||||
| export const OffersNotFoundHeading = styled(Typography)` | export const OffersNotFoundHeading = styled(Typography)` |
| SecondaryTextContainer, | SecondaryTextContainer, | ||||
| } from "./HeaderPopover.styled"; | } from "./HeaderPopover.styled"; | ||||
| import { useTranslation } from "react-i18next"; | import { useTranslation } from "react-i18next"; | ||||
| import useIsMobile from "../../../hooks/useIsMobile"; | |||||
| import { getImageUrl, variants } from "../../../util/helpers/imageUrlGetter"; | |||||
| const HeaderPopover = (props) => { | const HeaderPopover = (props) => { | ||||
| const { t } = useTranslation(); | const { t } = useTranslation(); | ||||
| const {isMobile} = useIsMobile(); | |||||
| return ( | return ( | ||||
| <HeaderPopoverContainer> | <HeaderPopoverContainer> | ||||
| <PopoverTitle p={2}>{props.title}</PopoverTitle> | <PopoverTitle p={2}>{props.title}</PopoverTitle> | ||||
| {props.isProfile ? ( | {props.isProfile ? ( | ||||
| <PopoverListItemProfileAvatar | <PopoverListItemProfileAvatar | ||||
| alt={item.alt} | alt={item.alt} | ||||
| src={item.src} | |||||
| src={getImageUrl(item.src, variants.profileCard, isMobile)} | |||||
| onClick={item?.onClick} | onClick={item?.onClick} | ||||
| /> | /> | ||||
| ) : ( | ) : ( | ||||
| <PopoverListItemAvatar | <PopoverListItemAvatar | ||||
| alt={item.alt} | alt={item.alt} | ||||
| src={item.src} | |||||
| src={getImageUrl(item.src, variants.profileCard, isMobile)} | |||||
| onClick={item?.onClick} | onClick={item?.onClick} | ||||
| /> | /> | ||||
| )} | )} |
| ProfilePIB, | ProfilePIB, | ||||
| } from "./ProfileMainInfo.styled"; | } from "./ProfileMainInfo.styled"; | ||||
| import { useTranslation } from "react-i18next"; | import { useTranslation } from "react-i18next"; | ||||
| import { getImageUrl, variants } from "../../../util/helpers/imageUrlGetter"; | |||||
| import useIsMobile from "../../../hooks/useIsMobile"; | |||||
| const ProfileMainInfo = (props) => { | const ProfileMainInfo = (props) => { | ||||
| const { t } = useTranslation(); | const { t } = useTranslation(); | ||||
| const { isMobile } = useIsMobile(); | |||||
| return ( | return ( | ||||
| <ProfileMainInfoContainer> | <ProfileMainInfoContainer> | ||||
| <AvatarImageContainer> | <AvatarImageContainer> | ||||
| <AvatarImage | |||||
| {/* <AvatarImage | |||||
| alt={props.profile?.company?.name} | alt={props.profile?.company?.name} | ||||
| src={props.profile?.image} | src={props.profile?.image} | ||||
| /> */} | |||||
| <AvatarImage | |||||
| src={getImageUrl( | |||||
| props.profile?.image, | |||||
| variants.profileImage, | |||||
| isMobile | |||||
| )} | |||||
| /> | /> | ||||
| </AvatarImageContainer> | </AvatarImageContainer> | ||||
| <ProfileMainInfoGrid> | <ProfileMainInfoGrid> |
| import React, { useState } from "react"; | |||||
| import React, { useEffect, useState } from "react"; | |||||
| import PropTypes from "prop-types"; | import PropTypes from "prop-types"; | ||||
| import { | import { | ||||
| RegisterPageContainer, | RegisterPageContainer, | ||||
| } | } | ||||
| }; | }; | ||||
| useEffect(() => { | |||||
| console.log("informations", informations) | |||||
| }, [informations]) | |||||
| const registerUser = (values) => { | const registerUser = (values) => { | ||||
| dispatch( | dispatch( |
| // baseURL: "http://192.168.88.175:3005/", | // baseURL: "http://192.168.88.175:3005/", | ||||
| // baseURL: "http://192.168.88.143:3001/", // DULE | // baseURL: "http://192.168.88.143:3001/", // DULE | ||||
| baseURL: "https://trampa-api-test.dilig.net/", | baseURL: "https://trampa-api-test.dilig.net/", | ||||
| // baseURL: "http://localhost:3001/", | |||||
| headers: { | headers: { | ||||
| "Content-Type": "application/json", | "Content-Type": "application/json", | ||||
| }, | }, |
| import io from "socket.io-client"; | |||||
| export const socket = io("https://trampa-api-test.dilig.net/", { | |||||
| autoConnect: true, | |||||
| transports: ["websocket"], | |||||
| reconnectionAttempts: 5, | |||||
| }); | |||||
| export const socketInit = (userId) => { | |||||
| socket.auth = { | |||||
| userId, | |||||
| }; | |||||
| }; | |||||
| export const sendMessage = (chatId, userId, text, receiverUserId) => { | |||||
| socket.emit("private_message", { | |||||
| chatId, | |||||
| receiverUserId, | |||||
| message: { | |||||
| userId, | |||||
| text, | |||||
| }, | |||||
| }); | |||||
| }; | |||||
| export const addMesageListener = (listener) => { | |||||
| return socket.on("private_message", listener); | |||||
| }; | |||||
| export const removeMessageListener = () => { | |||||
| return socket.off("private_message"); | |||||
| }; |
| export const CHAT_SET = createSetType("CHAT_SET"); | export const CHAT_SET = createSetType("CHAT_SET"); | ||||
| export const CHAT_ONE_SET = createSetType("CHAT_ONE_SET"); | export const CHAT_ONE_SET = createSetType("CHAT_ONE_SET"); | ||||
| export const CHAT_CLEAR = createSetType("CHAT_CLEAR"); | export const CHAT_CLEAR = createSetType("CHAT_CLEAR"); | ||||
| export const CHAT_ADD_MESSAGE = createSetType("CHAT_ADD_MESSAGE"); | |||||
| // export const ADD_ONE_CHAT = "CHAT_ONE_ADD"; | // export const ADD_ONE_CHAT = "CHAT_ONE_ADD"; |
| import { CHAT_CLEAR, CHAT_FETCH, CHAT_FETCH_ERROR, CHAT_FETCH_SUCCESS, CHAT_HEADER_FETCH, CHAT_HEADER_FETCH_ERROR, CHAT_HEADER_FETCH_SUCCESS, CHAT_NEW_FETCH, CHAT_NEW_FETCH_ERROR, CHAT_NEW_FETCH_SUCCESS, CHAT_ONE_FETCH, CHAT_ONE_FETCH_ERROR, CHAT_ONE_FETCH_SUCCESS, CHAT_ONE_SET, CHAT_SEND_ERROR, CHAT_SEND_FETCH, CHAT_SEND_SUCCESS, CHAT_SET } from "./chatActionConstants"; | |||||
| import { CHAT_ADD_MESSAGE, CHAT_CLEAR, CHAT_FETCH, CHAT_FETCH_ERROR, CHAT_FETCH_SUCCESS, CHAT_HEADER_FETCH, CHAT_HEADER_FETCH_ERROR, CHAT_HEADER_FETCH_SUCCESS, CHAT_NEW_FETCH, CHAT_NEW_FETCH_ERROR, CHAT_NEW_FETCH_SUCCESS, CHAT_ONE_FETCH, CHAT_ONE_FETCH_ERROR, CHAT_ONE_FETCH_SUCCESS, CHAT_ONE_SET, CHAT_SEND_ERROR, CHAT_SEND_FETCH, CHAT_SEND_SUCCESS, CHAT_SET } from "./chatActionConstants"; | |||||
| export const fetchChats = (payload) => ({ | export const fetchChats = (payload) => ({ | ||||
| type: CHAT_FETCH, | type: CHAT_FETCH, | ||||
| }) | }) | ||||
| export const startNewChatError = () => ({ | export const startNewChatError = () => ({ | ||||
| type: CHAT_NEW_FETCH_ERROR | type: CHAT_NEW_FETCH_ERROR | ||||
| }) | |||||
| export const addNewMessage = (payload) => ({ | |||||
| type: CHAT_ADD_MESSAGE, | |||||
| payload | |||||
| }) | }) |
| // const baseURL = "http://192.168.88.143:3001/"; // DULE | // const baseURL = "http://192.168.88.143:3001/"; // DULE | ||||
| // const baseURL = "http://192.168.88.175:3005/"; | // const baseURL = "http://192.168.88.175:3005/"; | ||||
| const baseURL = "https://trampa-api-test.dilig.net/"; | const baseURL = "https://trampa-api-test.dilig.net/"; | ||||
| // const baseURL = "http://localhost:3001/"; | |||||
| //Interceptor unique name | //Interceptor unique name | ||||
| export const accessTokensMiddlewareInterceptorName = "ACCESS_TOKEN_INTERCEPTOR"; | export const accessTokensMiddlewareInterceptorName = "ACCESS_TOKEN_INTERCEPTOR"; | ||||
| const axiosResponse = await axios.post(`${baseURL}auth/refresh`, { | const axiosResponse = await axios.post(`${baseURL}auth/refresh`, { | ||||
| token: refresh, | token: refresh, | ||||
| }); | }); | ||||
| const newToken = axiosResponse.data.token; | |||||
| const newToken = axiosResponse.data; | |||||
| response.headers.Authorization = `Bearer ${newToken}`; | response.headers.Authorization = `Bearer ${newToken}`; | ||||
| dispatch(refreshUserToken(newToken)); | dispatch(refreshUserToken(newToken)); | ||||
| } | } |
| import { CHAT_CLEAR, CHAT_ONE_SET, CHAT_SET } from "../../actions/chat/chatActionConstants" | |||||
| import createReducer from "../../utils/createReducer" | |||||
| import { | |||||
| CHAT_ADD_MESSAGE, | |||||
| CHAT_CLEAR, | |||||
| CHAT_ONE_SET, | |||||
| CHAT_SET, | |||||
| } from "../../actions/chat/chatActionConstants"; | |||||
| import createReducer from "../../utils/createReducer"; | |||||
| const initialState = { | const initialState = { | ||||
| latestChats: [], | |||||
| selectedChat: {} | |||||
| } | |||||
| latestChats: [], | |||||
| selectedChat: {}, | |||||
| }; | |||||
| export default createReducer( | export default createReducer( | ||||
| { | |||||
| [CHAT_SET]: setChats, | |||||
| [CHAT_ONE_SET]: setOneChat, | |||||
| [CHAT_CLEAR]: clearChats | |||||
| }, | |||||
| initialState | |||||
| ) | |||||
| { | |||||
| [CHAT_SET]: setChats, | |||||
| [CHAT_ONE_SET]: setOneChat, | |||||
| [CHAT_CLEAR]: clearChats, | |||||
| [CHAT_ADD_MESSAGE]: addNewMessage, | |||||
| }, | |||||
| initialState | |||||
| ); | |||||
| function setChats(state, action) { | function setChats(state, action) { | ||||
| return { | |||||
| ...state, | |||||
| latestChats: [...action.payload] | |||||
| } | |||||
| return { | |||||
| ...state, | |||||
| latestChats: [...action.payload], | |||||
| }; | |||||
| } | } | ||||
| function setOneChat(state, action) { | function setOneChat(state, action) { | ||||
| return { | |||||
| ...state, | |||||
| selectedChat: action.payload | |||||
| } | |||||
| return { | |||||
| ...state, | |||||
| selectedChat: action.payload, | |||||
| }; | |||||
| } | } | ||||
| function clearChats() { | function clearChats() { | ||||
| return initialState; | |||||
| } | |||||
| return initialState; | |||||
| } | |||||
| function addNewMessage(state, { payload }) { | |||||
| let allChats = [...state.latestChats]; | |||||
| let chat = allChats.find((item) => item.chat._id === payload._id); | |||||
| console.log(chat); | |||||
| chat = { | |||||
| ...chat, | |||||
| chat: { | |||||
| ...chat.chat, | |||||
| messages: [...chat.chat.messages, payload.message], | |||||
| }, | |||||
| }; | |||||
| allChats = allChats.filter((item) => item.chat._id !== chat.chat._id); | |||||
| allChats = [chat, ...allChats]; | |||||
| let newSelectedChat = { ...state.selectedChat }; | |||||
| console.log(chat); | |||||
| console.log(newSelectedChat); | |||||
| if (newSelectedChat.chat._id === chat.chat._id) newSelectedChat = { ...newSelectedChat, chat: chat.chat }; | |||||
| return { | |||||
| ...state, | |||||
| latestChats: [...allChats], | |||||
| selectedChat: { ...newSelectedChat }, | |||||
| }; | |||||
| } |
| "?" + newQueryString.toString() | "?" + newQueryString.toString() | ||||
| ); | ); | ||||
| yield put(setTotalOffers(data.data.total)); | yield put(setTotalOffers(data.data.total)); | ||||
| yield put(setOffers(data.data.offers.filter(offer => !offer.pinned))); | |||||
| yield put(setPinnedOffers(data.data.offers.filter(offer => offer.pinned))); | |||||
| yield put(setOffers(data.data.offers.filter((offer) => !offer.pinned))); | |||||
| yield put( | |||||
| setPinnedOffers(data.data.offers.filter((offer) => offer.pinned)) | |||||
| ); | |||||
| yield put(fetchOffersSuccess()); | yield put(fetchOffersSuccess()); | ||||
| } catch (e) { | } catch (e) { | ||||
| yield put(fetchOffersError()); | yield put(fetchOffersError()); | ||||
| function* createOffer(payload) { | function* createOffer(payload) { | ||||
| try { | try { | ||||
| yield call(attemptAddOffer, payload.payload.values.offerData); | |||||
| console.log(payload.payload.values.offerData); | |||||
| const offerData = payload.payload.values.offerData; | |||||
| const formData = new FormData(); | |||||
| formData.append("category[name]", offerData.category.name); | |||||
| formData.append("condition", offerData.condition); | |||||
| formData.append("description", offerData.description); | |||||
| // formData.append("file", JSON.stringify(offerData.images)) | |||||
| for (var i = 0; i < offerData.images.length; i++) { | |||||
| formData.append("file", offerData.images[i]); | |||||
| } | |||||
| formData.append("location[city]", offerData.location.city); | |||||
| formData.append("name", offerData.name); | |||||
| formData.append("subcategory", offerData.subcategory); | |||||
| yield call(attemptAddOffer, formData); | |||||
| yield put(addOfferSuccess()); | yield put(addOfferSuccess()); | ||||
| if (payload.payload.handleApiResponseSuccess) { | if (payload.payload.handleApiResponseSuccess) { | ||||
| yield call(payload.payload.handleApiResponseSuccess); | yield call(payload.payload.handleApiResponseSuccess); | ||||
| function* editOffer(payload) { | function* editOffer(payload) { | ||||
| try { | try { | ||||
| console.log(payload); | |||||
| const offerId = payload.payload.offerId; | const offerId = payload.payload.offerId; | ||||
| const editedData = payload.payload.offerData; | |||||
| yield call(attemptEditOffer, offerId, editedData); | |||||
| // const editedData = payload.payload.offerData; | |||||
| const offerData = payload.payload.offerData; | |||||
| const formData = new FormData(); | |||||
| formData.append("category[name]", offerData.category.name); | |||||
| formData.append("condition", offerData.condition); | |||||
| formData.append("description", offerData.description); | |||||
| // const oldImages = []; | |||||
| for (var i = 0; i < offerData.images.length; i++) { | |||||
| if (offerData.images[i] !== null) { | |||||
| if (typeof offerData.images[i] === "string") { | |||||
| formData.append("images[]", offerData.images[i]); | |||||
| } else { | |||||
| formData.append("file", offerData.images[i]); | |||||
| } | |||||
| } | |||||
| } | |||||
| // if (oldImages.length > 0) { | |||||
| // formData.append("images", JSON.stringify(oldImages)); | |||||
| // } | |||||
| // if (oldImages.length === offerData.images.length) { | |||||
| // formData.append("file", ""); | |||||
| // } | |||||
| formData.append("location[city]", offerData.location.city); | |||||
| formData.append("name", offerData.name); | |||||
| formData.append("subcategory", offerData.subcategory); | |||||
| yield call(attemptEditOffer, offerId, formData); | |||||
| yield put(editOfferSuccess()); | yield put(editOfferSuccess()); | ||||
| if (payload.payload.handleApiResponseSuccess) { | if (payload.payload.handleApiResponseSuccess) { | ||||
| yield call(payload.payload.handleApiResponseSuccess); | yield call(payload.payload.handleApiResponseSuccess); |
| function* changeMineProfile(payload) { | function* changeMineProfile(payload) { | ||||
| try { | try { | ||||
| let image; | |||||
| if (payload.payload.firmLogo.includes("data:image")) { | |||||
| image = payload.payload.firmLogo | |||||
| .replace("data:image/jpeg;base64,", "") | |||||
| .replace("data:image/jpg;base64,", "") | |||||
| .replace("data:image/png;base64,", ""); | |||||
| } else if (payload.payload.firmLogo === "") { | |||||
| image = ""; | |||||
| } | |||||
| // console.log(payload); | |||||
| // let image; | |||||
| // if (payload.payload.firmLogo) { | |||||
| // image = payload.payload.firmLogo; | |||||
| // } else if (payload.payload.firmLogo === "") { | |||||
| // image = ""; | |||||
| // } | |||||
| // const reqData = { | |||||
| // company: { | |||||
| // name: payload.payload.firmName, | |||||
| // PIB: payload.payload.firmPIB, | |||||
| // contacts: { | |||||
| // telephone: payload.payload.firmPhone.toString(), | |||||
| // location: payload.payload.firmLocation ?? "", | |||||
| // web: payload.payload.firmWebsite, | |||||
| // }, | |||||
| // }, | |||||
| // image: image, | |||||
| // }; | |||||
| const reqData = { | |||||
| company: { | |||||
| name: payload.payload.firmName, | |||||
| PIB: payload.payload.firmPIB, | |||||
| contacts: { | |||||
| telephone: payload.payload.firmPhone.toString(), | |||||
| location: payload.payload.firmLocation ?? "", | |||||
| web: payload.payload.firmWebsite, | |||||
| }, | |||||
| }, | |||||
| image: image, | |||||
| }; | |||||
| // if (payload.payload.firmLogo?.includes("https")) delete reqData.image; | |||||
| // if (reqData.company.contacts.telephone.length === 0) | |||||
| // delete reqData.company.contacts.telephone; | |||||
| // if (reqData.company.contacts.location.length === 0) | |||||
| // delete reqData.company.contacts.location; | |||||
| // if (reqData.company.contacts.web.length === 0) | |||||
| // delete reqData.company.contacts.web; | |||||
| if (payload.payload.firmLogo.includes("https")) delete reqData.image; | |||||
| if (reqData.company.contacts.telephone.length === 0) | |||||
| delete reqData.company.contacts.telephone; | |||||
| if (reqData.company.contacts.location.length === 0) | |||||
| delete reqData.company.contacts.location; | |||||
| if (reqData.company.contacts.web.length === 0) | |||||
| delete reqData.company.contacts.web; | |||||
| const requestBody = new FormData(); | |||||
| if (typeof payload.payload.firmLogo !== "string") | |||||
| requestBody.append("file", payload.payload.firmLogo); | |||||
| requestBody.append("company[name]", payload.payload.firmName); | |||||
| requestBody.append("company[PIB]", payload.payload.firmPIB); | |||||
| if (payload.payload.firmPhone.toString().length !== 0) | |||||
| requestBody.append( | |||||
| "company[contacts][telephone]", | |||||
| payload.payload.firmPhone | |||||
| ); | |||||
| if (payload.payload.firmLocation.toString().length !== 0) | |||||
| requestBody.append( | |||||
| "company[contacts][location]", | |||||
| payload.payload.firmLocation | |||||
| ); | |||||
| if (payload.payload.firmWebsite.toString().length !== 0) | |||||
| requestBody.append("company[contacts][web]", payload.payload.firmWebsite); | |||||
| const userId = yield select(selectUserId); | const userId = yield select(selectUserId); | ||||
| const data = yield call(attemptEditProfile, userId, reqData); | |||||
| const data = yield call(attemptEditProfile, userId, requestBody); | |||||
| yield put(editMineProfileSuccess()); | yield put(editMineProfileSuccess()); | ||||
| if (payload.payload.handleApiResponseSuccess) { | if (payload.payload.handleApiResponseSuccess) { | ||||
| yield call(payload.payload.handleApiResponseSuccess); | yield call(payload.payload.handleApiResponseSuccess); |
| function* fetchRegisterUser({ payload }) { | function* fetchRegisterUser({ payload }) { | ||||
| try { | try { | ||||
| let requestData = { | |||||
| email: payload.values.mail.toString(), | |||||
| password: payload.values.password.toString(), | |||||
| image: payload.values.image | |||||
| .replace("data:image/jpeg;base64,", "") | |||||
| .replace("data:image/jpg;base64,", "") | |||||
| .replace("data:image/png;base64,", ""), | |||||
| company: { | |||||
| name: payload.values.nameOfFirm.toString(), | |||||
| PIB: payload.values.PIB.toString(), | |||||
| contacts: { | |||||
| telephone: payload.values.phoneNumber.toString(), | |||||
| location: payload.values.location.toString(), | |||||
| web: payload.values.website.toString(), | |||||
| }, | |||||
| }, | |||||
| }; | |||||
| if (payload.values.phoneNumber?.length === 0) | |||||
| delete requestData.company.contacts.telephone; | |||||
| if (payload.values.location?.length === 0) | |||||
| delete requestData.company.contacts.location; | |||||
| if (payload.values.website?.length === 0) | |||||
| delete requestData.company.contacts.web; | |||||
| yield call(attemptRegister, requestData); | |||||
| const requestBody = new FormData(); | |||||
| console.log("requeest body image", payload.values.image); | |||||
| requestBody.append("email", payload.values.mail); | |||||
| requestBody.append("password", payload.values.password); | |||||
| requestBody.append("file", payload.values.image); | |||||
| requestBody.append("company[name]", payload.values.nameOfFirm); | |||||
| requestBody.append("company[PIB]", payload.values.PIB); | |||||
| if (payload.values.phoneNumber.toString().length !== 0) | |||||
| requestBody.append("company[contacts][telephone]", payload.values.phoneNumber); | |||||
| if (payload.values.location.toString().length !== 0) | |||||
| requestBody.append("company[contacts][location]", payload.values.location); | |||||
| if (payload.values.website.toString().length !== 0) | |||||
| requestBody.append("company[contacts][web]", payload.values.website); | |||||
| yield call(attemptRegister, requestBody); | |||||
| const { data } = yield call(attemptLogin, { | const { data } = yield call(attemptLogin, { | ||||
| email: payload.values.mail, | email: payload.values.mail, |
| const CLOUDFLARE = "CLOUDFLARE"; | |||||
| // const IMAGE_KIT = "IMAGEKIT"; | |||||
| const IMAGE_PLATFORM = CLOUDFLARE; | |||||
| export const variants = { | |||||
| offerCard: "offerCard", | |||||
| offerDetails: "offerDetails", | |||||
| profileImage: "profileImage", | |||||
| reviewCard: "reviewCard", | |||||
| chatHeader: "chatHeader", | |||||
| chatMessage: "chatMessage", | |||||
| chatCard: "chatCard", | |||||
| deleteChat: "chatHeader", | |||||
| profileCard: "profileCard" | |||||
| } | |||||
| const cloudFlareVariants = { | |||||
| offerCard: "primary", | |||||
| offerCardMobile: "primaryMobile", | |||||
| offerDetails: "primary", | |||||
| offerDetailsMobile: "primary", | |||||
| profileImage: "primary", | |||||
| profileImageMobile: "profileImage", | |||||
| reviewCard: "review", | |||||
| reviewCardMobile: "review", | |||||
| chatHeader: "chatHeader", | |||||
| chatHeaderMobile: "chatHeader", | |||||
| chatMessage: "chatHeader", | |||||
| chatMessageMobile: "chatHeader", | |||||
| chatCard: "chatCard", | |||||
| chatCardMobile: "chatCard", | |||||
| profileCard: "profileCard" | |||||
| } | |||||
| export const getImageUrl = (imageUrl, variant, isMobile) => { | |||||
| let imageVariant = ""; | |||||
| if (IMAGE_PLATFORM === CLOUDFLARE) { | |||||
| imageVariant = isMobile ? cloudFlareVariants[variant + "Mobile"] : cloudFlareVariants[variant]; | |||||
| } | |||||
| return imageUrl + imageVariant; | |||||
| } |