on c19b2a8 help sign in
bridge/src/views/Admin/Reticket/ReticketExecute.js
181 lines 5.5 kB history raw
1import React, { useState, useCallback } from 'react';
2import { Just, Nothing } from 'folktale/maybe';
3import { Grid, H4, Text, ErrorText } from 'indigo-react';
5import {
6 reticketPointBetweenWallets,
7 TRANSACTION_PROGRESS,
8} from 'lib/reticket';
9import * as need from 'lib/need';
10import useLifecycle from 'lib/useLifecycle';
11import { WALLET_TYPES } from 'lib/wallet';
12import convertToInt from 'lib/convertToInt';
13import useBlockWindowClose from 'lib/useBlockWindowClose';
15import { useNetwork } from 'store/network';
16import { useWallet } from 'store/wallet';
17import { usePointCursor } from 'store/pointCursor';
18import { usePointCache } from 'store/pointCache';
19import { useHistory } from 'store/history';
21import { RestartButton, ForwardButton } from 'components/Buttons';
22import WarningBox from 'components/WarningBox';
23import LoadingBar from 'components/LoadingBar';
24import NeedFundsNotice from 'components/NeedFundsNotice';
26const labelForProgress = progress => {
27 if (progress <= 0) {
28 return 'Starting...';
29 } else if (progress <= TRANSACTION_PROGRESS.GENERATING) {
30 return 'Generating Ethereum Transactions...';
31 } else if (progress <= TRANSACTION_PROGRESS.SIGNING) {
32 return 'Signing Ethereum Transactions...';
33 } else if (progress <= TRANSACTION_PROGRESS.FUNDING) {
34 return 'Funding Ethereum Transactions...';
35 } else if (progress <= TRANSACTION_PROGRESS.TRANSFERRING) {
36 return 'Transferring ID...';
37 } else if (progress <= TRANSACTION_PROGRESS.CLEANING) {
38 return 'Cleaning Up...';
39 } else if (progress <= TRANSACTION_PROGRESS.DONE) {
40 return 'Done';
41 }
42};
44export default function ReticketExecute({ newWallet, setNewWallet }) {
45 const { popTo, names, reset } = useHistory();
46 const { web3, contracts, networkType } = useNetwork();
47 const { wallet, setWalletType, resetWallet, setUrbitWallet } = useWallet();
48 const { pointCursor } = usePointCursor();
49 const { getDetails } = usePointCache();
51 const [generalError, setGeneralError] = useState();
52 const [progress, setProgress] = useState(0);
53 const [needFunds, setNeedFunds] = useState();
54 const isDone = progress >= 1.0;
56 useBlockWindowClose();
58 // start reticketing transactions on mount
59 useLifecycle(() => {
60 (async () => {
61 const point = need.point(pointCursor);
62 const details = need.details(getDetails(point));
63 const networkRevision = convertToInt(details.keyRevisionNumber, 10);
64 try {
65 await reticketPointBetweenWallets({
66 fromWallet: need.wallet(wallet),
67 toWallet: newWallet.value.wallet,
68 point: point,
69 web3: need.web3(web3),
70 contracts: need.contracts(contracts),
71 networkType,
72 onUpdate: handleUpdate,
73 nextRevision: networkRevision + 1,
74 });
75 } catch (err) {
76 setGeneralError(err);
77 }
78 })();
79 });
81 const goToRestart = useCallback(() => {
82 reset();
83 setNewWallet(Nothing());
84 }, [reset, setNewWallet]);
86 const loginAndGoHome = useCallback(() => {
87 // set wallet state
88 resetWallet();
89 setWalletType(WALLET_TYPES.TICKET);
90 setUrbitWallet(Just(newWallet.value.wallet));
91 // (implicit) pointCursor stays the same
92 // rediect to point
93 popTo(names.POINT);
94 }, [resetWallet, setWalletType, setUrbitWallet, newWallet, popTo, names]);
96 const handleUpdate = useCallback(
97 ({ type, state, value }) => {
98 switch (type) {
99 case 'progress':
100 return setProgress(state);
101 case 'askFunding':
102 return setNeedFunds(value);
103 case 'gotFunding':
104 return setNeedFunds(false);
105 default:
106 console.error(`Unknown update: ${type}`);
107 }
108 },
109 [setProgress, setNeedFunds]
110 );
112 const renderAdditionalInfo = () => {
113 if (generalError) {
114 return (
115 <>
116 <Grid.Item full className="mt4">
117 <ErrorText>{generalError.message.toString()}</ErrorText>
118 </Grid.Item>
119 <Grid.Item
120 full
121 className="mt4"
122 as={RestartButton}
123 solid
124 onClick={goToRestart}>
125 Restart
126 </Grid.Item>
127 </>
128 );
129 }
131 if (needFunds) {
132 return (
133 <Grid.Item full as={NeedFundsNotice} className="mt4" {...needFunds} />
134 );
135 }
137 return (
138 <Grid.Item full as={WarningBox} className="mt4">
139 Never give your Master Ticket to anyone
140 </Grid.Item>
141 );
142 };
144 return (
145 <Grid className="mt4">
146 <Grid.Item full as={H4}>
147 {labelForProgress(progress)}
148 </Grid.Item>
150 {isDone ? (
151 <>
152 <Grid.Item full as={Text} className="mt4">
153 Your changes are now reflected on-chain and you can use the new
154 ticket to manage your point.
155 </Grid.Item>
156 <Grid.Item
157 full
158 as={ForwardButton}
159 solid
160 className="mt4"
161 accessory="↺"
162 onClick={loginAndGoHome}>
163 Login with New Master Ticket
164 </Grid.Item>
165 </>
166 ) : (
167 <>
168 <Grid.Item full as={Grid} className="mt4" gap={3}>
169 <Grid.Item full as={LoadingBar} progress={progress} />
170 <Grid.Item full as={Text} className="f5 green4">
171 This process can take up to 5 minutes to complete. Don't close
172 this page until the process is complete.
173 </Grid.Item>
174 </Grid.Item>
176 {renderAdditionalInfo()}
177 </>
178 )}
179 </Grid>
180 );