on master help sign in
roller: move polling to it's own file, change polling behavior to be less request heavy
6ba8792Hunter Miller
src/Bridge.js+8
@@ -25,6 +25,7 @@ import Modal from 'components/L2/Modal';
25import { useRollerStore } from 'store/rollerStore';
25import { useRollerStore } from 'store/rollerStore';
26import { Box } from '@tlon/indigo-react';
26import { Box } from '@tlon/indigo-react';
27import LoadingOverlay from 'components/L2/LoadingOverlay';
27import LoadingOverlay from 'components/L2/LoadingOverlay';
28+import { useRollerPoller } from 'lib/useRollerPoller';
28
29
29const INITIAL_NETWORK_TYPE = isRopsten
30const INITIAL_NETWORK_TYPE = isRopsten
30 ? NETWORK_TYPES.ROPSTEN
31 ? NETWORK_TYPES.ROPSTEN
@@ -72,6 +73,12 @@ function useInitialRoutes() {
72 return [{ key: ROUTE_NAMES.LOGIN }];
73 return [{ key: ROUTE_NAMES.LOGIN }];
73}
74}
74
75
76+function Poller() {
77+ useRollerPoller();
78+
79+ return null;
80+}
81+
75function Bridge() {
82function Bridge() {
76 const initialRoutes = useInitialRoutes();
83 const initialRoutes = useInitialRoutes();
77 const { loading, modalText, setModalText } = useRollerStore();
84 const { loading, modalText, setModalText } = useRollerStore();
@@ -105,6 +112,7 @@ function Bridge() {
105 <Box width="280px">{modalText}</Box>
112 <Box width="280px">{modalText}</Box>
106 </Modal>
113 </Modal>
107 <LoadingOverlay loading={loading} />
114 <LoadingOverlay loading={loading} />
115+ <Poller />
108 </Provider>
116 </Provider>
109 </WithErrorBoundary>
117 </WithErrorBoundary>
110 );
118 );
src/lib/useRoller.ts−32
@@ -27,7 +27,6 @@ import {
27 generateInviteWallet,
27 generateInviteWallet,
28 getPendingSpawns,
28 getPendingSpawns,
29 submitL2Transaction,
29 submitL2Transaction,
30− getTimeToNextBatch,
31 registerProxyAddress,
30 registerProxyAddress,
32 isL2Spawn,
31 isL2Spawn,
33} from './utils/roller';
32} from './utils/roller';
@@ -44,7 +43,6 @@ import {
44} from '@urbit/roller-api';
43} from '@urbit/roller-api';
45
44
46import Point, { PointField, Points } from './types/Point';
45import Point, { PointField, Points } from './types/Point';
47−import { useTimerStore } from 'store/timerStore';
48import { ReticketParams, SendL2Params } from './types/L2Transaction';
46import { ReticketParams, SendL2Params } from './types/L2Transaction';
49import { L1Point } from './types/L1Point';
47import { L1Point } from './types/L1Point';
50import { ddmmmYYYY } from './utils/date';
48import { ddmmmYYYY } from './utils/date';
@@ -53,8 +51,6 @@ import { useWalletConnect } from './useWalletConnect';
53import { PendingL1Txn } from './types/PendingL1Transaction';
51import { PendingL1Txn } from './types/PendingL1Transaction';
54import { TRANSACTION_PROGRESS } from './reticket';
52import { TRANSACTION_PROGRESS } from './reticket';
55
53
56−const ONE_SECOND = 1000;
57−
58interface UpdateParams {
54interface UpdateParams {
59 point: number;
55 point: number;
60 message?: string;
56 message?: string;
@@ -90,11 +86,8 @@ export default function useRoller() {
90 const allPoints: any = usePointCache();
86 const allPoints: any = usePointCache();
91 const getDetails = allPoints?.getDetails;
87 const getDetails = allPoints?.getDetails;
92
88
93− const { setNextRoll } = useTimerStore();
94−
95 const {
89 const {
96 invitesLoading,
90 invitesLoading,
97− nextBatchTime,
98 point,
91 point,
99 points,
92 points,
100 pointList,
93 pointList,
@@ -1050,31 +1043,6 @@ export default function useRoller() {
1050 fetchConfig();
1043 fetchConfig();
1051 }, [config, fetchConfig]);
1044 }, [config, fetchConfig]);
1052
1045
1053− useEffect(() => {
1054− const time = ONE_SECOND;
1055−
1056− const interval = setInterval(() => {
1057− const nextRoll = getTimeToNextBatch(nextBatchTime, new Date().getTime());
1058− setNextRoll(nextRoll);
1059−
1060− if (nextBatchTime - ONE_SECOND <= new Date().getTime()) {
1061− api.getRollerConfig().then(response => {
1062− setNextBatchTime(response.nextBatch);
1063− });
1064−
1065− getPendingTransactions();
1066−
1067− setTimeout(() => {
1068− if (!point.isDefault) {
1069− getInvites(); // This will also get pending txns
1070− }
1071− }, TEN_SECONDS); // Should this be more like a minute?
1072− }
1073− }, time);
1074−
1075− return () => clearInterval(interval);
1076− }, [point, nextBatchTime, getPendingTransactions, getInvites]); // eslint-disable-line react-hooks/exhaustive-deps
1077−
1078 return {
1046 return {
1079 api,
1047 api,
1080 changeSponsorship,
1048 changeSponsorship,
src/lib/useRollerPoller.tsnew file+42
@@ -0,0 +1,42 @@
1+import { useEffect, useState } from 'react';
2+import { useRollerStore } from 'store/rollerStore';
3+import { useTimerStore } from 'store/timerStore';
4+import { ONE_SECOND, TEN_SECONDS } from './constants';
5+import useRoller from './useRoller';
6+import { getTimeToNextBatch } from './utils/roller';
7+
8+export function useRollerPoller() {
9+ const { nextBatchTime, setNextBatchTime, setNextRoll } = useTimerStore();
10+ const { point } = useRollerStore();
11+ const { api, getInvites, getPendingTransactions } = useRoller();
12+ const [time, setTime] = useState(ONE_SECOND);
13+
14+ useEffect(() => {
15+ const interval = setInterval(async () => {
16+ const nextRoll = getTimeToNextBatch(nextBatchTime, new Date().getTime());
17+ setNextRoll(nextRoll);
18+
19+ if (nextBatchTime - ONE_SECOND <= new Date().getTime()) {
20+ const response = await api.getRollerConfig();
21+
22+ if (response.nextBatch === nextBatchTime) {
23+ // exponentially back off or cap at polling every minute
24+ setTime(Math.min(60 * ONE_SECOND, time + time));
25+ return;
26+ }
27+
28+ setTime(ONE_SECOND); // reset the timer
29+ setNextBatchTime(response.nextBatch);
30+ getPendingTransactions();
31+
32+ setTimeout(() => {
33+ if (!point.isDefault) {
34+ getInvites(); // This will also get pending txns
35+ }
36+ }, TEN_SECONDS); // Should this be more like a minute?
37+ }
38+ }, time);
39+
40+ return () => clearInterval(interval);
41+ }, [time, point, nextBatchTime, getPendingTransactions, getInvites]); // eslint-disable-line react-hooks/exhaustive-deps
42+}