on master help sign in
inviter: display and recover deterministic invites
be56aeeLiam Fitzgerald
src/store/lib/usePointStore.js+6−1
@@ -25,7 +25,12 @@ export default function usePointStore() {
25 );
25 );
26
26
27 // sync all of the on-chain info required to display a foreign point
27 // sync all of the on-chain info required to display a foreign point
28− const syncForeignPoint = useCallback(async point => {}, []);
28+ const syncForeignPoint = useCallback(
29+ async point => {
30+ syncDetails(point);
31+ },
32+ [syncDetails]
33+ );
29
34
30 // sync all of the on-chain info required for a point that the user owns
35 // sync all of the on-chain info required for a point that the user owns
31 const syncOwnedPoint = useCallback(
36 const syncOwnedPoint = useCallback(
src/views/Invite/Cohort.js+54−44
@@ -3,6 +3,7 @@ import { Grid, Flex, Button } from 'indigo-react';
3import * as ob from 'urbit-ob';
3import * as ob from 'urbit-ob';
4import { Just, Nothing } from 'folktale/maybe';
4import { Just, Nothing } from 'folktale/maybe';
5import cn from 'classnames';
5import cn from 'classnames';
6+import { delegatedSending } from 'azimuth-js';
6
7
7import { usePointCursor } from 'store/pointCursor';
8import { usePointCursor } from 'store/pointCursor';
8import { usePointCache } from 'store/pointCache';
9import { usePointCache } from 'store/pointCache';
@@ -27,6 +28,7 @@ import Inviter from 'views/Invite/Inviter';
27import { ReactComponent as SearchIcon } from 'assets/search.svg';
28import { ReactComponent as SearchIcon } from 'assets/search.svg';
28import CopyButton from 'components/CopyButton';
29import CopyButton from 'components/CopyButton';
29import { useSyncForeignPoints } from 'lib/useSyncPoints';
30import { useSyncForeignPoints } from 'lib/useSyncPoints';
31+import { useNetwork } from 'store/network';
30
32
31function SearchInput({ className, value, onChange }) {
33function SearchInput({ className, value, onChange }) {
32 return (
34 return (
@@ -164,10 +166,14 @@ function CohortMemberExpanded({ point, className, ...rest }) {
164 const { sentInvites, acceptedInvites } = useInvites(point);
166 const { sentInvites, acceptedInvites } = useInvites(point);
165 const { getDetails } = usePointCache();
167 const { getDetails } = usePointCache();
166 const { authToken } = useWallet();
168 const { authToken } = useWallet();
169+ const { contracts } = useNetwork();
167− const details = getDetails(point).getOrElse({});
170+ const details = getDetails(point);
168− const { active } = details;
171+ const { active } = details.getOrElse({});
169 const patp = useMemo(() => ob.patp(point), [point]);
172 const patp = useMemo(() => ob.patp(point), [point]);
173+ const colors = useMemo(
170− const colors = !active ? ['#ee892b', '#FFFFFF'] : ['#000000', '#FFFFFF'];
174+ () => (!active ? ['#ee892b', '#FFFFFF'] : ['#000000', '#FFFFFF']),
175+ [active]
176+ );
171
177
172 const [code, setCode] = useState(Nothing());
178 const [code, setCode] = useState(Nothing());
173 const [codeVisible, setCodeVisible] = useState(false);
179 const [codeVisible, setCodeVisible] = useState(false);
@@ -175,20 +181,35 @@ function CohortMemberExpanded({ point, className, ...rest }) {
175 useEffect(() => {
181 useEffect(() => {
176 const fetchWallet = async () => {
182 const fetchWallet = async () => {
177 const _authToken = authToken.getOrElse(null);
183 const _authToken = authToken.getOrElse(null);
184+ const _details = details.getOrElse(null);
185+ const _contracts = contracts.getOrElse(null);
186+ if (
178− if (!_authToken || active) {
187+ !_authToken ||
188+ !_details ||
189+ _details.active ||
190+ !_contracts ||
191+ !codeVisible
192+ ) {
193+ setCode(Nothing());
179 return;
194 return;
180 }
195 }
181− const ticket = await wg.makeDeterministicTicket(point, _authToken);
196+ const { ticket, owner } = await wg.generateTemporaryDeterministicWallet(
197+ point,
198+ _authToken
199+ );
200+
201+ if (owner.keys.address !== _details.transferProxy) {
202+ setCode(Just(null));
203+ } else {
182− setCode(Just(ticket));
204+ setCode(Just(ticket));
205+ }
183 };
206 };
184 fetchWallet();
207 fetchWallet();
185− }, [authToken, point, active]);
208+ }, [codeVisible]);
186
209
187− const DetailText = useCallback(
188− () =>
210+ useEffect(() => {
189− !active ? 'Pending' : <> {matchBlinky(sentInvites)} points invited </>,
211+ setCodeVisible(false);
190− [active, sentInvites]
212+ }, [point]);
191− );
192
213
193 return (
214 return (
194 <Grid justify="between" className={cn('b1 b-gray2', className)} {...rest}>
215 <Grid justify="between" className={cn('b1 b-gray2', className)} {...rest}>
@@ -209,20 +230,27 @@ function CohortMemberExpanded({ point, className, ...rest }) {
209 col>
230 col>
210 Invite Code
231 Invite Code
211 </Grid.Item>
232 </Grid.Item>
212− <Grid.Item
213− cols={[4, 10]}
214− className="mb-auto mt1 f6 gray4"
233+ <Grid.Item cols={[4, 10]} className="mb-auto mt1 f6 gray4">
215− as={Flex}
234+ {(code.getOrElse(true) === null &&
216− col
235+ 'This invite code cannot be recovered') ||
217− onClick={() => setCodeVisible(r => !r)}>
218− {hideIf(!codeVisible, matchBlinky(code))}
236+ hideIf(!codeVisible, matchBlinky(code))}
219 </Grid.Item>
237 </Grid.Item>
238+ {!codeVisible && (
220− <Grid.Item
239+ <Grid.Item
240+ cols={[10, 13]}
241+ className="mh-auto f6 underline pointer"
242+ onClick={() => setCodeVisible(true)}>
243+ Show
244+ </Grid.Item>
245+ )}
246+ {codeVisible && code.getOrElse('') !== null && (
247+ <Grid.Item
221− className="mh-auto f6"
248+ className="mh-auto f6 t-right"
222− cols={[10, 13]}
249+ cols={[10, 13]}
223− as={CopyButton}
250+ as={CopyButton}
224− text={code.getOrElse('')}
251+ text={code.getOrElse('')}
225− />
252+ />
253+ )}
226 </>
254 </>
227 )}
255 )}
228
256
@@ -244,22 +272,6 @@ function CohortMemberExpanded({ point, className, ...rest }) {
244 </Grid.Item>
272 </Grid.Item>
245 </>
273 </>
246 )}
274 )}
247−
248− {/* <Flex.Item>Invite Code</Flex.Item> */}
249− {/* <Flex.Item>{matchBlinky(code)}</Flex.Item> */}
250− {/* <span className="pointer underline">Get Invite code </span> */}
251− {/* <br /> */}
252− {/* {resend && <span>{matchBlinky(code)}</span>} */}
253− {/* </Grid.Item> */}
254− {/* {resend && ( */}
255− {/* <Grid.Item cols={[5, 13]} rows={[2, 3]} className="mv-auto"></Grid.Item> */}
256− {/* )} */}
257− {/* <Grid.Item justify="evenly" as={Flex} col className="mono f6 ph4"> */}
258− {/* <Flex.Item>{patp}</Flex.Item> */}
259− {/* <Flex.Item className="gray4"> */}
260− {/* <DetailText /> */}
261− {/* </Flex.Item> */}
262− {/* </Grid.Item> */}
263 </Grid>
275 </Grid>
264 );
276 );
265}
277}
@@ -293,9 +305,7 @@ export default function InviteCohort() {
293
305
294 const [selectedInvite, _setSelectedInvite] = useState();
306 const [selectedInvite, _setSelectedInvite] = useState();
295
307
296− useEffect(() => {
297− Promise.all(_acceptedPoints.map(i => syncDetails(i)));
298− }, [_acceptedPoints, syncDetails]);
308+ useSyncForeignPoints([..._acceptedPoints, ..._pendingPoints]);
299
309
300 const setSelectedInvite = useCallback(
310 const setSelectedInvite = useCallback(
301 p => _setSelectedInvite(old => (old === p ? null : p)),
311 p => _setSelectedInvite(old => (old === p ? null : p)),
src/views/Login/Ledger.js+1−1
@@ -78,7 +78,7 @@ export default function Ledger({ className, goHome }) {
78 walletHdPath: addHdPrefix(values.hdpath),
78 walletHdPath: addHdPrefix(values.hdpath),
79 });
79 });
80
80
81− setAuthToken(authToken);
81+ setAuthToken(Just(authToken));
82 setWallet(Just(hd));
82 setWallet(Just(hd));
83 setWalletHdPath(addHdPrefix(values.hdpath));
83 setWalletHdPath(addHdPrefix(values.hdpath));
84 } catch (error) {
84 } catch (error) {
src/views/Login/Metamask.js+1−1
@@ -33,7 +33,7 @@ export default function Metamask({ className, goHome }) {
33 web3: _web3,
33 web3: _web3,
34 });
34 });
35
35
36− setAuthToken(authToken);
36+ setAuthToken(Just(authToken));
37 setWallet(Just(wallet));
37 setWallet(Just(wallet));
38 setWalletType(WALLET_TYPES.METAMASK);
38 setWalletType(WALLET_TYPES.METAMASK);
39 } catch (e) {
39 } catch (e) {
src/views/Login/Trezor.js+1−1
@@ -74,7 +74,7 @@ export default function Trezor({ className, goHome }) {
74 walletHdPath: values.hdPath,
74 walletHdPath: values.hdPath,
75 });
75 });
76
76
77− setAuthToken(authToken);
77+ setAuthToken(Just(authToken));
78 setWallet(Just(hd));
78 setWallet(Just(hd));
79 setWalletHdPath(values.hdPath);
79 setWalletHdPath(values.hdPath);
80 },
80 },