diff --git a/frontend/pages/stream/index.js b/frontend/pages/stream/index.js
index 5c11e593..06921ccf 100644
--- a/frontend/pages/stream/index.js
+++ b/frontend/pages/stream/index.js
@@ -1,6 +1,49 @@
+import React, { useContext } from "react";
import { getLayout } from "../../src/layouts/EntriesLayout";
+import StreamEntryDetails from "../../src/components/SteamEntryDetails";
+import UIContext from "../../src/core/providers/UIProvider/context";
+import {
+ Box,
+ Heading,
+ Text,
+ Stack,
+ UnorderedList,
+ ListItem,
+} from "@chakra-ui/react";
const Entry = () => {
- return "";
+ const ui = useContext(UIContext);
+
+ // return "";
+ if (ui.currentTransaction) {
+ return ;
+ } else
+ return (
+
+ <>
+
+ Stream view
+
+ In this view you can follow events that happen on your subscribed
+ addresses
+
+
+
+ Click filter icon on right top corner to filter by specific
+ address across your subscriptions
+
+
+ On event cards you can click at right corner to see detailed
+ view!
+
+
+ For any adress of interest here you can copy it and subscribe at
+ subscription screen
+
+
+
+ >
+
+ );
};
Entry.getLayout = getLayout;
export default Entry;
diff --git a/frontend/pages/subscriptions.js b/frontend/pages/subscriptions.js
index 867bf8ea..5a9cbb5e 100644
--- a/frontend/pages/subscriptions.js
+++ b/frontend/pages/subscriptions.js
@@ -62,7 +62,6 @@ const Subscriptions = () => {
{
{!ui.isMobileView && (
<>
-
- }
- onClick={() => {
- router.push(
- {
- pathname: "/stream",
- query: router.query,
- },
- undefined,
- { shallow: false }
- );
- // router.params?.entryId && ui.entriesViewMode === "entry"
- // ?
- ui.setEntriesViewMode("list");
- // : router.nextRouter.back();
- }}
- >
- Back to stream
-
-
@@ -185,8 +153,9 @@ const AppNavbar = () => {
aria-label="App navigation"
icon={}
onClick={() => {
- router.params?.entryId && ui.entriesViewMode === "entry"
- ? ui.setEntriesViewMode("list")
+ router.nextRouter.pathname === "/stream" &&
+ ui.isEntryDetailView
+ ? ui.setEntryDetailView(false)
: router.nextRouter.back();
}}
/>
@@ -216,8 +185,9 @@ const AppNavbar = () => {
aria-label="App navigation"
icon={}
onClick={() => {
- router.params?.entryId && ui.entriesViewMode === "list"
- ? ui.setEntriesViewMode("entry")
+ router.nextRouter.pathname === "/stream" &&
+ !ui.isEntryDetailView
+ ? ui.setEntryDetailView(true)
: history.forward();
}}
/>
diff --git a/frontend/src/components/EntriesNavigation.js b/frontend/src/components/EntriesNavigation.js
index 870c7b52..687eb850 100644
--- a/frontend/src/components/EntriesNavigation.js
+++ b/frontend/src/components/EntriesNavigation.js
@@ -32,7 +32,6 @@ import {
TagCloseButton,
Stack,
Spacer,
- useBoolean,
} from "@chakra-ui/react";
import { useSubscriptions } from "../core/hooks";
import StreamEntry from "./StreamEntry";
@@ -40,9 +39,7 @@ import UIContext from "../core/providers/UIProvider/context";
import { FaFilter } from "react-icons/fa";
import useStream from "../core/hooks/useStream";
import { ImCancelCircle } from "react-icons/im";
-import { IoStopCircleOutline, IoPlayCircleOutline } from "react-icons/io5";
-const pageSize = 25;
const FILTER_TYPES = {
ADDRESS: 0,
GAS: 1,
@@ -64,7 +61,6 @@ const CONDITION = {
const EntriesNavigation = () => {
const ui = useContext(UIContext);
- const [isStreamOn, setStreamState] = useBoolean(true);
const { isOpen, onOpen, onClose } = useDisclosure();
const { subscriptionsCache } = useSubscriptions();
const [newFilterState, setNewFilterState] = useState([
@@ -150,29 +146,22 @@ const EntriesNavigation = () => {
};
const { EntriesPages, isLoading, refetch, isFetching, remove } = useStream({
- refreshRate: 1500,
searchQuery: ui.searchTerm,
start_time: streamBoundary.start_time,
end_time: streamBoundary.end_time,
include_start: streamBoundary.include_start,
include_end: streamBoundary.include_end,
- enabled: isStreamOn,
updateStreamBoundaryWith: updateStreamBoundaryWith,
streamBoundary: streamBoundary,
setStreamBoundary: setStreamBoundary,
isContent: false,
});
- // const handleScroll = ({ currentTarget }) => {
- // if (
- // currentTarget.scrollTop + currentTarget.clientHeight >=
- // 0.5 * currentTarget.scrollHeight
- // ) {
- // if (!isLoading && hasPreviousPage) {
- // fetchPreviousPage();
- // }
- // }
- // };
+ useEffect(() => {
+ if (!streamBoundary.start_time && !streamBoundary.end_time) {
+ refetch();
+ }
+ }, [streamBoundary, refetch]);
const setFilterProps = useCallback(
(filterIdx, props) => {
@@ -436,20 +425,6 @@ const EntriesNavigation = () => {
-
- setStreamState.toggle()}
- icon={
- isStreamOn ? (
-
- ) : (
-
- )
- }
- colorScheme={isStreamOn ? "unsafe" : "suggested"}
- />
-
{filterState.map((filter, idx) => {
if (filter.type === FILTER_TYPES.DISABLED) return "";
return (
diff --git a/frontend/pages/stream/[entryId].js b/frontend/src/components/SteamEntryDetails.js
similarity index 53%
rename from frontend/pages/stream/[entryId].js
rename to frontend/src/components/SteamEntryDetails.js
index a233f5e2..8d0f46e4 100644
--- a/frontend/pages/stream/[entryId].js
+++ b/frontend/src/components/SteamEntryDetails.js
@@ -1,49 +1,15 @@
import React, { useContext } from "react";
-import {
- Flex,
- HStack,
- Skeleton,
- Box,
- Heading,
- Center,
- Spinner,
-} from "@chakra-ui/react";
-import { useTxInfo, useRouter } from "../../src/core/hooks";
-import FourOFour from "../../src/components/FourOFour";
-import FourOThree from "../../src/components/FourOThree";
-import Tags from "../../src/components/Tags";
-import { getLayout } from "../../src/layouts/EntriesLayout";
-import Scrollable from "../../src/components/Scrollable";
-import TxInfo from "../../src/components/TxInfo";
-import UIContext from "../../src/core/providers/UIProvider/context";
+import { Flex, HStack, Skeleton, Heading } from "@chakra-ui/react";
+import { useTxInfo } from "../core/hooks";
+import FourOFour from "./FourOFour";
+import FourOThree from "./FourOThree";
+import Tags from "./Tags";
+import Scrollable from "./Scrollable";
+import TxInfo from "./TxInfo";
+import UIContext from "../core/providers/UIProvider/context";
-const Entry = () => {
+const SteamEntryDetails = () => {
const ui = useContext(UIContext);
- const router = useRouter();
- const { entryId } = router.params;
-
- const callReroute = () => {
- ui.setEntriesViewMode("list");
- router.push({
- pathname: `/stream`,
- query: router.query,
- });
- const LoadingSpinner = () => (
-
-
-
-
-
- );
- return ;
- };
const {
data: entry,
@@ -54,20 +20,13 @@ const Entry = () => {
error,
} = useTxInfo({ tx: ui.currentTransaction });
if (!isFetching) {
- return callReroute();
+ return "";
}
if (isError && error.response.status === 404) return ;
if (isError && error.response.status === 403) return ;
- // if (!entry || isLoading) return "";
return (
-
+
{
{
);
};
-Entry.getLayout = getLayout;
-export default Entry;
+export default SteamEntryDetails;
diff --git a/frontend/src/components/StreamEntry.js b/frontend/src/components/StreamEntry.js
index 52ab9284..50b9f56b 100644
--- a/frontend/src/components/StreamEntry.js
+++ b/frontend/src/components/StreamEntry.js
@@ -9,16 +9,18 @@ import {
Heading,
Image,
useMediaQuery,
+ Spacer,
+ Spinner,
} from "@chakra-ui/react";
import moment from "moment";
import { ArrowRightIcon } from "@chakra-ui/icons";
-import { useRouter } from "../core/hooks";
import UIContext from "../core/providers/UIProvider/context";
import { useToast } from "../core/hooks";
+import { useSubscriptions } from "../core/hooks";
const StreamEntry = ({ entry }) => {
+ const { subscriptionsCache } = useSubscriptions();
const ui = useContext(UIContext);
- const router = useRouter();
const [copyString, setCopyString] = useState(false);
const { onCopy, hasCopied } = useClipboard(copyString, 1);
const toast = useToast();
@@ -31,17 +33,19 @@ const StreamEntry = ({ entry }) => {
onCopy();
}
}, [copyString, onCopy, hasCopied, toast]);
- const handleViewClicked = (entryId) => {
- ui.setEntryId(entryId);
- ui.setEntriesViewMode("entry");
- ui.setCurrentTransaction(entry);
- router.push({
- pathname: `/stream/${entry.hash}`,
- query: router.query,
- });
- };
const [showFullView] = useMediaQuery(["(min-width: 420px)"]);
+ if (subscriptionsCache.isLoading) return ;
+
+ const from_color =
+ subscriptionsCache.data.subscriptions.find((obj) => {
+ return obj.address === entry.from_address;
+ })?.color ?? "gray.500";
+
+ const to_color =
+ subscriptionsCache.data.subscriptions.find((obj) => {
+ return obj.address === entry.to_address;
+ })?.color ?? "gray.500";
return (
{
bgColor="gray.100"
borderColor="white.300"
transition="0.1s"
- _hover={{ bg: "secondary.200" }}
flexBasis="50px"
direction="row"
justifySelf="center"
@@ -80,9 +83,11 @@ const StreamEntry = ({ entry }) => {
borderLeftRadius="md"
borderColor="gray.600"
spacing={0}
- h="fit-content"
- minH="fit-content"
+ h="auto"
+ // h="fit-content"
+ // minH="fit-content"
overflowX="hidden"
+ overflowY="visible"
>
{
textAlign="center"
spacing={0}
alignItems="center"
- bgColor="brand.300"
+ bgColor="gray.300"
>
{
"https://upload.wikimedia.org/wikipedia/commons/0/05/Ethereum_logo_2014.svg"
}
/>
- Ethereum blockhain
+
+ Hash
+
+
+ setCopyString(entry.hash)}
+ pr={12}
+ >
+ {entry.hash}
+
{
spacing={0}
>
{
mx={0}
py="2px"
fontSize="sm"
- bgColor="secondary.200"
+ bgColor={from_color}
isTruncated
w="calc(100%)"
h="100%"
@@ -166,9 +181,8 @@ const StreamEntry = ({ entry }) => {
spacing={0}
>
{
{
-
-
+
+
{
{entry.gasPrice}
-
-
+
+
{
{entry.gas}
-
-
+
+
{
{entry.value}
-
- {entry.timestamp && (
-
+
+
+
-
+ Nonce:
+
+
+ setCopyString(entry.value)}
+ >
+ {entry.nonce}
+
+
+
+ {entry.timestamp && (
+
+
{moment(entry.timestamp * 1000).format(
"DD MMM, YYYY, HH:mm:ss"
)}{" "}
-
+
)}
-
+
)}
handleViewClicked(entry)}
+ onClick={() => ui.setCurrentTransaction(entry)}
h="full"
// minH="24px"
borderLeftRadius={0}
variant="solid"
px={0}
minW="24px"
- colorScheme="suggested"
+ colorScheme="secondary"
icon={}
/>
diff --git a/frontend/src/components/TxInfo.js b/frontend/src/components/TxInfo.js
index f86132dc..f0afcc9f 100644
--- a/frontend/src/components/TxInfo.js
+++ b/frontend/src/components/TxInfo.js
@@ -10,7 +10,9 @@ import {
VStack,
} from "@chakra-ui/react";
import { Table, Thead, Tbody, Tr, Th, Td } from "@chakra-ui/react";
-const toEth = (wei) => { return wei / Math.pow(10, 18) }
+const toEth = (wei) => {
+ return wei / Math.pow(10, 18);
+};
const TxABI = (props) => {
const byteCode = props.byteCode;
const abi = props.abi;
diff --git a/frontend/src/core/hooks/useStream.js b/frontend/src/core/hooks/useStream.js
index 6d20bec6..d8dee482 100644
--- a/frontend/src/core/hooks/useStream.js
+++ b/frontend/src/core/hooks/useStream.js
@@ -3,14 +3,12 @@ import { useQuery } from "react-query";
import { queryCacheProps } from "./hookCommon";
const useJournalEntries = ({
- refreshRate,
searchQuery,
start_time,
end_time,
include_start,
include_end,
updateStreamBoundaryWith,
- enabled,
}) => {
// set our get method
const getStream =
@@ -49,7 +47,6 @@ const useJournalEntries = ({
// TODO(andrey): Response should send page parameters inside "boundary" object (can be null).
updateStreamBoundaryWith(response.boundaries);
},
- enabled: !!enabled,
}
);
diff --git a/frontend/src/core/hooks/useTxInfo.js b/frontend/src/core/hooks/useTxInfo.js
index 6e6bfb32..602eda5a 100644
--- a/frontend/src/core/hooks/useTxInfo.js
+++ b/frontend/src/core/hooks/useTxInfo.js
@@ -10,13 +10,21 @@ const useTxInfo = (transaction) => {
return response.data;
};
const { data, isLoading, isFetchedAfterMount, refetch, isError, error } =
- useQuery(["txinfo", (transaction.tx && transaction.tx.hash)], getTxInfo, {
+ useQuery(["txinfo", transaction.tx && transaction.tx.hash], getTxInfo, {
...queryCacheProps,
enabled: !!transaction.tx,
onError: (error) => toast(error, "error"),
});
const isFetching = !!transaction.tx;
- return { data, isFetchedAfterMount, isLoading, refetch, isFetching, isError, error };
+ return {
+ data,
+ isFetchedAfterMount,
+ isLoading,
+ refetch,
+ isFetching,
+ isError,
+ error,
+ };
};
export default useTxInfo;
diff --git a/frontend/src/core/providers/UIProvider/index.js b/frontend/src/core/providers/UIProvider/index.js
index 9bdf23da..2f6319ae 100644
--- a/frontend/src/core/providers/UIProvider/index.js
+++ b/frontend/src/core/providers/UIProvider/index.js
@@ -30,8 +30,6 @@ const UIProvider = ({ children }) => {
const { modal, toggleModal } = useContext(ModalContext);
const [searchTerm, setSearchTerm] = useQuery("q", "", true, false);
- const [entryId, setEntryId] = useState();
-
const [searchBarActive, setSearchBarActive] = useState(false);
// ****** Session state *****
@@ -136,22 +134,30 @@ const UIProvider = ({ children }) => {
// *********** Entries layout states **********************
+ //
+ // const [entryId, setEntryId] = useState();
+ // Current transaction to show in sideview
+ const [currentTransaction, _setCurrentTransaction] = useState(undefined);
+ const [isEntryDetailView, setEntryDetailView] = useState(false);
+
+ const setCurrentTransaction = (tx) => {
+ _setCurrentTransaction(tx);
+ setEntryDetailView(!!tx);
+ };
+
/**
* States that entries list box should be expanded
* Default true in mobile mode and false in desktop mode
*/
const [entriesViewMode, setEntriesViewMode] = useState(
- router.params?.entryId ? "entry" : "list"
+ isMobileView ? "list" : "split"
);
useEffect(() => {
- setEntriesViewMode(router.params?.entryId ? "entry" : "list");
- // eslint-disable-next-line react-hooks/exhaustive-deps
- }, [router.params?.id]);
-
- // *********** TX stream state **********************
-
- const [currentTransaction, setCurrentTransaction] = useState(undefined);
+ setEntriesViewMode(
+ isMobileView ? (isEntryDetailView ? "entry" : "list") : "split"
+ );
+ }, [isEntryDetailView, isMobileView]);
// ********************************************************
@@ -175,14 +181,13 @@ const UIProvider = ({ children }) => {
isLoggedIn,
isAppReady,
entriesViewMode,
- setEntriesViewMode,
+ setEntryDetailView,
modal,
toggleModal,
- entryId,
- setEntryId,
sessionId,
currentTransaction,
setCurrentTransaction,
+ isEntryDetailView,
}}
>
{children}
diff --git a/frontend/src/layouts/EntriesLayout.js b/frontend/src/layouts/EntriesLayout.js
index 119e50ff..5a1f23b5 100644
--- a/frontend/src/layouts/EntriesLayout.js
+++ b/frontend/src/layouts/EntriesLayout.js
@@ -20,6 +20,7 @@ const EntriesLayout = (props) => {
<>
{
? { transition: "1s", width: "100%" }
: ui.entriesViewMode === "entry"
? { transition: "1s", width: "0%" }
- : { overflowX: "hidden", height: "100%" }
+ : {
+ overflowX: "hidden",
+ height: "100%",
+ width: ui.isMobileView ? "100%" : "55%",
+ }
}
pane2Style={
ui.entriesViewMode === "entry"
diff --git a/frontend/styles/styles.css b/frontend/styles/styles.css
index 80b52141..ab3e2ad8 100644
--- a/frontend/styles/styles.css
+++ b/frontend/styles/styles.css
@@ -46,6 +46,7 @@
}
.Resizer.disabled:hover {
border-color: transparent;
+ cursor: inherit;
}
.triangle {
@@ -156,7 +157,7 @@
word-break: break-word;
}
-.mde-preview * {
+.mde-preview * {
word-break: break-word;
}
@@ -181,12 +182,10 @@
padding: 0.5rem;
}
-
code {
white-space: pre-line !important;
}
-
.fade-in-section {
opacity: 0;
transform: translateY(5vh);
@@ -195,8 +194,7 @@ code {
will-change: opacity, visibility;
}
.fade-in-section.is-visible {
-
opacity: 1;
transform: none;
visibility: visible;
-}
\ No newline at end of file
+}